From 1486d15000f6d1d75e614eec0906b905bbf3336e Mon Sep 17 00:00:00 2001 From: sleybo Date: Thu, 25 Jan 2007 12:58:44 +0000 Subject: [PATCH] [OPENSM] update opensm from the OFED linux trunk. include many changes and new files. git-svn-id: svn://openib.tc.cornell.edu/gen1@571 ad392aa1-c5ef-ae45-8dd8-e69d62a5ef86 --- trunk/ulp/opensm/user/README.opensm-build | 24 + trunk/ulp/opensm/user/TODO | 16 + trunk/ulp/opensm/user/config.h | 71 + trunk/ulp/opensm/user/doc/OpenSM_PKey_Mgr.txt | 79 + trunk/ulp/opensm/user/doc/OpenSM_RN_0_3_1.pdf | Bin 0 -> 83938 bytes trunk/ulp/opensm/user/doc/OpenSM_UM_0_3.pdf | Bin 0 -> 223001 bytes trunk/ulp/opensm/user/doc/current-routing.txt | 202 + trunk/ulp/opensm/user/doc/modular-routing.txt | 78 + .../doc/opensm_release_notes_openib-2.0.5.txt | 487 ++ trunk/ulp/opensm/user/doc/qos-config.txt | 45 + .../user/include/complib/cl_dispatcher.h | 660 ++ .../user/include/complib/cl_event_wheel.h | 493 ++ trunk/ulp/opensm/user/include/iba/ib_types.h | 971 ++- .../user/include/iba/ib_types_extended.h | 2 +- .../user/include/opensm/osm_attrib_req.h | 6 +- .../ulp/opensm/user/include/opensm/osm_base.h | 162 +- .../opensm/user/include/opensm/osm_console.h | 6 +- trunk/ulp/opensm/user/include/opensm/osm_db.h | 14 +- .../opensm/user/include/opensm/osm_db_pack.h | 5 +- .../opensm/user/include/opensm/osm_drop_mgr.h | 7 +- .../opensm/user/include/opensm/osm_errors.h | 21 +- .../opensm/user/include/opensm/osm_fwd_tbl.h | 12 +- .../opensm/user/include/opensm/osm_helper.h | 34 +- .../opensm/user/include/opensm/osm_inform.h | 94 +- .../opensm/user/include/opensm/osm_lid_mgr.h | 37 +- .../user/include/opensm/osm_lin_fwd_rcv.h | 7 +- .../include/opensm/osm_lin_fwd_rcv_ctrl.h | 9 +- .../user/include/opensm/osm_lin_fwd_tbl.h | 16 +- .../opensm/user/include/opensm/osm_link_mgr.h | 8 +- .../ulp/opensm/user/include/opensm/osm_log.h | 112 +- .../opensm/user/include/opensm/osm_mad_pool.h | 5 +- .../ulp/opensm/user/include/opensm/osm_madw.h | 112 +- .../opensm/user/include/opensm/osm_matrix.h | 13 +- .../user/include/opensm/osm_mcast_fwd_rcv.h | 7 +- .../include/opensm/osm_mcast_fwd_rcv_ctrl.h | 9 +- .../user/include/opensm/osm_mcast_mgr.h | 52 +- .../user/include/opensm/osm_mcast_tbl.h | 38 +- .../opensm/user/include/opensm/osm_mcm_info.h | 8 +- .../opensm/user/include/opensm/osm_mcm_port.h | 24 +- .../opensm/user/include/opensm/osm_msgdef.h | 29 +- .../opensm/user/include/opensm/osm_mtl_bind.h | 6 +- .../opensm/user/include/opensm/osm_mtree.h | 20 +- .../user/include/opensm/osm_multicast.h | 62 +- .../ulp/opensm/user/include/opensm/osm_node.h | 36 +- .../user/include/opensm/osm_node_desc_rcv.h | 7 +- .../include/opensm/osm_node_desc_rcv_ctrl.h | 9 +- .../user/include/opensm/osm_node_info_rcv.h | 18 +- .../include/opensm/osm_node_info_rcv_ctrl.h | 18 +- .../opensm/user/include/opensm/osm_opensm.h | 76 +- .../user/include/opensm/osm_partition.h | 168 +- .../ulp/opensm/user/include/opensm/osm_path.h | 19 +- .../ulp/opensm/user/include/opensm/osm_pkey.h | 282 +- .../opensm/user/include/opensm/osm_pkey_mgr.h | 190 +- .../opensm/user/include/opensm/osm_pkey_rcv.h | 8 +- .../user/include/opensm/osm_pkey_rcv_ctrl.h | 16 +- .../ulp/opensm/user/include/opensm/osm_port.h | 334 +- .../user/include/opensm/osm_port_info_rcv.h | 19 +- .../include/opensm/osm_port_info_rcv_ctrl.h | 18 +- .../user/include/opensm/osm_port_profile.h | 30 +- .../user/include/opensm/osm_rand_fwd_tbl.h | 16 +- .../user/include/opensm/osm_remote_sm.h | 23 +- .../ulp/opensm/user/include/opensm/osm_req.h | 16 +- .../opensm/user/include/opensm/osm_req_ctrl.h | 17 +- .../ulp/opensm/user/include/opensm/osm_resp.h | 9 +- .../opensm/user/include/opensm/osm_router.h | 323 + trunk/ulp/opensm/user/include/opensm/osm_sa.h | 139 +- .../include/opensm/osm_sa_class_port_info.h | 8 +- .../opensm/osm_sa_class_port_info_ctrl.h | 16 +- .../include/opensm/osm_sa_guidinfo_record.h | 10 +- .../opensm/osm_sa_guidinfo_record_ctrl.h | 10 +- .../user/include/opensm/osm_sa_informinfo.h | 52 +- .../include/opensm/osm_sa_informinfo_ctrl.h | 26 +- .../user/include/opensm/osm_sa_lft_record.h | 31 +- .../include/opensm/osm_sa_lft_record_ctrl.h | 19 +- .../user/include/opensm/osm_sa_link_record.h | 9 +- .../include/opensm/osm_sa_link_record_ctrl.h | 18 +- .../user/include/opensm/osm_sa_mad_ctrl.h | 16 +- .../include/opensm/osm_sa_mcmember_record.h | 88 +- .../opensm/osm_sa_mcmember_record_ctrl.h | 17 +- .../include/opensm/osm_sa_multipath_record.h | 273 + .../opensm/osm_sa_multipath_record_ctrl.h | 260 + .../user/include/opensm/osm_sa_node_record.h | 9 +- .../include/opensm/osm_sa_node_record_ctrl.h | 10 +- .../user/include/opensm/osm_sa_path_record.h | 15 +- .../include/opensm/osm_sa_path_record_ctrl.h | 10 +- .../user/include/opensm/osm_sa_pkey_record.h | 10 +- .../include/opensm/osm_sa_pkey_record_ctrl.h | 10 +- .../include/opensm/osm_sa_portinfo_record.h | 21 +- .../opensm/osm_sa_portinfo_record_ctrl.h | 10 +- .../user/include/opensm/osm_sa_response.h | 21 +- .../include/opensm/osm_sa_service_record.h | 8 +- .../opensm/osm_sa_service_record_ctrl.h | 10 +- .../user/include/opensm/osm_sa_slvl_record.h | 10 +- .../include/opensm/osm_sa_slvl_record_ctrl.h | 10 +- .../include/opensm/osm_sa_sminfo_record.h | 26 +- .../opensm/osm_sa_sminfo_record_ctrl.h | 10 +- .../include/opensm/osm_sa_sw_info_record.h | 306 + .../opensm/osm_sa_sw_info_record_ctrl.h | 259 + .../user/include/opensm/osm_sa_vlarb_record.h | 17 +- .../include/opensm/osm_sa_vlarb_record_ctrl.h | 10 +- .../opensm/user/include/opensm/osm_service.h | 17 +- .../user/include/opensm/osm_slvl_map_rcv.h | 8 +- .../include/opensm/osm_slvl_map_rcv_ctrl.h | 16 +- trunk/ulp/opensm/user/include/opensm/osm_sm.h | 17 +- .../user/include/opensm/osm_sm_mad_ctrl.h | 31 +- .../user/include/opensm/osm_sm_state_mgr.h | 49 +- .../user/include/opensm/osm_sminfo_rcv.h | 7 +- .../user/include/opensm/osm_sminfo_rcv_ctrl.h | 9 +- .../user/include/opensm/osm_state_mgr.h | 26 +- .../user/include/opensm/osm_state_mgr_ctrl.h | 16 +- .../opensm/user/include/opensm/osm_stats.h | 6 +- .../opensm/user/include/opensm/osm_subnet.h | 513 +- .../user/include/opensm/osm_sw_info_rcv.h | 17 +- .../include/opensm/osm_sw_info_rcv_ctrl.h | 18 +- .../user/include/opensm/osm_sweep_fail_ctrl.h | 10 +- .../opensm/user/include/opensm/osm_switch.h | 343 +- .../opensm/user/include/opensm/osm_trap_rcv.h | 41 +- .../user/include/opensm/osm_trap_rcv_ctrl.h | 9 +- .../user/include/opensm/osm_ts_useraccess.h | 6 +- .../user/include/opensm/osm_ucast_mgr.h | 83 +- .../opensm/user/include/opensm/osm_umadt.h | 7 +- .../opensm/user/include/opensm/osm_version.h | 7 +- .../opensm/user/include/opensm/osm_vl15intf.h | 7 +- .../user/include/opensm/osm_vl_arb_rcv.h | 52 +- .../user/include/opensm/osm_vl_arb_rcv_ctrl.h | 20 +- trunk/ulp/opensm/user/include/opensm/st.h | 5 +- trunk/ulp/opensm/user/include/unistd.h | 38 + .../opensm/user/include/vendor/osm_vendor.h | 6 +- .../user/include/vendor/osm_vendor_al.h | 14 +- .../user/include/vendor/osm_vendor_api.h | 27 +- .../user/include/vendor/osm_vendor_sa_api.h | 218 +- .../user/include/vendor/osm_vendor_select.h | 6 +- trunk/ulp/opensm/user/libopensm/SOURCES | 1 + trunk/ulp/opensm/user/libopensm/osm_helper.c | 661 +- trunk/ulp/opensm/user/libopensm/osm_log.c | 234 +- .../ulp/opensm/user/libopensm/osm_mad_pool.c | 14 +- trunk/ulp/opensm/user/libvendor/SOURCES | 1 + .../ulp/opensm/user/libvendor/osm_vendor_al.c | 8 +- .../opensm/user/libvendor/osm_vendor_mlx_sa.c | 90 +- trunk/ulp/opensm/user/opensm/SOURCES | 11 + trunk/ulp/opensm/user/opensm/cl_dispatcher.c | 34 +- trunk/ulp/opensm/user/opensm/cl_event_wheel.c | 19 +- trunk/ulp/opensm/user/opensm/main.c | 148 +- trunk/ulp/opensm/user/opensm/osm.h | 68 + trunk/ulp/opensm/user/opensm/osm.rc | 2 + trunk/ulp/opensm/user/opensm/osm_console.c | 6 +- trunk/ulp/opensm/user/opensm/osm_db_files.c | 68 +- trunk/ulp/opensm/user/opensm/osm_db_pack.c | 9 +- trunk/ulp/opensm/user/opensm/osm_drop_mgr.c | 170 +- trunk/ulp/opensm/user/opensm/osm_fwd_tbl.c | 7 +- trunk/ulp/opensm/user/opensm/osm_inform.c | 534 +- trunk/ulp/opensm/user/opensm/osm_lid_mgr.c | 249 +- .../ulp/opensm/user/opensm/osm_lin_fwd_rcv.c | 20 +- .../opensm/user/opensm/osm_lin_fwd_rcv_ctrl.c | 10 +- .../ulp/opensm/user/opensm/osm_lin_fwd_tbl.c | 15 +- trunk/ulp/opensm/user/opensm/osm_link_mgr.c | 173 +- trunk/ulp/opensm/user/opensm/osm_matrix.c | 11 +- .../opensm/user/opensm/osm_mcast_fwd_rcv.c | 21 +- .../user/opensm/osm_mcast_fwd_rcv_ctrl.c | 9 +- trunk/ulp/opensm/user/opensm/osm_mcast_mgr.c | 272 +- trunk/ulp/opensm/user/opensm/osm_mcast_tbl.c | 22 +- trunk/ulp/opensm/user/opensm/osm_mcm_info.c | 11 +- trunk/ulp/opensm/user/opensm/osm_mcm_port.c | 14 +- trunk/ulp/opensm/user/opensm/osm_mtree.c | 24 +- trunk/ulp/opensm/user/opensm/osm_multicast.c | 51 +- trunk/ulp/opensm/user/opensm/osm_node.c | 20 +- .../opensm/user/opensm/osm_node_desc_rcv.c | 18 +- .../user/opensm/osm_node_desc_rcv_ctrl.c | 14 +- .../opensm/user/opensm/osm_node_info_rcv.c | 212 +- .../user/opensm/osm_node_info_rcv_ctrl.c | 14 +- trunk/ulp/opensm/user/opensm/osm_opensm.c | 127 +- trunk/ulp/opensm/user/opensm/osm_pkey.c | 293 +- trunk/ulp/opensm/user/opensm/osm_pkey_mgr.c | 694 +- trunk/ulp/opensm/user/opensm/osm_pkey_rcv.c | 43 +- .../opensm/user/opensm/osm_pkey_rcv_ctrl.c | 15 +- trunk/ulp/opensm/user/opensm/osm_port.c | 121 +- .../opensm/user/opensm/osm_port_info_rcv.c | 146 +- .../user/opensm/osm_port_info_rcv_ctrl.c | 14 +- trunk/ulp/opensm/user/opensm/osm_prtn.c | 399 + .../ulp/opensm/user/opensm/osm_prtn_config.c | 447 + trunk/ulp/opensm/user/opensm/osm_qos.c | 451 + trunk/ulp/opensm/user/opensm/osm_remote_sm.c | 20 +- trunk/ulp/opensm/user/opensm/osm_req.c | 28 +- trunk/ulp/opensm/user/opensm/osm_req_ctrl.c | 14 +- trunk/ulp/opensm/user/opensm/osm_resp.c | 24 +- trunk/ulp/opensm/user/opensm/osm_router.c | 124 + trunk/ulp/opensm/user/opensm/osm_sa.c | 792 +- .../user/opensm/osm_sa_class_port_info.c | 66 +- .../user/opensm/osm_sa_class_port_info_ctrl.c | 14 +- .../user/opensm/osm_sa_guidinfo_record.c | 194 +- .../user/opensm/osm_sa_guidinfo_record_ctrl.c | 14 +- .../opensm/user/opensm/osm_sa_informinfo.c | 655 +- .../user/opensm/osm_sa_informinfo_ctrl.c | 44 +- .../opensm/user/opensm/osm_sa_lft_record.c | 136 +- .../user/opensm/osm_sa_lft_record_ctrl.c | 13 +- .../opensm/user/opensm/osm_sa_link_record.c | 223 +- .../user/opensm/osm_sa_link_record_ctrl.c | 12 +- .../ulp/opensm/user/opensm/osm_sa_mad_ctrl.c | 57 +- .../user/opensm/osm_sa_mcmember_record.c | 772 +- .../user/opensm/osm_sa_mcmember_record_ctrl.c | 10 +- .../opensm/user/opensm/osm_sa_mft_record.c | 547 ++ .../user/opensm/osm_sa_mft_record_ctrl.c | 123 + .../user/opensm/osm_sa_multipath_record.c | 1652 ++++ .../opensm/osm_sa_multipath_record_ctrl.c | 128 + .../opensm/user/opensm/osm_sa_node_record.c | 171 +- .../user/opensm/osm_sa_node_record_ctrl.c | 10 +- .../opensm/user/opensm/osm_sa_path_record.c | 773 +- .../user/opensm/osm_sa_path_record_ctrl.c | 14 +- .../opensm/user/opensm/osm_sa_pkey_record.c | 230 +- .../user/opensm/osm_sa_pkey_record_ctrl.c | 13 +- .../user/opensm/osm_sa_portinfo_record.c | 237 +- .../user/opensm/osm_sa_portinfo_record_ctrl.c | 14 +- .../ulp/opensm/user/opensm/osm_sa_response.c | 32 +- .../user/opensm/osm_sa_service_record.c | 251 +- .../user/opensm/osm_sa_service_record_ctrl.c | 10 +- .../opensm/user/opensm/osm_sa_slvl_record.c | 263 +- .../user/opensm/osm_sa_slvl_record_ctrl.c | 14 +- .../opensm/user/opensm/osm_sa_sminfo_record.c | 490 +- .../user/opensm/osm_sa_sminfo_record_ctrl.c | 14 +- .../user/opensm/osm_sa_sw_info_record.c | 535 ++ .../user/opensm/osm_sa_sw_info_record_ctrl.c | 123 + .../opensm/user/opensm/osm_sa_vlarb_record.c | 258 +- .../user/opensm/osm_sa_vlarb_record_ctrl.c | 14 +- trunk/ulp/opensm/user/opensm/osm_service.c | 19 +- .../ulp/opensm/user/opensm/osm_slvl_map_rcv.c | 35 +- .../user/opensm/osm_slvl_map_rcv_ctrl.c | 14 +- trunk/ulp/opensm/user/opensm/osm_sm.c | 56 +- .../ulp/opensm/user/opensm/osm_sm_mad_ctrl.c | 102 +- .../ulp/opensm/user/opensm/osm_sm_state_mgr.c | 55 +- trunk/ulp/opensm/user/opensm/osm_sminfo_rcv.c | 130 +- .../opensm/user/opensm/osm_sminfo_rcv_ctrl.c | 10 +- trunk/ulp/opensm/user/opensm/osm_state_mgr.c | 385 +- .../opensm/user/opensm/osm_state_mgr_ctrl.c | 14 +- trunk/ulp/opensm/user/opensm/osm_subnet.c | 439 +- .../ulp/opensm/user/opensm/osm_sw_info_rcv.c | 88 +- .../opensm/user/opensm/osm_sw_info_rcv_ctrl.c | 13 +- .../opensm/user/opensm/osm_sweep_fail_ctrl.c | 10 +- trunk/ulp/opensm/user/opensm/osm_switch.c | 88 +- trunk/ulp/opensm/user/opensm/osm_trap_rcv.c | 157 +- .../opensm/user/opensm/osm_trap_rcv_ctrl.c | 10 +- trunk/ulp/opensm/user/opensm/osm_ucast_file.c | 413 + .../ulp/opensm/user/opensm/osm_ucast_ftree.c | 3141 +++++++ trunk/ulp/opensm/user/opensm/osm_ucast_mgr.c | 779 +- trunk/ulp/opensm/user/opensm/osm_ucast_updn.c | 1002 ++- trunk/ulp/opensm/user/opensm/osm_vl15intf.c | 14 +- trunk/ulp/opensm/user/opensm/osm_vl_arb_rcv.c | 37 +- .../opensm/user/opensm/osm_vl_arb_rcv_ctrl.c | 14 +- trunk/ulp/opensm/user/opensm/st.c | 17 +- trunk/ulp/opensm/user/osmtest/SOURCES | 1 + trunk/ulp/opensm/user/osmtest/include/error.h | 6 +- .../opensm/user/osmtest/include/osmt_inform.h | 6 +- .../osmtest/include/osmt_mtl_regular_qp.h | 6 +- .../ulp/opensm/user/osmtest/include/osmtest.h | 26 +- .../user/osmtest/include/osmtest_base.h | 6 +- .../user/osmtest/include/osmtest_subnet.h | 51 +- trunk/ulp/opensm/user/osmtest/osmt_inform.c | 148 +- .../opensm/user/osmtest/osmt_mtl_regular_qp.c | 6 +- .../ulp/opensm/user/osmtest/osmt_multicast.c | 1247 +-- trunk/ulp/opensm/user/osmtest/osmt_service.c | 246 +- .../opensm/user/osmtest/osmt_slvl_vl_arb.c | 389 +- trunk/ulp/opensm/user/osmtest/osmtest.c | 7546 ++++++++++------- 261 files changed, 29459 insertions(+), 11548 deletions(-) create mode 100644 trunk/ulp/opensm/user/README.opensm-build create mode 100644 trunk/ulp/opensm/user/TODO create mode 100644 trunk/ulp/opensm/user/config.h create mode 100644 trunk/ulp/opensm/user/doc/OpenSM_PKey_Mgr.txt create mode 100644 trunk/ulp/opensm/user/doc/OpenSM_RN_0_3_1.pdf create mode 100644 trunk/ulp/opensm/user/doc/OpenSM_UM_0_3.pdf create mode 100644 trunk/ulp/opensm/user/doc/current-routing.txt create mode 100644 trunk/ulp/opensm/user/doc/modular-routing.txt create mode 100644 trunk/ulp/opensm/user/doc/opensm_release_notes_openib-2.0.5.txt create mode 100644 trunk/ulp/opensm/user/doc/qos-config.txt create mode 100644 trunk/ulp/opensm/user/include/complib/cl_dispatcher.h create mode 100644 trunk/ulp/opensm/user/include/complib/cl_event_wheel.h create mode 100644 trunk/ulp/opensm/user/include/opensm/osm_router.h create mode 100644 trunk/ulp/opensm/user/include/opensm/osm_sa_multipath_record.h create mode 100644 trunk/ulp/opensm/user/include/opensm/osm_sa_multipath_record_ctrl.h create mode 100644 trunk/ulp/opensm/user/include/opensm/osm_sa_sw_info_record.h create mode 100644 trunk/ulp/opensm/user/include/opensm/osm_sa_sw_info_record_ctrl.h create mode 100644 trunk/ulp/opensm/user/include/unistd.h create mode 100644 trunk/ulp/opensm/user/opensm/osm.h create mode 100644 trunk/ulp/opensm/user/opensm/osm.rc create mode 100644 trunk/ulp/opensm/user/opensm/osm_prtn.c create mode 100644 trunk/ulp/opensm/user/opensm/osm_prtn_config.c create mode 100644 trunk/ulp/opensm/user/opensm/osm_qos.c create mode 100644 trunk/ulp/opensm/user/opensm/osm_router.c create mode 100644 trunk/ulp/opensm/user/opensm/osm_sa_mft_record.c create mode 100644 trunk/ulp/opensm/user/opensm/osm_sa_mft_record_ctrl.c create mode 100644 trunk/ulp/opensm/user/opensm/osm_sa_multipath_record.c create mode 100644 trunk/ulp/opensm/user/opensm/osm_sa_multipath_record_ctrl.c create mode 100644 trunk/ulp/opensm/user/opensm/osm_sa_sw_info_record.c create mode 100644 trunk/ulp/opensm/user/opensm/osm_sa_sw_info_record_ctrl.c create mode 100644 trunk/ulp/opensm/user/opensm/osm_ucast_file.c create mode 100644 trunk/ulp/opensm/user/opensm/osm_ucast_ftree.c diff --git a/trunk/ulp/opensm/user/README.opensm-build b/trunk/ulp/opensm/user/README.opensm-build new file mode 100644 index 00000000..cccd07a1 --- /dev/null +++ b/trunk/ulp/opensm/user/README.opensm-build @@ -0,0 +1,24 @@ +##### Begin svn/gen1/trunk/src/userspace/osm/README.opensm-build + +# How to Build the OpenSM Subnet Manager +# ---------------------------------------- + +# This file is arranged as a shell script so you can paste or execute +# it. This is for building from the SVN source at openib.org. + +# 1. Complete steps outlined in README.kernel-build. +# 2. Complete steps outlined in README.user-build. + +# set TOP to wherever you've checked out the openib repository. +TOP=/usr/src/openib + +export TSHOME=$TOP/src/linux-kernel/infiniband/include/ +export MTHOME=$TOP/src/userspace/hw/mellanox-hca/mthome/ + +# Add util dir to path for makedepend +export PATH=$TOP/src/userspace/osm/util:$PATH + +cd $TOP/src/userspace/osm +make VENDOR=ts + +##### end \ No newline at end of file diff --git a/trunk/ulp/opensm/user/TODO b/trunk/ulp/opensm/user/TODO new file mode 100644 index 00000000..684ef454 --- /dev/null +++ b/trunk/ulp/opensm/user/TODO @@ -0,0 +1,16 @@ +Support new HOQ value for the ports feeding HCA ports + +Support Static Lid assignment with a flag for specifying a file with guid to lid. + +Support PKey comp in Path Record +Support SL comp in Path Record + +Support VL traversal in Path Record - compute the SL accordingly + Make it a runtime option, So we do not pay the price if no SL are used. + +Support a fast Path Record mode - if the fabric is totally uniform in rate and + MTU. No need to traverse the path at all... + +Improve the MinHop routing algorithm such that it only calc the min hops +for switches, then + diff --git a/trunk/ulp/opensm/user/config.h b/trunk/ulp/opensm/user/config.h new file mode 100644 index 00000000..5d7c42de --- /dev/null +++ b/trunk/ulp/opensm/user/config.h @@ -0,0 +1,71 @@ +/* + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. + * + * This software is available to you under the OpenIB.org BSD license + * below: + * + * Redistribution and use in source and binary forms, with or + * without modification, are permitted provided that the following + * conditions are met: + * + * - Redistributions of source code must retain the above + * copyright notice, this list of conditions and the following + * disclaimer. + * + * - Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials + * provided with the distribution. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS + * BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN + * ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN + * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + * + * $Id$ + */ + +/* + * Abstract: + * Windows-specific definitions + * + * Environment: + * Windows + * + * $Revision: $ + */ + +#ifndef _CONFIG_h_ +#define _CONFIG_h_ + +#include +#include +#include + +#define chmod(a,b) _chmod(a,b) +#define S_IRUSR _S_IREAD +#define S_IWUSR _S_IWRITE + +#define snprintf _snprintf +#define fileno _fileno + +#define stat _stat +#define fstat(a,b) fstat_alias((a),(b)) + +inline int +fstat_alias(int filedes, struct _stat *buf) +{ + return _fstat(filedes, buf); +} + +#endif /*_CONFIG_h_ */ + + + + diff --git a/trunk/ulp/opensm/user/doc/OpenSM_PKey_Mgr.txt b/trunk/ulp/opensm/user/doc/OpenSM_PKey_Mgr.txt new file mode 100644 index 00000000..df4031cd --- /dev/null +++ b/trunk/ulp/opensm/user/doc/OpenSM_PKey_Mgr.txt @@ -0,0 +1,79 @@ +OpenSM Partition Management +--------------------------- + +Roadmap: +Phase 1 - provide partition management at the EndPort (HCA, Router and Switch + Port 0) level with no routing affects. +Phase 2 - routing engine should take partitions into account. + +Phase 1 functionality: + +Supported Policy: + +1. EndPort partition groups are to be defined by listing the + PortGUIDs as full and limited members. + +2. Each partition group might be assigned an explicit P_Key (only the 15 + LSB bits are valid) or the SM should assign it randomly. + +3. A flag should control the generation of IPoIB broadcast group for + that partition. Extra optional MGIDs can be provided to be setup (on + top of the IPoIB broadcast group). + +4. A global flag "Disconnect Unconfigured EndPorts": If TRUE prevents + EndPorts that are not explicitly defined as part of any partition + (thus "unconfigured") to communicate with any other EndPort. Otherwise, it + will let these EndPorts send packets to all other EndPorts. + +Functionality: + +1. The policy should be updated: + - during SM bringup + - after kill -HUP + - through SNMP (once it is supported) + +2. Partition tables will be updated on full sweep (new port/trap etc). + As a first step, the policy feasibility should be + verified. Feasibility could be limited by the EndPorts supports for + number of partitions, etc. Unrealizable policy should be reported + and extra rules ignored after providing error messages. + +3. Each EndPort will be assigned P_Keys as follows: + + a. Default partition group limited membership as defined by rule #4 below. + (only the SM port will get 0xffff). + + b. P_Keys for all partition groups it is part of as defined in + the policy. + + c. P_Key update will preserve index for the existing P_Keys on the + port. If port has limited resources that will require reuse of, + on index a message will be provided and some of the settings will be + ommitted. P_Key indexes will not change under any circumstances. + +4. Each Switch Leaf Port (a switch port that is connected to an + EndPort) should be configured according to the same rules that + apply to the EndPort connected to that switch port. + This actually enables unauthorized port isolation (with future + usage of M_Key and ProtectBits). + +5. Policy entries matching a non EndPort will be flagged as + erroneous in the log file and ignored. + +6. At the end of the P_Key setting phase, a check for successful + setting should be made. + Errors should be clearly logged and cause a new sweep. + +7. Each partition that is marked to support IPoIB should define a + broadcast MGRP. If the partition does not support IPoIB, it should + define a dummy MGRP with parameters blocking IPoIB drivers from + registering to it. + +Phase 2 functionality: + +The partition policy should be considered during the routing such that +links are associated with particular partition or a set of +partitions. Policy should be enhanced to provide hints for how to do +that (correlating to QoS too). The exact algorithm is TBD. + + diff --git a/trunk/ulp/opensm/user/doc/OpenSM_RN_0_3_1.pdf b/trunk/ulp/opensm/user/doc/OpenSM_RN_0_3_1.pdf new file mode 100644 index 0000000000000000000000000000000000000000..4eaacf87aabeba3261a395dfc2be991e5a4355f5 GIT binary patch literal 83938 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 YAhD&U#iyk4(hU@i+A372-#pg#f8MppG5`Po literal 0 HcmV?d00001 diff --git a/trunk/ulp/opensm/user/doc/OpenSM_UM_0_3.pdf b/trunk/ulp/opensm/user/doc/OpenSM_UM_0_3.pdf new file mode 100644 index 0000000000000000000000000000000000000000..99511713d56b7e92b2381f2868b675daa12d6645 GIT binary patch literal 223001 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

jtcLU)E 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 z zKsd3UR}H8$UPPsd11Y-k!DAI<_Z#v}5@UU6#(A+rC_*Qf@46#Cs`yUK zJ=JQQYPf{gmM!Z}rDv-y_$=qB=!|c&;eZSSy!0=QU-*b*;IQ6&&zPyo5so|u?2E>!#xiz0Tsct;b;JXU4eISy&pL)c*;Fgmu znk=~7p;o%>w{bBpNfMLEL8rg!$4GI~ypav_h)sTd(&zep?<4-P{VfEJ5JrL?p6+A- z!N7vVG1eF>>P$_iE435qSqxKuBjPo~2F~SHL>te~UC4UfQWX~Dr%{XXfxo-la7C6N z^70*_DHK$!2zao6=RSXP6Bcu}nS;?;h<*r*BtaA<0Orh_v77d`H*N;labQbQ!9-16 zN%eR%4#(e;a|Kdl(=u*4d=ONM-}P`2BTi-%zpJ2D-D00}s(pcTpi0mOCclsgZ)$WR z6v05VieU@UmLAh z<%7d=7LF+bp{YkhGBi^!bOld+%F*-gKE1s(n_asV1OFPSD0oO-x3!m&ODN>CaphRz z@R!n*aSaS)sYSXMFkAm1;*7Y8I0z771L!w#dq2ucp9sB64`Vx4JEkr*Rke(j?qr?G zWH#2-sR#^|PlIgsY<`NI6=~ql5F7M5+h>2^VRZ47ybxqr7#0>*#?Qp-fKkK@0)5&6 zH;H?Tee)WZf!1ceF587_HAKcwc(EjN@_-N{&s5cXcL{Tiu#$u4LX@crM%9ZBn)bT( zvGFhx&@XW+ruKCHyB+2S8J>nDq@n#fFRppyB5$rFK&4=u`?diDAIUPnWqME>4T6?o zybu`xsa>hJIW)--P%Hk$mNGogXzy8A9F6-K8R`xRW%6eOL)q=WM3))nV||P#gqv=T zdgrtjjj6wxu39YU#t6$;%f_KCKvsGDsbYKWDm?X;>mhKokO@ZQ%+F20$_Gij#$(^$gJy0B28sH$CJ7Eik`#f04ZQO73TKo5XSLoQ$9DA5}0Gicw(2kaw_Z1 z_+#|dbo3TFg|KNrB={2}j%AVZijuv!2V_`qE`sVg*$`Z9-r z=fY^0i_5Xzu>fX-D@cB&)Hw%o?m*-Kl*@@32PXXyz6G8UkAX<~A#+%cWWO0|h^Pv` z3XLtUKv9PMFn`BS9`paTSn%DW1ASvp=fXj5Z7G_Ef)wHpe~Y;#bo)_}aL0LoTLg2e zy`XGkDQxG`wZKD9@5w4IU~AHWCVd>5D#34%M#7`1kK7IuH>Y z<(XS{541))5E2z%f>4QBPq=i$S4f*_-K74~gImV=6Bc+l`2D zXr17go1$;&LBlhInGhG=j=7HHpC55EuxtyB#`xe7+Ix2QWEM&;+;2rfQz|#4dk?v; zTj{;Xw$E$*yKs3V3lsK{q1W|RBYRPh6RdRH;ZO@~O!+j@irkZUDy8!_CA(6^komS; z>h1J7(l-3IlQGTGfSM|kVc7s3YU>inM?WOP=QZom)=8EaA12k0s~z@Si!>zz!iDRAgs~$TNgh7|=f3&St8C>)9qGr)bVD>1b!gXlE2c{z^YlE`5$sNM;0> zK(_~=h=+($Lsl9FiH_S&_=tdE{~amtsg^>euw}xmULZG-_!iC<+uh5ut_O}HF7{-F zsC&{^5dMmwSJEX~-(c0A1Lt(bnW62&IT7NW*SVNuQufj|1~xK4-)FVs$%tjBSBE8T z4~xUV$Ow24p)FZ2kKygH5Az1%Oo@IF59tSk42Oi{EvJo@L~<@mnBg5~Zf)qwWGs4P zE=1H6|5Byp;u{p+t=l&0ezf0z#KM?O_D6e)bt}lGogCW04(X79SQC!Xg#dN$w5Nr3 z%tW&Ls~dh{%-8ae#C#S@>tSpXkXHA$Y<*zq!yheLx zZoNi;Ol;bd73UsGVtKX-fKX~x1H1GJNEs96FuOxqVn&F`!&)suF~}&OF>yw-9YhKy zG?EY8_oMl8n%u0paNZ~bU_hvKTe99YuI+7UiZaJgGi5jQx7;4N4$OtL_o>Jzs%RZj zo5jEy&^dipzCN0%2x-+8Kq4D`}Zf`@HyzU01{|Mx&_eRU{6TYJK<2{)ElI{{mucT%MI6rzLxx7kMzeskwWAQCyD-{mAQPjpTFbr@7DI!_p- z3glD#HG@wf{E)F-d%&7U)US8>;D{QC@$=#LB~S5tzB4@|Yz|AKkIPd$qI zdx`h&Eeg=m4i6O5S7J)WvL55&<8cnv2xat1ZV9fiuxBXsSwvX!f|nd`p6@em1$`G7 z)(?^g*zei(o9U05ga${6%qyX;g96qQ^YPBWK*M^UYps^G#@W=H05}WBql*f<5H@RS4mpEvj4~^%q4VGlmmd z49A+a44vIQYWe`bno#gQBd z@FLhHW-KUvy!&AMyo{ImjB-V-uk@H{TH-+1< zjx^0oC}H_b`~ZKr-y`~Ae#fB|*Fij<6JY^Mi{z808loTedi!Te5Vci|+x6P*>=g?h znF)yb`-qiL@8axyK7r04JYf0}4SDy!8nEBhkj?l_47o32BjpovXCz(h(Ja9WW6<>N`cdJs2qL?1eKf#289Lmh?%0A2m&2Y~C?+58Vg@qcO-`@ayy|CN9I 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 SPvJ$6&;Icr|M|~ 0, more checks are added: Within each group of LIDs assigned to +same target port, + a. use only ports which have same MinHop + b. first prefer the ones that go to different systemImageGuid (then +the previous LID of the same LMC group) + c. if none - prefer those which go through another NodeGuid + d. fall back to the number of paths method (if all go to same node). + + +Effect of Topology Changes + +OpenSM will preserve existing routing in any case where there is no change in +the fabric switches unless the -r (--reassign_lids) option is specified. + +-r +--reassign_lids + This option causes OpenSM to reassign LIDs to all + end nodes. Specifying -r on a running subnet + may disrupt subnet traffic. + Without -r, OpenSM attempts to preserve existing + LID assignments resolving multiple use of same LID. + +If a link is added or removed, OpenSM does not recalculate +the routes that do not have to change. A route has to change +if the port is no longer UP or no longer the MinHop. When routing changes +are performed, the same algorithm for balancing the routes is invoked. + +In the case of using the file based routing, any topology changes are +currently ignored The 'file' routing engine just loads the LFTs from the file +specified, with no reaction to real topology. Obviously, this will not be able +to recheck LIDs (by GUID) for disconnected nodes, and LFTs for non-existent +switches will be skipped. Multicast is not affected by 'file' routing engine +(this uses min hop tables). + + +Min Hop Algorithm +----------------- + +The Min Hop algorithm is invoked when neither UPDN or the file method are +specified. + +The Min Hop algorithm is divided into two stages: computation of +min-hop tables on every switch and LFT output port assignment. Link +subscription is also equalized with the ability to override based on +port GUID. The latter is supplied by: + +-i +-ignore-guids + This option provides the means to define a set of ports + (by guids) that will be ignored by the link load + equalization algorithm. + +LMC awareness routes based on (remote) system or switch basis. + + +UPDN Routing Algorithm +---------------------- + +Purpose of UPDN Algorithm + +The UPDN algorithm is designed to prevent deadlocks from occurring in loops +of the subnet. A loop-deadlock is a situation in which it is no longer +possible to send data between any two hosts connected through the loop. As +such, the UPDN routing algorithm should be used if the subnet is not a pure +Fat Tree, and one of its loops may experience a deadlock (due, for example, +to high pressure). + +The UPDN algorithm is based on the following main stages: + +1. Auto-detect root nodes - based on the CA hop length from any switch in +the subnet, a statistical histogram is built for each switch (hop num vs +number of occurrences). If the histogram reflects a specific column (higher +than others) for a certain node, then it is marked as a root node. Since +the algorithm is statistical, it may not find any root nodes. The list of +the root nodes found by this auto-detect stage is used by the ranking +process stage. + + Note 1: The user can override the node list manually. + Note 2: If this stage cannot find any root nodes, and the user did not + specify a guid list file, OpenSM defaults back to the Min Hop + routing algorithm. + +2. Ranking process - All root switch nodes (found in stage 1) are assigned +a rank of 0. Using the BFS algorithm, the rest of the switch nodes in the +subnet are ranked incrementally. This ranking aids in the process of enforcing +rules that ensure loop-free paths. + +3. Min Hop Table setting - after ranking is done, a BFS algorithm is run from +each (CA or switch) node in the subnet. During the BFS process, the FDB table +of each switch node traversed by BFS is updated, in reference to the starting +node, based on the ranking rules and guid values. + +At the end of the process, the updated FDB tables ensure loop-free paths +through the subnet. + + +UPDN Algorithm Usage + +Activation through OpenSM + +Use '-R updn' option (instead of old '-u') to activate the UPDN algorithm. +Use `-a ' for adding an UPDN guid file that contains the +root nodes for ranking. +If the `-a' option is not used, OpenSM uses its auto-detect root nodes +algorithm. + +Notes on the guid list file: +1. A valid guid file specifies one guid in each line. Lines with an invalid +format will be discarded. +2. The user should specify the root switch guids. However, it is also +possible to specify CA guids; OpenSM will use the guid of the switch (if +it exists) that connects the CA to the subnet as a root node. + + +To learn more about deadlock-free routing, see the article +"Deadlock Free Message Routing in Multiprocessor Interconnection Networks" +by William J Dally and Charles L Seitz (1985). + + +Fat-tree Routing Algorithm +-------------------------- + +Purpose: + +The fat-tree algorithm optimizes routing for "shift" communication pattern. +It should be chosen if a subnet is a symmetrical fat-tree of various types. +It supports not just K-ary-N-Trees, by handling for non-constant K, +cases where not all leafs (CAs) are present, any CBB ratio. +As in UPDN, fat-tree also prevents credit-loop-deadlocks. +Fat-tree algorithm supports topologies that comply with the following rules: + - Tree rank should be between two and eight (inclusively) + - Switches of the same rank should have the same number + of UP-going port groups*, unless they are root switches, + in which case the shouldn't have UP-going ports at all. + - Switches of the same rank should have the same number + of DOWN-going port groups, unless they are leaf switches. + - Switches of the same rank should have the same number + of ports in each UP-going port group. + - Switches of the same rank should have the same number + of ports in each DOWN-going port group. +*ports that are connected to the same remote switch are referenced as +'port group'. + +Note that although fat-tree algorithm supports trees with non-integer CBB +ratio, the routing will not be as balanced as in case of integer CBB ratio. +In addition to this, although the algorithm allows leaf switches to have any +number of CAs, the closer the tree is to be fully populated, the more effective +the "shift" communication pattern will be. + +The algorithm also dumps CA ordering file (osm-ftree-ca-order.dump) in the +same directory where the OpenSM log resides. This ordering file provides the +CA order that may be used to create efficient communication pattern, that +will match the routing tables. + + +Usage: + +Activation through OpenSM + +Use '-R ftree' option to activate the fat-tree algorithm. + +Note: LMC > 0 is not supported by fat-tree routing. If this is +specified, the default routing algorithm is invoked instead. + diff --git a/trunk/ulp/opensm/user/doc/modular-routing.txt b/trunk/ulp/opensm/user/doc/modular-routing.txt new file mode 100644 index 00000000..0a593467 --- /dev/null +++ b/trunk/ulp/opensm/user/doc/modular-routing.txt @@ -0,0 +1,78 @@ +Modular Routine Engine + +Modular routing engine structure has been added to allow +for ease of "plugging" new routing modules. + +Currently, only unicast callbacks are supported. Multicast +can be added later. + +One of existing routing modules is up-down "updn", which may +be activated with '-R updn' option (instead of old '-u'). + +General usage is: +$ opensm -R 'module-name' + +There is also a trivial routing module which is able +to load LFT tables from a dump file. + +Main features: + +- this will load switch LFTs and/or LID matrices (min hops tables) +- this will load switch LFTs according to the path entries introduced in + the dump file +- no additional checks will be performed (such as "is port connected", etc.) +- in case when fabric LIDs were changed this will try to reconstruct LFTs + correctly if endport GUIDs are represented in the dump file (in order + to disable this GUIDs may be removed from the dump file or zeroed) + +The dump file format is compatible with output of 'ibroute' util and for +whole fabric may be generated with script like this: + + for sw_lid in `ibswitches | awk '{print $NF}'` ; do + ibroute $sw_lid + done > /path/to/dump_file + +, or using DR paths: + + for sw_dr in `ibnetdiscover -v \ + | sed -ne '/^DR path .* switch /s/^DR path \[\(.*\)\].*$/\1/p' \ + | sed -e 's/\]\[/,/g' \ + | sort -u` ; do + ibroute -D ${sw_dr} + done > /path/to/dump_file + +This script is dump_lfts.sh + +In order to activate new module use: + + opensm -R file -U /path/to/dump_file + +If the dump_file is not found or is in error, the default routing +algorithm is utilized. + +The ability to dump switch lid matrices (aka min hops tables) to file and +later to load these is also supported. + +The usage is similar to unicast forwarding tables loading from dump +file (introduced by 'file' routing engine), but new lid matrix file +name should be specified by -M or --lid_matrix_file option. For example: + +  opensm -R file -M ./opensm-lid-matrix.dump + +The dump file is named 'opensm-lid-matrix.dump' and will be generated in +standard opensm dump directory (/var/log by default) when +OSM_LOG_ROUTING logging flag is set. + +When routing engine 'file' is activated, but dump file is not specified +or not cannot be open default lid matrix algorithm will be used. + +There is also a switch forwarding tables dumper which generates +a file compatible with dump_lfts.sh output. This file can be used +as input for forwarding tables loading by 'file' routing engine. +Both or one of options -U and -M can be specified together with '-R file'. + +NOTE: ibroute has been updated (for switch management ports) to support this. +Also, lmc was added to switch management ports. ibroute needs to be r7855 or +later from the trunk. + + diff --git a/trunk/ulp/opensm/user/doc/opensm_release_notes_openib-2.0.5.txt b/trunk/ulp/opensm/user/doc/opensm_release_notes_openib-2.0.5.txt new file mode 100644 index 00000000..a6555733 --- /dev/null +++ b/trunk/ulp/opensm/user/doc/opensm_release_notes_openib-2.0.5.txt @@ -0,0 +1,487 @@ + OpenSM Release Notes 2.0.5 + ============================ + +Version: OpenFabrics Enterprise Distribution (OFED) 1.1 +Repo: https://openib.org/svn/gen2/branches/1.1/src/userspace/management/osm +Version: 9535 (openib-2.0.5) +Date: October 2006 + +1 Overview +---------- +This document describes the contents of the OpenSM OFED 1.1 release. +OpenSM is an InfiniBand compliant Subnet Manager and Administration, +and runs on top of OpenIB. The OpenSM version for this release +is openib-2.0.5 + +This document includes the following sections: +1 This Overview section (describing new features and software + dependencies) +2 Known Issues And Limitations +3 Unsupported IB compliance statements +4 Major Bug Fixes +5 Main Verification Flows +6 Qualified software stacks and devices + +1.1 Major New Features + +* Partition manager: + The partition manager provides a means to setup multiple partitions + by providing a partition policy file. For details please read the + doc/partition-config.txt or the opensm man page. + +* Basic QoS Manager: + Provides a uniform configuration of the entire fabric with values defined + in the OpenSM options file. The options support different settings for + CAs, Switches, and Routers. Note that this is disabled by default and + using -Q enables QoS fabric setup. + +* Loading pre-routes from a file: + A new routing module enables loading pre-routes from a file. + To use this option you should use the command line options: + "-R file --U " or + "--routing_engine file --ucast_file " + For more information refer to the file doc/modular-routing.txt + or the opensm man page. + +* SA MultiPathRecord support: + The SA can now handle requests for multiple PathRecords in one query. + This includes methods SA GetMulti/GetMultiResp and dual sided RMPP. + +* PPC64 is now QAed and supported + +* Support LMC > 0 for Switch Enhanced Port 0: + Allows enhanced switch port 0 (ESP0) to have a non zero + LMC. Use the configured subnet wide LMC for this. Modifications were + necessary to the LID assignment and routing to support this. + Also, added an option to the configuration to use LMC configured for + subnet for enhanced switch port 0 or set it to 0 even if a non zero + LMC is configured for the subnet. The default is currently the + latter option. The new configuration option is: lmc_esp0 + +1.2 Minor New Features: + +* IPoIB broadcast group configuration: + It is now possible to control the IPoIB broadcast group parameters + (MTU, rate, SL) through the partitions configuration file. + +* Limiting OpenSM log file size: + By providing the command line option: "-L " or + "--log_limit " the user can limit the generated log + file size. When specified, the log file will be truncated upon reaching + this limit. + +* Favor 1K MTU for Tavor (MT23108) HCA + In cases where a PathRecord or MultiPathRecord is queried and the + requestor does not specify the MTU or does specify it in a way + that allows for MTU to be 1K and one of the path ends in a Tavor, + limit the MTU to 1K max. + +* Man pages: + Added opensm.8 and osmtest.8 + +* Leaf VL stall count control: + A new parameter (leaf_vl_stall_count) for controlling the number of + sequential packets dropped on a switch port driving a HCA/TCA/Router + that cause the port to enter the VLStalled state was added to the + options file. + +* SM Polling/Handover defaults changed + The default SMInfo polling retries was decreased from 18 to 4 + which reduces the default handover time from 3 min to 40 seconds. + +1.3 Library API Changes + +* cl_mem* APIs deprecated in complib: + These functions are now considered as deprecated and should be + replaced by direct calls to malloc, free, memset, etc. + +* osm_log_init_v2 API added in libopensm: + Supports providing the new option for log file truncation. + +1.4 Software Dependencies + +OpenSM depends on the installation of either OFED 1.1, OFED 1.0, +OpenIB gen2 (e.g. IBG2 distribution), OpenIB gen1 (e.g. IBGD +distribution), or Mellanox VAPI stacks. The qualified driver versions +are provided in Table 2, "Qualified IB Stacks". + +1.5 Supported Devices Firmware + +The main task of OpenSM is to initialize InfiniBand devices. The +qualified devices and their corresponding firmware versions +are listed in Table 3. + +2 Known Issues And Limitations +------------------------------ + +* No Service / Key associations: + There is no way to manage Service access by Keys. + +* No SM to SM SMDB synchronization: + Puts the burden of re-registering services, multicast groups, and + inform-info on the client application (or IB access layer core). + +* No "port down" event handling: + Changing the switch port through which OpenSM connects to the IB + fabric may cause incorrect operation. Please restart OpenSM whenever + such a connectivity change is made. + +* Changing connections during SM operation: + Under some conditions the SM can get confused by a change in + cabling (moving a cable from one switch port to the other) and + momentarily see this as having the same GUID appear connected + to two different IB ports. Under some conditions, when the SM fails to + get the corresponding change event it might mistakenly report this case + as a "duplicated GUID" case and abort. It is advisable to double-check + the syslog after each such change in connectivity and restart + OpenSM if it has exited. + +3 Unsupported IB Compliance Statements +-------------------------------------- +The following section lists all the IB compliance statements which +OpenSM does not support. Please refer to the IB specification for detailed +information regarding each compliance statement. + +* C14-22 (Authentication): + M_Key M_KeyProtectBits and M_KeyLeasePeriod shall be set in one + SubnSet method. As a work-around, an OpenSM option is provided for + defining the protect bits. + +* C14-67 (Authentication): + On SubnGet(SMInfo) and SubnSet(SMInfo) - if M_Key is not zero then + the SM shall generate a SubnGetResp if the M_Key matches, or + silently drop the packet if M_Key does not match. + +* C15-0.1.23.4 (Authentication): + InformInfoRecords shall always be provided with the QPN set to 0, + except for the case of a trusted request, in which case the actual + subscriber QPN shall be returned. + +* o13-17.1.2 (Event-FWD): + If no permission to forward, the subscription should be removed and + no further forwarding should occur. + +* C14-24.1.1.5 and C14-62.1.1.22 (Initialization): + GUIDInfo - SM should enable assigning Port GUIDInfo. + +* C14-44 (Initialization): + If the SM discovers that it is missing an M_Key to update CA/RT/SW, + it should notify the higher level. + +* C14-62.1.1.12 (Initialization): + PortInfo:M_Key - Set the M_Key to a node based random value. + +* C14-62.1.1.13 (Initialization): + PortInfo:P_KeyProtectBits - set according to an optional policy. + +* C14-62.1.1.24 (Initialization): + SwitchInfo:DefaultPort - should be configured for random FDB. + +* C14-62.1.1.32 (Initialization): + RandomForwardingTable should be configured. + +* o15-0.1.12 (Multicast): + If the JoinState is SendOnlyNonMember = 1 (only), then the endport + should join as sender only. + +* o15-0.1.8 (Multicast): + If a request for creating an MCG with fields that cannot be met, + return ERR_REQ_INVALID (currently ignores SL and FlowLabelTClass). + +* C15-0.1.8.6 (SA-Query): + Respond to SubnAdmGetTraceTable - this is an optional attribute. + +* C15-0.1.13 Services: + Reject ServiceRecord create, modify or delete if the given + ServiceP_Key does not match the one included in the ServiceGID port + and the port that sent the request. + +* C15-0.1.14 (Services): + Provide means to associate service name and ServiceKeys. + +4 Major Bug Fixes +----------------- + +The following is a list of bugs that were fixed. Note that other less critical +or visible bugs were also fixed. + +* "Broken" fabric (duplicated port GUIDs) handling improved + Replace assert with a real check to handle invalid physical port + in osm_node_info_rcv.c which could occur on a broken fabric + +* SA client synchronous request failed but status returned was IB_SUCCESS + even if there was no response. + There was a missing setting of the status in the synchronous case. + +* Memory leak fixes: + 1. In libvendor/osm_vendor_ibumad.c:osm_vendor_get_all_port_attr + 2. In libvendor/osm_vendor_ibumad_sa.c:__osmv_sa_mad_rcv_cb + 3. On receiving SMInfo SA request from a node that does not share a + partition, the response mad was allocated but never free'd + as it was never sent. + +* Set(InformInfo) OpenSM Deadlock: + When receiving a request with unknown LID + +* PathRecord to inconsistent multicast destination: + Fix the return error when multicast destination is not consistently + indicated. + +* Remove double calculation of reversible path + In osm_sa_path_record.c:__osm_pr_rcv_get_lid_pair_path a PathRecord + query used to double check if the path is reversible + +* Some PathRecord log messages use "net order": + Fix GUID net to host conversion in some osm_log messages + +* DR/LID routed SMPs direction bit handling: + osm_resp.c:osm_resp_make_resp_smp, set direction bit only if direct + routed class. This bug caused two issues: + 1. Get/Set responses always had direction bit set. + 2. Trap represses never had direction bit set. + The direction bit needs setting in direct routed responses and it + doesn't exist in LID routed responses. + osm_sm_mad_ctrl.c: did not detect the "direction bit" correctly. + +* OpenSM crash due to transaction lookup (interop with Cisco stack) + When a wire TID that maps to internal TID of zero (after applying + mask) was received the lookup of the transaction was successful. + The stale transaction pointed to "free'd" memory. + +* Better handling for Path/MultiPath requests for raw traffic + +* Wrong ProducerType provided in Notice Reports: + When formating an SM generated report, the ProducerType was using + CL_NTOH32 which can not be used to format a 24bit network order number. + +* OpenSM break on PPC64 + complib: Fixed memory corruption in cl_pool.c:cl_qcpool_init. This + affected big endian 64-bit architectures only. + +* Illegal Set(InformInfo) was wrongly successful in updating the SMDB + osm_sa_informinfo.c: In osm_infr_rcv_process_set_method, if sending + error, don't call osm_infr_rcv_process_set_method + +* RMPP queries of InformInfoRecord fail + ib_types.h: Pad ib_inform_info_record_t to be modulo 8 in size so + that attribute offset is calculated properly + +* Returning "invalid request" rather than "unsupported method/attribute" + In these cases, a noncompliant response was being provided. + +* Noncompliant response for SubnAdmGet(PortInfoRecord) with no match + osm_pir_rcv_process, now returns "SA no records error" for SubnAdmGet + with 0 records found + +* Noncompliant non base LID returned by some queries: + The following attributes used to return the request LID rather than + its base LID in responses: PKeyTableRecord, GUIDInfoRecord, + SLtoVLMappingTableRecord, VLArbitrationTableRecord, LinkRecord + +* Noncompliant SubnAdmGet and SubnAdmGetTable: + Mixing of error codes in case of no records or multiple records + fixed for the attributes: + LinearForwardingTableRecord, GUIDInfoRecord, + VLArbitrationTableRecord, LinkRecord, PathRecord + +* segfault in InformInfo flows + Under stress concurrent Set/Delete/Get flows. Fixed by adding + missing lock. + +* SA queries containing LID out if range did not return ERR_REQ_INVALID + +5 Main Verification Flows +------------------------- + +OpenSM verification is run using the following activities: +* osmtest - a stand-alone program +* ibmgtsim (IB management simulator) based - a set of flows that + simulate clusters, inject errors and verify OpenSM capability to + respond and bring up the network correctly. +* small cluster regression testing - where the SM is used on back to + back or single switch configurations. The regression includes + multiple OpenSM dedicated tests. +* cluster testing - when we run OpenSM to setup a large cluster, perform + hand-off, reboots and reconnects, verify routing correctness and SA + responsiveness at the ULP level (IPoIB and SDP). + +5.1 osmtest + +osmtest is an automated verification tool used for OpenSM +testing. Its verification flows are described by list below. + +* Inventory File: Obtain and verify all port info, node info, link and path + records parameters. + +* Service Record: + - Register new service + - Register another service (with a lease period) + - Register another service (with service p_key set to zero) + - Get all services by name + - Delete the first service + - Delete the third service + - Added bad flows of get/delete non valid service + - Add / Get same service with different data + - Add / Get / Delete by different component mask values (services + by Name & Key / Name & Data / Name & Id / Id only ) + +* Multicast Member Record: + - Query of existing Groups (IPoIB) + - BAD Join with insufficient comp mask (o15.0.1.3) + - Create given MGID=0 (o15.0.1.4) + - Create given MGID=0xFF12A01C,FE800000,00000000,12345678 (o15.0.1.4) + - Create BAD MGID=0xFA. (o15.0.1.6) + - Create BAD MGID=0xFF12A01B w/ link-local not set (o15.0.1.6) + - New MGID with invalid join state (o15.0.1.9) + - Retry of existing MGID - See JoinState update (o15.0.1.11) + - BAD RATE when connecting to existing MGID (o15.0.1.13) + - Partial JoinState delete request - removing FullMember (o15.0.1.14) + - Full Delete of a group (o15.0.1.14) + - Verify Delete by trying to Join deleted group (o15.0.1.14) + - BAD Delete of IPoIB membership (no prev join) (o15.0.1.15) + +* GUIDInfo Record: + - All GUIDInfoRecords in subnet are obtained + +* MultiPathRecord: + - Perform some compliant and noncompliant MultiPathRecord requests + - Validation is via status in responses and IB analyzer + +* PKeyTableRecord: + - Perform some compliant and noncompliant PKeyTableRecord queries + - Validation is via status in responses and IB analyzer + +* LinearForwardingTableRecord: + - Perform some compliant and noncompliant LinearForwardingTableRecord queries + - Validation is via status in responses and IB analyzer + +* Event Forwarding: Register for trap forwarding using reports + - Send a trap and wait for report + - Unregister non-existing + +* Trap 64/65 Flow: Register to Trap 64-65, create traps (by + disconnecting/connecting ports) and wait for report, then unregister. + +* Stress Test: send PortInfoRecord queries, both single and RMPP and + check for the rate of responses as well as their validity. + + +5.2 IB Management Simulator OpenSM Test Flows: + +The simulator provides ability to simulate the SM handling of virtual +topologies that are not limited to actual lab equipment availability. +OpenSM was simulated to bring up clusters of up to 10,000 nodes. Daily +regressions use smaller (16 and 128 nodes clusters). + +The following test flows are run on the IB management simulator: + +* Stability: + Up to 12 links from the fabric are randomly selected to drop packets + at drop rates up to 90%. The SM is required to succeed in bringing the + fabric up. The resulting routing is verified to be correct as well. + +* LID Manager: + Using LMC = 2 the fabric is initialized with LIDs. Faults such as + zero LID, Duplicated LID, non-aligned (to LMC) LIDs are + randomly assigned to various nodes and other errors are randomly + output to the guid2lid cache file. The SM sweep is run 5 times and + after each iteration a complete verification is made to ensure that all + LIDs that could possibly be maintained are kept, as well as that all nodes + were assigned a legal LID range. + +* Multicast Routing: + Nodes randomly join the 0xc000 group and eventually the + resulting routing is verified for completeness and adherence to + Up/Down routing rules. + +* osmtest: + The complete osmtest flow as described in the previous table is run on + the simulated fabrics. + +* Stress Test: + This flow merges fabric, LID and stability issues with continuous + PathRecord, ServiceRecord and Multicast Join/Leave activity to + stress the SM/SA during continuous sweeps. InformInfo Set/Delete/Get + were added to the test such both existing and non existing nodes + perform them in random order. + +5.3 OpenSM Regression + +Using a back-to-back or single switch connection, the following set of +tests is run nightly on the stacks described in table 2. The included +tests are: + +* Stress Testing: Flood the SA with queries from multiple channel + adapters to check the robustness of the entire stack up to the SA. + +* Dynamic Changes: Dynamic Topology changes, through randomly + dropping SMP packets, used to test OpenSM adaptation to an unstable + network & verify DB correctness. + +* Trap Injection: This flow injects traps to the SM and verifies that it + handles them gracefully. + +* SA Query Test: This test exhaustively checks the SA responses to all + possible single component mask. To do that the test examines the + entire set of records the SA can provide, classifies them by their + field values and then selects every field (using component mask and a + value) and verifies that the response matches the expected set of records. + A random selection using multiple component mask bits is also performed. + +5.4 Cluster testing: + +Cluster testing is usually run before a distribution release. It +involves real hardware setups of 16 to 32 nodes (or more if a beta site +is available). Each test is validated by running all-to-all ping through the IB +interface. The test procedure includes: + +* Cluster bringup + +* Hand-off between 2 or 3 SM's while performing: + - Node reboots + - Switch power cycles (disconnecting the SM's) + +* Unresponsive port detection and recovery + +* osmtest from multiple nodes + +* Trap injection and recovery + + +6 Qualification +---------------- + +Table 2 - Qualified IB Stacks +============================= + +Stack | Version +-----------------------------------------|-------------------------- +OFED | 1.1 +OFED | 1.0 +OpenIB Gen2 (IBG2 distribution) | 1.0 +OpenIB Gen1 (IBGD distribution) | 1.8.0 +VAPI (Mellanox InfiniBand HCA Driver) | 3.2 and later + +Table 3 - Qualified Devices and Corresponding Firmware +====================================================== + +Mellanox +Device | FW versions +--------|----------------------------------------------------------- +MT43132 | InfiniScale - fw-43132 5.2.0 (and later) +MT47396 | InfiniScale III - fw-47396 0.5.0 (and later) +MT23108 | InfiniHost - fw-23108 3.3.2 (and later) +MT25204 | InfiniHost III Lx - fw-25204 1.0.1i (and later) +MT25208 | InfiniHost III Ex (InfiniHost Mode) - fw-25208 4.6.2 (and later) +MT25208 | InfiniHost III Ex (MemFree Mode) - fw-25218 5.0.1 (and later) + +QLogic/PathScale +Device | Note +--------|----------------------------------------------------------- +iPath | QHT6040 (PathScale InfiniPath HT-460) +iPath | QHT6140 (PathScale InfiniPath HT-465) +iPath | QLE6140 (PathScale InfiniPath PE-880) + +Note: OpenSM does not run on an IBM Galaxy (eHCA) as it does not expose +QP0 and QP1. However, it does support it as a device on the subnet. + diff --git a/trunk/ulp/opensm/user/doc/qos-config.txt b/trunk/ulp/opensm/user/doc/qos-config.txt new file mode 100644 index 00000000..c90e6f7b --- /dev/null +++ b/trunk/ulp/opensm/user/doc/qos-config.txt @@ -0,0 +1,45 @@ +Trivial low level QoS configuration proposition +=============================================== + +Basically there is a set of QoS related low-level configuration parameters. +All these parameter names are prefixed by "qos_" string. Here is a full +list of these parameters: + + qos_max_vls - The maximum number of VLs that will be on the subnet + qos_high_limit - The limit of High Priority component of VL Arbitration + table (IBA 7.6.9) + qos_vlarb_low - High priority VL Arbitration table (IBA 7.6.9) template + qos_vlarb_high - Low priority VL Arbitration table (IBA 7.6.9) template + Both VL arbitration templates are pairs of VL and weight + qos_sl2vl - SL2VL Mapping table (IBA 7.6.6) template. It is a list + of VLs corresponding to SLs 0-15 (Note the VL15 used + here means drop this SL) + +Typical default values (hard-coded in OpenSM initialization) are: + + qos_max_vls=15 + qos_high_limit=0 + qos_vlarb_low=0:0,1:4,2:4,3:4,4:4,5:4,6:4,7:4,8:4,9:4,10:4,11:4,12:4,13:4,14:4 + qos_vlarb_high=0:4,1:0,2:0,3:0,4:0,5:0,6:0,7:0,8:0,9:0,10:0,11:0,12:0,13:0,14:0 + qos_sl2vl=0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,7 + +The syntax is compatible with rest of OpenSM configuration options and +values may be stored in OpenSM config file (cached options file). + +In addition to the above, we may define separate QoS configuration +parameters sets for various target types. As targets, we currently support +CAs, routers, switch external ports, and switch's enhanced port 0. The +names of such specialized parameters are prefixed by "qos__" +string. Here is a full list of the currently supported sets: + + qos_ca_ - QoS configuration parameters set for CAs. + qos_rtr_ - parameters set for routers. + qos_sw0_ - parameters set for switches' port 0. + qos_swe_ - parameters set for switches' external ports. + +Examples: + + qos_sw0_max_vls=2 + qos_ca_sl2vl=0,1,2,3,5,5,5,12,12,0, + qos_swe_high_limit=0 + diff --git a/trunk/ulp/opensm/user/include/complib/cl_dispatcher.h b/trunk/ulp/opensm/user/include/complib/cl_dispatcher.h new file mode 100644 index 00000000..123bd093 --- /dev/null +++ b/trunk/ulp/opensm/user/include/complib/cl_dispatcher.h @@ -0,0 +1,660 @@ +/* + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. + * + * This software is available to you under the OpenIB.org BSD license + * below: + * + * Redistribution and use in source and binary forms, with or + * without modification, are permitted provided that the following + * conditions are met: + * + * - Redistributions of source code must retain the above + * copyright notice, this list of conditions and the following + * disclaimer. + * + * - Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials + * provided with the distribution. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS + * BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN + * ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN + * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + * + * $Id$ + */ + + +/* + * Abstract: + * Declaration of dispatcher abstraction. + * + * Environment: + * All + * + * $Revision: 1.4 $ + */ + +#ifndef _CL_DISPATCHER_H_ +#define _CL_DISPATCHER_H_ + +#include +#include +#include +#include +#include +#include + +#ifdef __cplusplus +# define BEGIN_C_DECLS extern "C" { +# define END_C_DECLS } +#else /* !__cplusplus */ +# define BEGIN_C_DECLS +# define END_C_DECLS +#endif /* __cplusplus */ + +BEGIN_C_DECLS + +/****h* Component Library/Dispatcher +* NAME +* Dispatcher +* +* DESCRIPTION +* The Dispatcher provides a facility for message routing to +* asynchronous worker threads. +* +* The Dispatcher functions operate on a cl_dispatcher_t structure +* which should be treated as opaque and should be manipulated +* only through the provided functions. +* +* SEE ALSO +* Structures: +* cl_dispatcher_t +* +* Initialization/Destruction: +* cl_disp_construct, cl_disp_init, cl_disp_shutdown, cl_disp_destroy +* +* Manipulation: +* cl_disp_post, cl_disp_reset, cl_disp_wait_on +*********/ + +/****s* Component Library: Dispatcher/cl_disp_msgid_t +* NAME +* cl_disp_msgid_t +* +* DESCRIPTION +* Defines the type of dispatcher messages. +* +* SYNOPSIS +*/ +typedef uint32_t cl_disp_msgid_t; +/**********/ + +/****s* Component Library: Dispatcher/CL_DISP_MSGID_NONE +* NAME +* CL_DISP_MSGID_NONE +* +* DESCRIPTION +* Defines a message value that means "no message". +* This value is used during registration by Dispatcher clients +* that do not wish to receive messages. +* +* No Dispatcher message is allowed to have this value. +* +* SYNOPSIS +*/ +#define CL_DISP_MSGID_NONE 0xFFFFFFFF +/**********/ + +/****s* Component Library: Dispatcher/CL_DISP_INVALID_HANDLE +* NAME +* CL_DISP_INVALID_HANDLE +* +* DESCRIPTION +* Defines the value of an invalid Dispatcher registration handle. +* +* SYNOPSIS +*/ +#define CL_DISP_INVALID_HANDLE ((cl_disp_reg_handle_t)0) +/*********/ + +/****f* Component Library: Dispatcher/cl_pfn_msgrcv_cb_t +* NAME +* cl_pfn_msgrcv_cb_t +* +* DESCRIPTION +* This typedef defines the prototype for client functions invoked +* by the Dispatcher. The Dispatcher calls the corresponding +* client function when delivering a message to the client. +* +* The client function must be reentrant if the user creates a +* Dispatcher with more than one worker thread. +* +* SYNOPSIS +*/ +typedef void +(*cl_pfn_msgrcv_cb_t)( + IN void* context, + IN void* p_data ); +/* +* PARAMETERS +* context +* [in] Client specific context specified in a call to +* cl_disp_register +* +* p_data +* [in] Pointer to the client specific data payload +* of this message. +* +* RETURN VALUE +* This function does not return a value. +* +* NOTES +* This typedef provides a function prototype reference for +* the function provided by Dispatcher clients as a parameter +* to the cl_disp_register function. +* +* SEE ALSO +* Dispatcher, cl_disp_register +*********/ + +/****f* Component Library: Dispatcher/cl_pfn_msgdone_cb_t +* NAME +* cl_pfn_msgdone_cb_t +* +* DESCRIPTION +* This typedef defines the prototype for client functions invoked +* by the Dispatcher. The Dispatcher calls the corresponding +* client function after completing delivery of a message. +* +* The client function must be reentrant if the user creates a +* Dispatcher with more than one worker thread. +* +* SYNOPSIS +*/ +typedef void +(*cl_pfn_msgdone_cb_t)( + IN void* context, + IN void* p_data ); +/* +* PARAMETERS +* context +* [in] Client specific context specified in a call to +* cl_disp_post +* +* p_data +* [in] Pointer to the client specific data payload +* of this message. +* +* RETURN VALUE +* This function does not return a value. +* +* NOTES +* This typedef provides a function prototype reference for +* the function provided by Dispatcher clients as a parameter +* to the cl_disp_post function. +* +* SEE ALSO +* Dispatcher, cl_disp_post +*********/ + +/****s* Component Library: Dispatcher/cl_dispatcher_t +* NAME +* cl_dispatcher_t +* +* DESCRIPTION +* Dispatcher structure. +* +* The Dispatcher is thread safe. +* +* The cl_dispatcher_t structure should be treated as opaque and should +* be manipulated only through the provided functions. +* +* SYNOPSIS +*/ +typedef struct _cl_dispatcher +{ + cl_spinlock_t lock; + cl_ptr_vector_t reg_vec; + cl_qlist_t reg_list; + cl_thread_pool_t worker_threads; + cl_qlist_t msg_fifo; + cl_qpool_t msg_pool; + uint64_t last_msg_queue_time_us; +} cl_dispatcher_t; +/* +* FIELDS +* reg_vec +* Vector of registration info objects. Indexed by message msg_id. +* +* lock +* Spinlock to guard internal structures. +* +* msg_fifo +* FIFO of messages being processed by the Dispatcher. New +* messages are posted to the tail of the FIFO. Worker threads +* pull messages from the front. +* +* worker_threads +* Thread pool of worker threads to dispose of posted messages. +* +* msg_pool +* Pool of message objects to be processed through the FIFO. +* +* reg_count +* Count of the number of registrants. +* +* state +* Indicates the state of the object. +* +* last_msg_queue_time_us +* The time that the last message spent in the Q in usec +* +* SEE ALSO +* Dispatcher +*********/ + +/****s* Component Library: Dispatcher/cl_disp_reg_info_t +* NAME +* cl_disp_reg_info_t +* +* DESCRIPTION +* Defines the dispatcher registration object structure. +* +* The cl_disp_reg_info_t structure is for internal use by the +* Dispatcher only. +* +* SYNOPSIS +*/ +typedef struct _cl_disp_reg_info +{ + cl_list_item_t list_item; + cl_pfn_msgrcv_cb_t pfn_rcv_callback; + const void *context; + atomic32_t ref_cnt; + cl_disp_msgid_t msg_id; + cl_dispatcher_t *p_disp; + +} cl_disp_reg_info_t; +/* +* FIELDS +* pfn_rcv_callback +* Client's message receive callback. +* +* context +* Client's context for message receive callback. +* +* rcv_thread_count +* Number of threads currently in the receive callback. +* +* msg_done_thread_count +* Number of threads currently in the message done callback. +* +* state +* State of this registration object. +* DISP_REGSTATE_INIT: initialized and inactive +* DISP_REGSTATE_ACTIVE: in active use +* DISP_REGSTATE_UNREGPEND: unregistration is pending +* +* msg_id +* Dispatcher message msg_id value for this registration object. +* +* p_disp +* Pointer to parent Dispatcher. +* +* SEE ALSO +*********/ + +/****s* Component Library: Dispatcher/cl_disp_msg_t +* NAME +* cl_disp_msg_t +* +* DESCRIPTION +* Defines the dispatcher message structure. +* +* The cl_disp_msg_t structure is for internal use by the +* Dispatcher only. +* +* SYNOPSIS +*/ +typedef struct _cl_disp_msg +{ + cl_pool_item_t item; + const void *p_data; + cl_disp_reg_info_t *p_src_reg; + cl_disp_reg_info_t *p_dest_reg; + cl_pfn_msgdone_cb_t pfn_xmt_callback; + uint64_t in_time; + const void *context; +} cl_disp_msg_t; +/* +* FIELDS +* item +* List & Pool linkage. Must be first element in the structure!! +* +* msg_id +* The message's numberic ID value. +* +* p_data +* Pointer to the data payload for this message. The payload +* is opaque to the Dispatcher. +* +* p_reg_info +* Pointer to the registration info of the sender. +* +* pfn_xmt_callback +* Client's message done callback. +* +* in_time +* The absolute time the message was inserted into the queue +* +* context +* Client's message done callback context. +* +* SEE ALSO +*********/ + +/****s* Component Library: Dispatcher/cl_disp_reg_info_t +* NAME +* cl_disp_reg_info_t +* +* DESCRIPTION +* Defines the Dispatcher registration handle. This handle +* should be treated as opaque by the client. +* +* SYNOPSIS +*/ +typedef const struct _cl_disp_reg_info *cl_disp_reg_handle_t; +/**********/ + +/****f* Component Library: Dispatcher/cl_disp_construct +* NAME +* cl_disp_construct +* +* DESCRIPTION +* This function constructs a Dispatcher object. +* +* SYNOPSIS +*/ +void +cl_disp_construct( + IN cl_dispatcher_t* const p_disp ); +/* +* PARAMETERS +* p_disp +* [in] Pointer to a Dispatcher. +* +* RETURN VALUE +* This function does not return a value. +* +* NOTES +* Allows calling cl_disp_init and cl_disp_destroy. +* +* SEE ALSO +* Dispatcher, cl_disp_init, cl_disp_destroy +*********/ + +/****f* Component Library: Dispatcher/cl_disp_init +* NAME +* cl_disp_init +* +* DESCRIPTION +* This function initializes a Dispatcher object. +* +* SYNOPSIS +*/ +cl_status_t +cl_disp_init( + IN cl_dispatcher_t* const p_disp, + IN const uint32_t thread_count, + IN const char* const name ); +/* +* PARAMETERS +* p_disp +* [in] Pointer to a Dispatcher. +* +* thread_count +* [in] The number of worker threads to create in this Dispatcher. +* A value of 0 causes the Dispatcher to create one worker thread +* per CPU in the system. When the Dispatcher is created with +* only one thread, the Dispatcher guarantees to deliver posted +* messages in order. When the Dispatcher is created with more +* than one thread, messages may be delivered out of order. +* +* name +* [in] Name to associate with the threads. The name may be up to 16 +* characters, including a terminating null character. All threads +* created in the Dispatcher have the same name. +* +* RETURN VALUE +* CL_SUCCESS if the operation is successful. +* +* SEE ALSO +* Dispatcher, cl_disp_destoy, cl_disp_register, cl_disp_unregister, +* cl_disp_post +*********/ + +/****f* Component Library: Dispatcher/cl_disp_shutdown +* NAME +* cl_disp_shutdown +* +* DESCRIPTION +* This function shutdown a Dispatcher object. So it unreg all messages and +* clears the fifo and waits for the threads to exit +* +* SYNOPSIS +*/ +void +cl_disp_shutdown( + IN cl_dispatcher_t* const p_disp ); +/* +* PARAMETERS +* p_disp +* [in] Pointer to a Dispatcher. +* +* RETURN VALUE +* This function does not return a value. +* +* NOTES +* This function does not returns until all worker threads +* have exited client callback functions and been successfully +* shutdowned. +* +* SEE ALSO +* Dispatcher, cl_disp_construct, cl_disp_init +*********/ + +/****f* Component Library: Dispatcher/cl_disp_destroy +* NAME +* cl_disp_destroy +* +* DESCRIPTION +* This function destroys a Dispatcher object. +* +* SYNOPSIS +*/ +void +cl_disp_destroy( + IN cl_dispatcher_t* const p_disp ); +/* +* PARAMETERS +* p_disp +* [in] Pointer to a Dispatcher. +* +* RETURN VALUE +* This function does not return a value. +* +* SEE ALSO +* Dispatcher, cl_disp_construct, cl_disp_init +*********/ + +/****f* Component Library: Dispatcher/cl_disp_register +* NAME +* cl_disp_register +* +* DESCRIPTION +* This function registers a client with a Dispatcher object. +* +* SYNOPSIS +*/ +cl_disp_reg_handle_t +cl_disp_register( + IN cl_dispatcher_t* const p_disp, + IN const cl_disp_msgid_t msg_id, + IN cl_pfn_msgrcv_cb_t pfn_callback OPTIONAL, + IN const void* const context ); +/* +* PARAMETERS +* p_disp +* [in] Pointer to a Dispatcher. +* +* msg_id +* [in] Numberic message ID for which the client is registering. +* If the client does not wish to receive any messages, +* (a send-only client) then the caller should set this value +* to CL_DISP_MSGID_NONE. For efficiency, numeric message msg_id +* values should start with 0 and should be contiguous, or nearly so. +* +* pfn_callback +* [in] Message receive callback. The Dispatcher calls this +* function after receiving a posted message with the +* appropriate message msg_id value. Send-only clients may specify +* NULL for this value. +* +* context +* [in] Client context value passed to the cl_pfn_msgrcv_cb_t +* function. +* +* RETURN VALUE +* On success a Dispatcher registration handle. +* CL_CL_DISP_INVALID_HANDLE otherwise. +* +* SEE ALSO +* Dispatcher, cl_disp_unregister, cl_disp_post +*********/ + +/****f* Component Library: Dispatcher/cl_disp_unregister +* NAME +* cl_disp_unregister +* +* DESCRIPTION +* This function unregisters a client from a Dispatcher. +* +* SYNOPSIS +*/ +void +cl_disp_unregister( + IN const cl_disp_reg_handle_t handle ); +/* +* PARAMETERS +* handle +* [in] cl_disp_reg_handle_t value return by cl_disp_register. +* +* RETURN VALUE +* This function does not return a value. +* +* NOTES +* This function will not return until worker threads have exited +* the callback functions for this client. Do not invoke this +* function from a callback. +* +* SEE ALSO +* Dispatcher, cl_disp_register +*********/ + +/****f* Component Library: Dispatcher/cl_disp_post +* NAME +* cl_disp_post +* +* DESCRIPTION +* This function posts a message to a Dispatcher object. +* +* SYNOPSIS +*/ +cl_status_t +cl_disp_post( + IN const cl_disp_reg_handle_t handle, + IN const cl_disp_msgid_t msg_id, + IN const void* const p_data, + IN cl_pfn_msgdone_cb_t pfn_callback OPTIONAL, + IN const void* const context ); +/* +* PARAMETERS +* handle +* [in] cl_disp_reg_handle_t value return by cl_disp_register. +* +* msg_id +* [in] Numeric message msg_id value associated with this message. +* +* p_data +* [in] Data payload for this message. +* +* pfn_callback +* [in] Pointer to a cl_pfn_msgdone_cb_t function. +* The Dispatcher calls this function after the message has been +* processed by the recipient. +* The caller may pass NULL for this value, which indicates no +* message done callback is necessary. +* +* context +* [in] Client context value passed to the cl_pfn_msgdone_cb_t +* function. +* +* RETURN VALUE +* CL_SUCCESS if the message was successfully queued in the Dispatcher. +* +* NOTES +* The caller must not modify the memory pointed to by p_data until +* the Dispatcher call the pfn_callback function. +* +* SEE ALSO +* Dispatcher +*********/ + +/****f* Component Library: Dispatcher/cl_disp_get_queue_status +* NAME +* cl_disp_get_queue_status +* +* DESCRIPTION +* This function posts a message to a Dispatcher object. +* +* SYNOPSIS +*/ +void +cl_disp_get_queue_status( + IN const cl_disp_reg_handle_t handle, + OUT uint32_t *p_num_queued_msgs, + OUT uint64_t *p_last_msg_queue_time_ms); +/* +* PARAMETERS +* handle +* [in] cl_disp_reg_handle_t value return by cl_disp_register. +* +* p_last_msg_queue_time_ms +* [out] pointer to a variable to hold the time the last popped up message +* spent in the queue +* +* p_num_queued_msgs +* [out] number of messages in the queue +* +* RETURN VALUE +* Thr time the last popped up message stayed in the queue, in msec +* +* NOTES +* Extarnel Locking is not required. +* +* SEE ALSO +* Dispatcher +*********/ + +END_C_DECLS + +#endif /* !defined(_CL_DISPATCHER_H_) */ + diff --git a/trunk/ulp/opensm/user/include/complib/cl_event_wheel.h b/trunk/ulp/opensm/user/include/complib/cl_event_wheel.h new file mode 100644 index 00000000..129eadd6 --- /dev/null +++ b/trunk/ulp/opensm/user/include/complib/cl_event_wheel.h @@ -0,0 +1,493 @@ +/* + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. + * + * This software is available to you under the OpenIB.org BSD license + * below: + * + * Redistribution and use in source and binary forms, with or + * without modification, are permitted provided that the following + * conditions are met: + * + * - Redistributions of source code must retain the above + * copyright notice, this list of conditions and the following + * disclaimer. + * + * - Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials + * provided with the distribution. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS + * BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN + * ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN + * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + * + * $Id$ + */ + + +/* + * Abstract: + * Declaration of event wheel abstraction. + * + * Environment: + * All + * + * $Revision: 1.4 $ + */ + +#ifndef _CL_EVENT_WHEEL_H_ +#define _CL_EVENT_WHEEL_H_ + +#include +#include +#include +#include +#include +#include + +#ifdef __cplusplus +# define BEGIN_C_DECLS extern "C" { +# define END_C_DECLS } +#else /* !__cplusplus */ +# define BEGIN_C_DECLS +# define END_C_DECLS +#endif /* __cplusplus */ + +BEGIN_C_DECLS + +/****h* Component Library/Event_Wheel +* NAME +* Event_Wheel +* +* DESCRIPTION +* The Event_Wheel provides a facility for registering delayed events +* and getting called once they timeout. +* +* The Event_Wheel functions operate on a cl_event_wheel_t structure +* which should be treated as opaque and should be manipulated +* only through the provided functions. +* +* SEE ALSO +* Structures: +* cl_event_wheel_t +* +* Initialization/Destruction: +* cl_event_wheel_construct, cl_event_wheel_init, cl_event_wheel_destroy +* +* Manipulation: +* cl_event_wheel_reg, cl_event_wheel_unreg +* +*********/ + +/****f* Component Library: Event_Wheel/cl_pfn_event_aged_cb_t +* NAME +* cl_pfn_event_aged_cb_t +* +* DESCRIPTION +* This typedef defines the prototype for client functions invoked +* by the Event_Wheel. The Event_Wheel calls the corresponding +* client function when the specific item has aged. +* +* SYNOPSIS +*/ +typedef uint64_t +(*cl_pfn_event_aged_cb_t)( + IN uint64_t key, + IN uint32_t num_regs, + IN void* context); +/* +* PARAMETERS +* key +* [in] The key used for registering the item in the call to +* cl_event_wheel_reg +* +* num_regs +* [in] The number of times this event was registered (pushed in time). +* +* context +* [in] Client specific context specified in a call to +* cl_event_wheel_reg +* +* RETURN VALUE +* This function returns the abosolute time the event should fire in [usec]. +* If lower then current time means the event should be unregistered +* immediatly. +* +* NOTES +* This typedef provides a function prototype reference for +* the function provided by Event_Wheel clients as a parameter +* to the cl_event_wheel_reg function. +* +* SEE ALSO +* Event_Wheel, cl_event_wheel_reg +*********/ + +/****s* Component Library: Event_Wheel/cl_event_wheel_t +* NAME +* cl_event_wheel_t +* +* DESCRIPTION +* Event_Wheel structure. +* +* The Event_Wheel is thread safe. +* +* The cl_event_wheel_t structure should be treated as opaque and should +* be manipulated only through the provided functions. +* +* SYNOPSIS +*/ +typedef struct _cl_event_wheel +{ + cl_spinlock_t lock; + cl_spinlock_t *p_external_lock; + + cl_qmap_t events_map; + boolean_t closing; + cl_qlist_t events_wheel; + cl_timer_t timer; + osm_log_t *p_log; +} cl_event_wheel_t; +/* +* FIELDS +* lock +* Spinlock to guard internal structures. +* +* p_external_lock +* Reference to external spinlock to guard internal structures +* if the event wheel is part of a larger object protected by its own lock +* +* events_map +* A Map holding all registered event items by their key. +* +* closing +* A flag indicating the event wheel is closing. This means that +* callbacks that are called when closing == TRUE should just be ignored. +* +* events_wheel +* A list of the events sorted by expiration time. +* +* timer +* The timer scheduling event time propagation. +* +* p_log +* Pointer to opensm log object. +* +* SEE ALSO +* Event_Wheel +*********/ + +/****s* Component Library: Event_Wheel/cl_event_wheel_reg_info_t +* NAME +* cl_event_wheel_reg_info_t +* +* DESCRIPTION +* Defines the event_wheel registration object structure. +* +* The cl_event_wheel_reg_info_t structure is for internal use by the +* Event_Wheel only. +* +* SYNOPSIS +*/ +typedef struct _cl_event_wheel_reg_info +{ + cl_map_item_t map_item; + cl_list_item_t list_item; + uint64_t key; + cl_pfn_event_aged_cb_t pfn_aged_callback; + uint64_t aging_time; + uint32_t num_regs; + void *context; + cl_event_wheel_t *p_event_wheel; +} cl_event_wheel_reg_info_t; +/* +* FIELDS +* map_item +* The map item of this event +* +* list_item +* The sorted by aging time list item +* +* key +* The key by which one can find the event +* +* pfn_aged_callback +* The clients Event-Aged callback +* +* aging_time +* The delta time [msec] for which the event should age. +* +* num_regs +* The number of times the same event (key) was registered +* +* context +* Client's context for event-aged callback. +* +* p_event_wheel +* Pointer to this event wheel object +* +* SEE ALSO +*********/ + +/****f* Component Library: Event_Wheel/cl_event_wheel_construct +* NAME +* cl_event_wheel_construct +* +* DESCRIPTION +* This function constructs a Event_Wheel object. +* +* SYNOPSIS +*/ +void +cl_event_wheel_construct( + IN cl_event_wheel_t* const p_event_wheel ); +/* +* PARAMETERS +* p_event_wheel +* [in] Pointer to a Event_Wheel. +* +* RETURN VALUE +* This function does not return a value. +* +* NOTES +* Allows calling cl_event_wheel_init and cl_event_wheel_destroy. +* +* SEE ALSO +* Event_Wheel, cl_event_wheel_init, cl_event_wheel_destroy +*********/ + +/****f* Component Library: Event_Wheel/cl_event_wheel_init +* NAME +* cl_event_wheel_init +* +* DESCRIPTION +* This function initializes a Event_Wheel object. +* +* SYNOPSIS +*/ +cl_status_t +cl_event_wheel_init( + IN cl_event_wheel_t* const p_event_wheel, + IN osm_log_t *p_log); + +/* +* PARAMETERS +* p_event_wheel +* [in] Pointer to a Event_Wheel. +* +* p_log +* [in] Pointer to opensm log object to be used for logging +* +* RETURN VALUE +* CL_SUCCESS if the operation is successful. +* +* SEE ALSO +* Event_Wheel, cl_event_wheel_destoy, cl_event_wheel_reg, cl_event_wheel_unreg +* +*********/ + +/****f* Component Library: Event_Wheel/cl_event_wheel_init +* NAME +* cl_event_wheel_init +* +* DESCRIPTION +* This function initializes a Event_Wheel object. +* +* SYNOPSIS +*/ +cl_status_t +cl_event_wheel_init_ex( + IN cl_event_wheel_t* const p_event_wheel, + IN osm_log_t *p_log, + IN cl_spinlock_t *p_external_lock); + +/* +* PARAMETERS +* p_event_wheel +* [in] Pointer to a Event_Wheel. +* +* p_log +* [in] Pointer to opensm log object to be used for logging +* +* p_external_lock +* [in] Reference to external spinlock to guard internal structures +* if the event wheel is part of a larger object protected by its own lock +* +* RETURN VALUE +* CL_SUCCESS if the operation is successful. +* +* SEE ALSO +* Event_Wheel, cl_event_wheel_destoy, cl_event_wheel_reg, cl_event_wheel_unreg +* +*********/ + +/****f* Component Library: Event_Wheel/cl_event_wheel_destroy +* NAME +* cl_event_wheel_destroy +* +* DESCRIPTION +* This function destroys a Event_Wheel object. +* +* SYNOPSIS +*/ +void +cl_event_wheel_destroy( + IN cl_event_wheel_t* const p_event_wheel ); +/* +* PARAMETERS +* p_event_wheel +* [in] Pointer to a Event_Wheel. +* +* RETURN VALUE +* This function does not return a value. +* +* NOTES +* This function does not returns until all client callback functions +* been successfully finished. +* +* SEE ALSO +* Event_Wheel, cl_event_wheel_construct, cl_event_wheel_init +*********/ + +/****f* Component Library: Event_Wheel/cl_event_wheel_dump +* NAME +* cl_event_wheel_dump +* +* DESCRIPTION +* This function dumps the details of an Event_Whell object. +* +* SYNOPSIS +*/ +void +cl_event_wheel_dump( + IN cl_event_wheel_t* const p_event_wheel ); +/* +* PARAMETERS +* p_event_wheel +* [in] Pointer to a Event_Wheel. +* +* RETURN VALUE +* This function does not return a value. +* +* NOTES +* Note that this function should be called inside a lock of the event wheel! +* It doesn't aquire the lock by itself. +* +* SEE ALSO +* Event_Wheel, cl_event_wheel_construct, cl_event_wheel_init +*********/ + +/****f* Component Library: Event_Wheel/cl_event_wheel_reg +* NAME +* cl_event_wheel_reg +* +* DESCRIPTION +* This function registers a client with a Event_Wheel object. +* +* SYNOPSIS +*/ +cl_status_t +cl_event_wheel_reg( + IN cl_event_wheel_t* const p_event_wheel, + IN const uint64_t key, + IN const uint64_t aging_time_usec, + IN cl_pfn_event_aged_cb_t pfn_callback, + IN void* const context ); +/* +* PARAMETERS +* p_event_wheel +* [in] Pointer to a Event_Wheel. +* +* key +* [in] The specifc Key by which events are registered. +* +* aging_time_usec +* [in] The absolute time this event should age in usec +* +* pfn_callback +* [in] Event Aging callback. The Event_Wheel calls this +* function after the time the event has registed for has come. +* +* context +* [in] Client context value passed to the cl_pfn_event_aged_cb_t +* function. +* +* RETURN VALUE +* On success a Event_Wheel CL_SUCCESS or CL_ERROR otherwise. +* +* SEE ALSO +* Event_Wheel, cl_event_wheel_unreg +*********/ + +/****f* Component Library: Event_Wheel/cl_event_wheel_unreg +* NAME +* cl_event_wheel_unreg +* +* DESCRIPTION +* This function unregisters a client event from a Event_Wheel. +* +* SYNOPSIS +*/ +void +cl_event_wheel_unreg( + IN cl_event_wheel_t* const p_event_wheel, + IN uint64_t key ); +/* +* PARAMETERS +* p_event_wheel +* [in] Pointer to a Event_Wheel. +* +* key +* [in] The key used for registering the event +* +* RETURN VALUE +* This function does not return a value. +* +* NOTES +* After the event has aged it is automatically removed from +* the event wheel. So it should only be invoked when the need arises +* to remove existing events before they age. +* +* SEE ALSO +* Event_Wheel, cl_event_wheel_reg +*********/ + +/****f* Component Library: Event_Wheel/cl_event_wheel_num_regs +* NAME +* cl_event_wheel_num_regs +* +* DESCRIPTION +* This function returns the number of times an event was registered. +* +* SYNOPSIS +*/ +uint32_t +cl_event_wheel_num_regs( + IN cl_event_wheel_t* const p_event_wheel, + IN uint64_t key ); +/* +* PARAMETERS +* p_event_wheel +* [in] Pointer to a Event_Wheel. +* +* key +* [in] The key used for registering the event +* +* RETURN VALUE +* The number of times the event was registered. +* 0 if never registered or eventually aged. +* +* SEE ALSO +* Event_Wheel, cl_event_wheel_reg, cl_event_wheel_unreg +*********/ + +END_C_DECLS + +#endif /* !defined(_CL_EVENT_WHEEL_H_) */ + diff --git a/trunk/ulp/opensm/user/include/iba/ib_types.h b/trunk/ulp/opensm/user/include/iba/ib_types.h index 691e41a3..9dd1ed6d 100644 --- a/trunk/ulp/opensm/user/include/iba/ib_types.h +++ b/trunk/ulp/opensm/user/include/iba/ib_types.h @@ -39,7 +39,6 @@ #include #include #include -#include #ifdef __cplusplus # define BEGIN_C_DECLS extern "C" { @@ -53,25 +52,16 @@ BEGIN_C_DECLS #if defined( WIN32 ) || defined( _WIN64 ) #if defined( EXPORT_AL_SYMBOLS ) - #define AL_EXPORT __declspec(dllexport) + #define OSM_EXPORT __declspec(dllexport) #else - #define AL_EXPORT __declspec(dllimport) + #define OSM_EXPORT __declspec(dllimport) #endif - - #ifdef CL_KERNEL - #define AL_API - #define AL_INLINE static inline - #else - #define AL_API __stdcall - #define AL_INLINE static inline - /* Defined for some unique access function that are defined only in osm ib_types */ - #define OSM_INLINE static inline - #endif /* CL_KERNEL */ + #define OSM_API __stdcall + #define OSM_CDECL __cdecl #else - #define AL_EXPORT extern - #define AL_INLINE static inline - #define OSM_INLINE static inline - #define AL_API + #define OSM_EXPORT extern + #define OSM_API + #define OSM_CDECL #define __ptr64 #endif @@ -538,6 +528,30 @@ BEGIN_C_DECLS #define IB_MCLASS_VENDOR_LOW_RANGE_MAX 0x0f /**********/ +/****d* IBA Base: Constants/IB_MCLASS_DEV_ADM +* NAME +* IB_MCLASS_DEV_ADM +* +* DESCRIPTION +* Subnet Management Class, Device Administration +* +* SOURCE +*/ +#define IB_MCLASS_DEV_ADM 0x10 +/**********/ + +/****d* IBA Base: Constants/IB_MCLASS_BIS +* NAME +* IB_MCLASS_BIS +* +* DESCRIPTION +* Subnet Management Class, BIS +* +* SOURCE +*/ +#define IB_MCLASS_BIS 0x12 +/**********/ + /****d* IBA Base: Constants/IB_MCLASS_VENDOR_HIGH_RANGE_MIN * NAME * IB_MCLASS_VENDOR_HIGH_RANGE_MIN @@ -572,7 +586,7 @@ BEGIN_C_DECLS * * SYNOPSIS */ -AL_INLINE boolean_t AL_API +static inline boolean_t OSM_API ib_class_is_vendor_specific_low( IN const uint8_t class_code ) { @@ -604,7 +618,7 @@ ib_class_is_vendor_specific_low( * * SYNOPSIS */ -AL_INLINE boolean_t AL_API +static inline boolean_t OSM_API ib_class_is_vendor_specific_high( IN const uint8_t class_code ) { @@ -636,7 +650,7 @@ ib_class_is_vendor_specific_high( * * SYNOPSIS */ -AL_INLINE boolean_t AL_API +static inline boolean_t OSM_API ib_class_is_vendor_specific( IN const uint8_t class_code ) { @@ -658,6 +672,38 @@ ib_class_is_vendor_specific( * ib_class_is_vendor_specific_low, ib_class_is_vendor_specific_high *********/ +/****f* IBA Base: Types/ib_class_is_rmpp +* NAME +* ib_class_is_rmpp +* +* DESCRIPTION +* Indicates if the Class Code supports RMPP +* +* SYNOPSIS +*/ +static inline boolean_t OSM_API +ib_class_is_rmpp( + IN const uint8_t class_code ) +{ + return( (class_code == IB_MCLASS_SUBN_ADM) || + (class_code == IB_MCLASS_DEV_MGMT) || + (class_code == IB_MCLASS_DEV_ADM) || + (class_code == IB_MCLASS_BIS) || + ib_class_is_vendor_specific_high( class_code ) ); +} +/* +* PARAMETERS +* class_code +* [in] The Management Datagram Class Code +* +* RETURN VALUE +* TRUE if the class supports RMPP +* FALSE otherwise. +* +* NOTES +* +*********/ + /* * MAD methods */ @@ -1127,6 +1173,18 @@ ib_class_is_vendor_specific( #define IB_MAD_ATTR_PORTINFO_RECORD (CL_NTOH16(0x0012)) /**********/ +/****d* IBA Base: Constants/IB_MAD_ATTR_SWITCH_INFO_RECORD +* NAME +* IB_MAD_ATTR_SWITCH_INFO_RECORD +* +* DESCRIPTION +* SwitchInfoRecord attribute (15.2.5) +* +* SOURCE +*/ +#define IB_MAD_ATTR_SWITCH_INFO_RECORD (CL_NTOH16(0x0014)) +/**********/ + /****d* IBA Base: Constants/IB_MAD_ATTR_LINK_RECORD * NAME * IB_MAD_ATTR_LINK_RECORD @@ -1223,6 +1281,18 @@ ib_class_is_vendor_specific( #define IB_MAD_ATTR_LFT_RECORD (CL_NTOH16(0x0015)) /**********/ +/****d* IBA Base: Constants/IB_MAD_ATTR_MFT_RECORD +* NAME +* IB_MAD_ATTR_MFT_RECORD +* +* DESCRIPTION +* MulticastForwardingTableRecord attribute (15.2.5.8) +* +* SOURCE +*/ +#define IB_MAD_ATTR_MFT_RECORD (CL_NTOH16(0x0017)) +/**********/ + /****d* IBA Base: Constants/IB_MAD_ATTR_PKEYTBL_RECORD * NAME * IB_MAD_ATTR_PKEYTBL_RECORD @@ -1285,7 +1355,7 @@ ib_class_is_vendor_specific( /****d* IBA Base: Constants/IB_MAD_ATTR_TRACE_RECORD * NAME -* IB_MAD_ATTR_MTRACE_RECORD +* IB_MAD_ATTR_TRACE_RECORD * * DESCRIPTION * TraceRecord attribute (15.2.5) @@ -1319,6 +1389,17 @@ ib_class_is_vendor_specific( #define IB_MAD_ATTR_SVC_ASSOCIATION_RECORD (CL_NTOH16(0x003B)) /**********/ +/****d* IBA Base: Constants/IB_MAD_ATTR_INFORM_INFO_RECORD +* NAME +* IB_MAD_ATTR_INFORM_INFO_RECORD +* +* DESCRIPTION +* InformInfo Record attribute (15.2.5) +* +* SOURCE +*/ +#define IB_MAD_ATTR_INFORM_INFO_RECORD (CL_NTOH16(0x00F3)) + /****d* IBA Base: Constants/IB_MAD_ATTR_IO_UNIT_INFO * NAME * IB_MAD_ATTR_IO_UNIT_INFO @@ -1617,6 +1698,18 @@ ib_class_is_vendor_specific( * SOURCE */ #define IB_PATH_REC_SELECTOR_MASK 0xC0 + +/****d* IBA Base: Constants/IB_MULTIPATH_REC_SELECTOR_MASK +* NAME +* IB_MULTIPATH_REC_SELECTOR_MASK +* +* DESCRIPTION +* Mask for the selector field for multipath record MTU, rate, +* and packet lifetime. +* +* SOURCE +*/ +#define IB_MULTIPATH_REC_SELECTOR_MASK 0xC0 /**********/ /****d* IBA Base: Constants/IB_PATH_REC_BASE_MASK @@ -1632,6 +1725,19 @@ ib_class_is_vendor_specific( #define IB_PATH_REC_BASE_MASK 0x3F /**********/ +/****d* IBA Base: Constants/IB_MULTIPATH_REC_BASE_MASK +* NAME +* IB_MULTIPATH_REC_BASE_MASK +* +* DESCRIPTION +* Mask for the base value field for multipath record MTU, rate, +* and packet lifetime. +* +* SOURCE +*/ +#define IB_MULTIPATH_REC_BASE_MASK 0x3F +/**********/ + /****h* IBA Base/Type Definitions * NAME * Type Definitions @@ -1723,7 +1829,7 @@ static const char* const __ib_node_type_str[] = * * SYNOPSIS */ -AL_INLINE const char* AL_API +static inline const char* OSM_API ib_get_node_type_str( IN uint32_t node_type ) { @@ -1765,7 +1871,7 @@ static const char* const __ib_port_state_str[] = * * SYNOPSIS */ -AL_INLINE const char* AL_API +static inline const char* OSM_API ib_get_port_state_str( IN uint8_t port_state ) { @@ -1796,7 +1902,7 @@ ib_get_port_state_str( * * SYNOPSIS */ -AL_INLINE uint8_t AL_API +static inline uint8_t OSM_API ib_get_port_state_from_str( IN char* p_port_state_str ) { @@ -1851,7 +1957,7 @@ ib_get_port_state_from_str( * * SYNOPSIS */ -AL_INLINE ib_net16_t AL_API +static inline ib_net16_t OSM_API ib_pkey_get_base( IN const ib_net16_t pkey ) { @@ -1879,7 +1985,7 @@ ib_pkey_get_base( * * SYNOPSIS */ -AL_INLINE boolean_t AL_API +static inline boolean_t OSM_API ib_pkey_is_full_member( IN const ib_net16_t pkey ) { @@ -1911,7 +2017,7 @@ ib_pkey_is_full_member( * * SYNOPSIS */ -OSM_INLINE boolean_t AL_API +static inline boolean_t OSM_API ib_pkey_is_invalid( IN const ib_net16_t pkey ) { @@ -1976,13 +2082,56 @@ typedef union _ib_gid * SEE ALSO *********/ -AL_INLINE boolean_t AL_API +/****f* IBA Base: Types/ib_gid_is_multicast +* NAME +* ib_gid_is_multicast +* +* DESCRIPTION +* Returns a boolean indicating whether a GID is a multicast GID. +* +* SYNOPSIS +*/ +static inline boolean_t OSM_API ib_gid_is_multicast( IN const ib_gid_t* p_gid ) { return( p_gid->raw[0] == 0xFF ); } +/****f* IBA Base: Types/ib_gid_get_scope +* NAME +* ib_gid_get_scope +* +* DESCRIPTION +* Returns scope of (assumed) multicast GID. +* +* SYNOPSIS +*/ +static inline uint8_t OSM_API +ib_mgid_get_scope( + IN const ib_gid_t* p_gid ) +{ + return( p_gid->raw[1] & 0x0F ); +} + +/****f* IBA Base: Types/ib_gid_set_scope +* NAME +* ib_gid_set_scope +* +* DESCRIPTION +* Sets scope of (assumed) multicast GID. +* +* SYNOPSIS +*/ +static inline void OSM_API +ib_mgid_set_scope( + IN ib_gid_t* const p_gid, + IN const uint8_t scope ) +{ + p_gid->raw[1] &= 0xF0; + p_gid->raw[1] |= scope & 0x0F; +} + /****f* IBA Base: Types/ib_gid_set_default * NAME * ib_gid_set_default @@ -1992,7 +2141,7 @@ ib_gid_is_multicast( * * SYNOPSIS */ -AL_INLINE void AL_API +static inline void OSM_API ib_gid_set_default( IN ib_gid_t* const p_gid, IN const ib_net64_t interface_id ) @@ -2026,7 +2175,7 @@ ib_gid_set_default( * * SYNOPSIS */ -AL_INLINE ib_net64_t AL_API +static inline ib_net64_t OSM_API ib_gid_get_subnet_prefix( IN const ib_gid_t* const p_gid ) { @@ -2056,11 +2205,12 @@ ib_gid_get_subnet_prefix( * * SYNOPSIS */ -AL_INLINE boolean_t AL_API +static inline boolean_t OSM_API ib_gid_is_link_local( IN const ib_gid_t* const p_gid ) { - return( ib_gid_get_subnet_prefix( p_gid ) == IB_DEFAULT_SUBNET_PREFIX ); + return( ( ib_gid_get_subnet_prefix( p_gid ) & + CL_HTON64( 0xFFC0000000000000ULL ) ) == IB_DEFAULT_SUBNET_PREFIX ); } /* * PARAMETERS @@ -2087,7 +2237,7 @@ ib_gid_is_link_local( * * SYNOPSIS */ -AL_INLINE boolean_t AL_API +static inline boolean_t OSM_API ib_gid_is_site_local( IN const ib_gid_t* const p_gid ) { @@ -2100,7 +2250,7 @@ ib_gid_is_site_local( * [in] Pointer to the GID object. * * RETURN VALUES -* Returns TRUE if the unicast GID scoping indicates link local, +* Returns TRUE if the unicast GID scoping indicates site local, * FALSE otherwise. * * NOTES @@ -2118,7 +2268,7 @@ ib_gid_is_site_local( * * SYNOPSIS */ -AL_INLINE ib_net64_t AL_API +static inline ib_net64_t OSM_API ib_gid_get_guid( IN const ib_gid_t* const p_gid ) { @@ -2252,7 +2402,7 @@ typedef struct _ib_path_rec #define IB_LR_COMPMASK_TO_PORT (CL_HTON64(((uint64_t)1)<<2)) #define IB_LR_COMPMASK_TO_LID (CL_HTON64(((uint64_t)1)<<3)) -/* VL Arbitration Record MASKs */ +/* VL Arbitration Record Masks */ #define IB_VLA_COMPMASK_LID (CL_HTON64(((uint64_t)1)<<0)) #define IB_VLA_COMPMASK_OUT_PORT (CL_HTON64(((uint64_t)1)<<1)) #define IB_VLA_COMPMASK_BLOCK (CL_HTON64(((uint64_t)1)<<2)) @@ -2267,10 +2417,21 @@ typedef struct _ib_path_rec #define IB_PKEY_COMPMASK_BLOCK (CL_HTON64(((uint64_t)1)<<1)) #define IB_PKEY_COMPMASK_PORT (CL_HTON64(((uint64_t)1)<<2)) +/* Switch Info Record Masks */ +#define IB_SWIR_COMPMASK_LID (CL_HTON64(((uint64_t)1)<<0)) +#define IB_SWIR_COMPMASK_RESERVED1 (CL_HTON64(((uint64_t)1)<<1)) + /* LFT Record Masks */ #define IB_LFTR_COMPMASK_LID (CL_HTON64(((uint64_t)1)<<0)) #define IB_LFTR_COMPMASK_BLOCK (CL_HTON64(((uint64_t)1)<<1)) +/* MFT Record Masks */ +#define IB_MFTR_COMPMASK_LID (CL_HTON64(((uint64_t)1)<<0)) +#define IB_MFTR_COMPMASK_POSITION (CL_HTON64(((uint64_t)1)<<1)) +#define IB_MFTR_COMPMASK_RESERVED1 (CL_HTON64(((uint64_t)1)<<2)) +#define IB_MFTR_COMPMASK_BLOCK (CL_HTON64(((uint64_t)1)<<3)) +#define IB_MFTR_COMPMASK_RESERVED2 (CL_HTON64(((uint64_t)1)<<4)) + /* NodeInfo Record Masks */ #define IB_NR_COMPMASK_LID (CL_HTON64(((uint64_t)1)<<0)) #define IB_NR_COMPMASK_RESERVED1 (CL_HTON64(((uint64_t)1)<<1)) @@ -2413,6 +2574,59 @@ typedef struct _ib_path_rec #define IB_GIR_COMPMASK_GID6 (CL_HTON64(((uint64_t)1)<<10)) #define IB_GIR_COMPMASK_GID7 (CL_HTON64(((uint64_t)1)<<11)) +/* MultiPath Record Component Masks */ +#define IB_MPR_COMPMASK_RAWTRAFFIC (CL_HTON64(((uint64_t)1)<<0)) +#define IB_MPR_COMPMASK_RESV0 (CL_HTON64(((uint64_t)1)<<1)) +#define IB_MPR_COMPMASK_FLOWLABEL (CL_HTON64(((uint64_t)1)<<2)) +#define IB_MPR_COMPMASK_HOPLIMIT (CL_HTON64(((uint64_t)1)<<3)) +#define IB_MPR_COMPMASK_TCLASS (CL_HTON64(((uint64_t)1)<<4)) +#define IB_MPR_COMPMASK_REVERSIBLE (CL_HTON64(((uint64_t)1)<<5)) +#define IB_MPR_COMPMASK_NUMBPATH (CL_HTON64(((uint64_t)1)<<6)) +#define IB_MPR_COMPMASK_PKEY (CL_HTON64(((uint64_t)1)<<7)) +#define IB_MPR_COMPMASK_RESV1 (CL_HTON64(((uint64_t)1)<<8)) +#define IB_MPR_COMPMASK_SL (CL_HTON64(((uint64_t)1)<<9)) +#define IB_MPR_COMPMASK_MTUSELEC (CL_HTON64(((uint64_t)1)<<10)) +#define IB_MPR_COMPMASK_MTU (CL_HTON64(((uint64_t)1)<<11)) +#define IB_MPR_COMPMASK_RATESELEC (CL_HTON64(((uint64_t)1)<<12)) +#define IB_MPR_COMPMASK_RATE (CL_HTON64(((uint64_t)1)<<13)) +#define IB_MPR_COMPMASK_PKTLIFETIMESELEC (CL_HTON64(((uint64_t)1)<<14)) +#define IB_MPR_COMPMASK_PKTLIFETIME (CL_HTON64(((uint64_t)1)<<15)) +#define IB_MPR_COMPMASK_RESV2 (CL_HTON64(((uint64_t)1)<<16)) +#define IB_MPR_COMPMASK_INDEPSELEC (CL_HTON64(((uint64_t)1)<<17)) +#define IB_MPR_COMPMASK_RESV3 (CL_HTON64(((uint64_t)1)<<18)) +#define IB_MPR_COMPMASK_SGIDCOUNT (CL_HTON64(((uint64_t)1)<<19)) +#define IB_MPR_COMPMASK_DGIDCOUNT (CL_HTON64(((uint64_t)1)<<20)) +#define IB_MPR_COMPMASK_RESV4 (CL_HTON64(((uint64_t)1)<<21)) + +/* SMInfo Record Component Masks */ +#define IB_SMIR_COMPMASK_LID (CL_HTON64(((uint64_t)1)<<0)) +#define IB_SMIR_COMPMASK_RESV0 (CL_HTON64(((uint64_t)1)<<1)) +#define IB_SMIR_COMPMASK_GUID (CL_HTON64(((uint64_t)1)<<2)) +#define IB_SMIR_COMPMASK_SMKEY (CL_HTON64(((uint64_t)1)<<3)) +#define IB_SMIR_COMPMASK_ACTCOUNT (CL_HTON64(((uint64_t)1)<<4)) +#define IB_SMIR_COMPMASK_PRIORITY (CL_HTON64(((uint64_t)1)<<5)) +#define IB_SMIR_COMPMASK_SMSTATE (CL_HTON64(((uint64_t)1)<<6)) + +/* InformInfo Record Component Masks */ +#define IB_IIR_COMPMASK_SUBSCRIBERGID (CL_HTON64(((uint64_t)1)<<0)) +#define IB_IIR_COMPMASK_ENUM (CL_HTON64(((uint64_t)1)<<1)) +#define IB_IIR_COMPMASK_RESV0 (CL_HTON64(((uint64_t)1)<<2)) +#define IB_IIR_COMPMASK_GID (CL_HTON64(((uint64_t)1)<<3)) +#define IB_IIR_COMPMASK_LIDRANGEBEGIN (CL_HTON64(((uint64_t)1)<<4)) +#define IB_IIR_COMPMASK_LIDRANGEEND (CL_HTON64(((uint64_t)1)<<5)) +#define IB_IIR_COMPMASK_RESV1 (CL_HTON64(((uint64_t)1)<<6)) +#define IB_IIR_COMPMASK_ISGENERIC (CL_HTON64(((uint64_t)1)<<7)) +#define IB_IIR_COMPMASK_SUBSCRIBE (CL_HTON64(((uint64_t)1)<<8)) +#define IB_IIR_COMPMASK_TYPE (CL_HTON64(((uint64_t)1)<<9)) +#define IB_IIR_COMPMASK_TRAPNUMB (CL_HTON64(((uint64_t)1)<<10)) +#define IB_IIR_COMPMASK_DEVICEID (CL_HTON64(((uint64_t)1)<<10)) +#define IB_IIR_COMPMASK_QPN (CL_HTON64(((uint64_t)1)<<11)) +#define IB_IIR_COMPMASK_RESV2 (CL_HTON64(((uint64_t)1)<<12)) +#define IB_IIR_COMPMASK_RESPTIME (CL_HTON64(((uint64_t)1)<<13)) +#define IB_IIR_COMPMASK_RESV3 (CL_HTON64(((uint64_t)1)<<14)) +#define IB_IIR_COMPMASK_PRODTYPE (CL_HTON64(((uint64_t)1)<<15)) +#define IB_IIR_COMPMASK_VENDID (CL_HTON64(((uint64_t)1)<<15)) + /****f* IBA Base: Types/ib_path_rec_init_local * NAME * ib_path_rec_init_local @@ -2422,7 +2636,7 @@ typedef struct _ib_path_rec * * SYNOPSIS */ -AL_INLINE void AL_API +static inline void OSM_API ib_path_rec_init_local( IN ib_path_rec_t* const p_rec, IN ib_gid_t* const p_dgid, @@ -2532,7 +2746,7 @@ ib_path_rec_init_local( * * SYNOPSIS */ -AL_INLINE uint8_t AL_API +static inline uint8_t OSM_API ib_path_rec_num_path( IN const ib_path_rec_t* const p_rec ) { @@ -2561,7 +2775,7 @@ ib_path_rec_num_path( * * SYNOPSIS */ -AL_INLINE uint8_t AL_API +static inline uint8_t OSM_API ib_path_rec_sl( IN const ib_path_rec_t* const p_rec ) { @@ -2590,7 +2804,7 @@ ib_path_rec_sl( * * SYNOPSIS */ -AL_INLINE uint8_t AL_API +static inline uint8_t OSM_API ib_path_rec_mtu( IN const ib_path_rec_t* const p_rec ) { @@ -2625,7 +2839,7 @@ ib_path_rec_mtu( * * SYNOPSIS */ -AL_INLINE uint8_t AL_API +static inline uint8_t OSM_API ib_path_rec_mtu_sel( IN const ib_path_rec_t* const p_rec ) { @@ -2658,7 +2872,7 @@ ib_path_rec_mtu_sel( * * SYNOPSIS */ -AL_INLINE uint8_t AL_API +static inline uint8_t OSM_API ib_path_rec_rate( IN const ib_path_rec_t* const p_rec ) { @@ -2697,7 +2911,7 @@ ib_path_rec_rate( * * SYNOPSIS */ -AL_INLINE uint8_t AL_API +static inline uint8_t OSM_API ib_path_rec_rate_sel( IN const ib_path_rec_t* const p_rec ) { @@ -2730,7 +2944,7 @@ ib_path_rec_rate_sel( * * SYNOPSIS */ -AL_INLINE uint8_t AL_API +static inline uint8_t OSM_API ib_path_rec_pkt_life( IN const ib_path_rec_t* const p_rec ) { @@ -2742,7 +2956,7 @@ ib_path_rec_pkt_life( * [in] Pointer to the path record object. * * RETURN VALUES -* Encoded path pkt_life = 4.096 µsec * 2 ** PacketLifeTime. +* Encoded path pkt_life = 4.096 µsec * 2 ** PacketLifeTime. * * NOTES * @@ -2759,7 +2973,7 @@ ib_path_rec_pkt_life( * * SYNOPSIS */ -AL_INLINE uint8_t AL_API +static inline uint8_t OSM_API ib_path_rec_pkt_life_sel( IN const ib_path_rec_t* const p_rec ) { @@ -2792,7 +3006,7 @@ ib_path_rec_pkt_life_sel( * * SYNOPSIS */ -AL_INLINE uint32_t AL_API +static inline uint32_t OSM_API ib_path_rec_flow_lbl( IN const ib_path_rec_t* const p_rec ) { @@ -2821,7 +3035,7 @@ ib_path_rec_flow_lbl( * * SYNOPSIS */ -AL_INLINE uint8_t AL_API +static inline uint8_t OSM_API ib_path_rec_hop_limit( IN const ib_path_rec_t* const p_rec ) { @@ -3024,7 +3238,7 @@ typedef struct _ib_sm_info * * SYNOPSIS */ -AL_INLINE uint8_t AL_API +static inline uint8_t OSM_API ib_sminfo_get_priority( IN const ib_sm_info_t* const p_smi ) { @@ -3052,7 +3266,7 @@ ib_sminfo_get_priority( * * SYNOPSIS */ -AL_INLINE uint8_t AL_API +static inline uint8_t OSM_API ib_sminfo_get_state( IN const ib_sm_info_t* const p_smi ) { @@ -3170,7 +3384,7 @@ typedef struct _ib_rmpp_mad * * SYNOPSIS */ -AL_INLINE void AL_API +static inline void OSM_API ib_mad_init_new( IN ib_mad_t* const p_mad, IN const uint8_t mgmt_class, @@ -3233,7 +3447,7 @@ ib_mad_init_new( * * SYNOPSIS */ -AL_INLINE void AL_API +static inline void OSM_API ib_mad_init_response( IN const ib_mad_t* const p_req_mad, IN ib_mad_t* const p_mad, @@ -3278,7 +3492,7 @@ ib_mad_init_response( * * SYNOPSIS */ -AL_INLINE boolean_t AL_API +static inline boolean_t OSM_API ib_mad_is_response( IN const ib_mad_t* const p_mad ) { @@ -3333,7 +3547,7 @@ ib_mad_is_response( * * SYNOPSIS */ -AL_INLINE boolean_t AL_API +static inline boolean_t OSM_API ib_rmpp_is_flag_set( IN const ib_rmpp_mad_t* const p_rmpp_mad, IN const uint8_t flag ) @@ -3358,7 +3572,7 @@ ib_rmpp_is_flag_set( * ib_mad_t, ib_rmpp_mad_t *********/ -AL_INLINE void AL_API +static inline void OSM_API ib_rmpp_set_resp_time( IN ib_rmpp_mad_t* const p_rmpp_mad, IN const uint8_t resp_time ) @@ -3368,7 +3582,7 @@ ib_rmpp_set_resp_time( } -AL_INLINE uint8_t AL_API +static inline uint8_t OSM_API ib_rmpp_get_resp_time( IN const ib_rmpp_mad_t* const p_rmpp_mad ) { @@ -3504,7 +3718,7 @@ typedef struct _ib_smp * * SYNOPSIS */ -AL_INLINE ib_net16_t AL_API +static inline ib_net16_t OSM_API ib_smp_get_status( IN const ib_smp_t* const p_smp ) { @@ -3533,7 +3747,7 @@ ib_smp_get_status( * * SYNOPSIS */ -AL_INLINE boolean_t AL_API +static inline boolean_t OSM_API ib_smp_is_response( IN const ib_smp_t* const p_smp ) { @@ -3562,7 +3776,7 @@ ib_smp_is_response( * * SYNOPSIS */ -AL_INLINE boolean_t AL_API +static inline boolean_t OSM_API ib_smp_is_d( IN const ib_smp_t* const p_smp ) { @@ -3595,7 +3809,7 @@ ib_smp_is_d( * * SYNOPSIS */ -AL_INLINE void AL_API +static inline void OSM_API ib_smp_init_new( IN ib_smp_t* const p_smp, IN const uint8_t method, @@ -3625,14 +3839,14 @@ ib_smp_init_new( p_smp->dr_slid = dr_slid; p_smp->dr_dlid = dr_dlid; - cl_memclr( p_smp->resv1, + memset( p_smp->resv1, 0, sizeof(p_smp->resv1) + sizeof(p_smp->data) + sizeof(p_smp->initial_path) + sizeof(p_smp->return_path) ); /* copy the path */ - cl_memcpy( &p_smp->initial_path, path_out, + memcpy( &p_smp->initial_path, path_out, sizeof( p_smp->initial_path ) ); } /* @@ -3682,7 +3896,7 @@ ib_smp_init_new( * * SYNOPSIS */ -AL_INLINE void* AL_API +static inline void* OSM_API ib_smp_get_payload_ptr( IN const ib_smp_t* const p_smp ) { @@ -3776,14 +3990,14 @@ typedef struct _ib_sa_mad /**********/ #define IB_SA_MAD_HDR_SIZE (sizeof(ib_sa_mad_t) - IB_SA_DATA_SIZE) -AL_INLINE uint32_t AL_API +static inline uint32_t OSM_API ib_get_attr_size( IN const ib_net16_t attr_offset ) { return( ((uint32_t)cl_ntoh16( attr_offset )) << 3 ); } -AL_INLINE ib_net16_t AL_API +static inline ib_net16_t OSM_API ib_get_attr_offset( IN const uint32_t attr_size ) { @@ -3799,7 +4013,7 @@ ib_get_attr_offset( * * SYNOPSIS */ -AL_INLINE void* AL_API +static inline void* OSM_API ib_sa_mad_get_payload_ptr( IN const ib_sa_mad_t* const p_sa_mad ) { @@ -3836,7 +4050,7 @@ ib_sa_mad_get_payload_ptr( * * SYNOPSIS */ -AL_INLINE uint8_t AL_API +static inline uint8_t OSM_API ib_node_info_get_local_port_num( IN const ib_node_info_t* const p_ni ) { @@ -3867,7 +4081,7 @@ ib_node_info_get_local_port_num( * * SYNOPSIS */ -AL_INLINE ib_net32_t AL_API +static inline ib_net32_t OSM_API ib_node_info_get_vendor_id( IN const ib_node_info_t* const p_ni ) { @@ -3963,6 +4177,7 @@ typedef struct _ib_port_info #define IB_PORT_STATE_MASK 0x0F #define IB_PORT_LMC_MASK 0x07 +#define IB_PORT_LMC_MAX 0x07 #define IB_PORT_MPB_MASK 0xC0 #define IB_PORT_MPB_SHIFT 6 #define IB_PORT_LINK_SPEED_SHIFT 4 @@ -4015,7 +4230,7 @@ typedef struct _ib_port_info * * SYNOPSIS */ -AL_INLINE uint8_t AL_API +static inline uint8_t OSM_API ib_port_info_get_port_state( IN const ib_port_info_t* const p_pi ) { @@ -4043,7 +4258,7 @@ ib_port_info_get_port_state( * * SYNOPSIS */ -AL_INLINE void AL_API +static inline void OSM_API ib_port_info_set_port_state( IN ib_port_info_t* const p_pi, IN const uint8_t port_state ) @@ -4075,7 +4290,7 @@ ib_port_info_set_port_state( * * SYNOPSIS */ -AL_INLINE uint8_t AL_API +static inline uint8_t OSM_API ib_port_info_get_vl_cap( IN const ib_port_info_t* const p_pi) { @@ -4103,7 +4318,7 @@ ib_port_info_get_vl_cap( * * SYNOPSIS */ -OSM_INLINE uint8_t AL_API +static inline uint8_t OSM_API ib_port_info_get_init_type( IN const ib_port_info_t* const p_pi) { @@ -4131,7 +4346,7 @@ ib_port_info_get_init_type( * * SYNOPSIS */ -AL_INLINE uint8_t AL_API +static inline uint8_t OSM_API ib_port_info_get_op_vls( IN const ib_port_info_t* const p_pi) { @@ -4159,7 +4374,7 @@ ib_port_info_get_op_vls( * * SYNOPSIS */ -AL_INLINE void AL_API +static inline void OSM_API ib_port_info_set_op_vls( IN ib_port_info_t* const p_pi, IN const uint8_t op_vls ) @@ -4191,11 +4406,11 @@ ib_port_info_set_op_vls( * * SYNOPSIS */ -AL_INLINE void AL_API +static inline void OSM_API ib_port_info_set_state_no_change( IN ib_port_info_t* const p_pi ) { - ib_port_info_set_port_state( p_pi, 0 ); + ib_port_info_set_port_state( p_pi, IB_LINK_NO_CHANGE ); p_pi->state_info2 = 0; } /* @@ -4220,7 +4435,7 @@ ib_port_info_set_state_no_change( * * SYNOPSIS */ -AL_INLINE uint8_t AL_API +static inline uint8_t OSM_API ib_port_info_get_link_speed_sup( IN const ib_port_info_t* const p_pi ) { @@ -4251,7 +4466,7 @@ ib_port_info_get_link_speed_sup( * * SYNOPSIS */ -AL_INLINE void AL_API +static inline void OSM_API ib_port_info_set_link_speed_sup( IN uint8_t const speed, IN ib_port_info_t* p_pi ) @@ -4286,7 +4501,7 @@ ib_port_info_set_link_speed_sup( * * SYNOPSIS */ -OSM_INLINE uint8_t AL_API +static inline uint8_t OSM_API ib_port_info_get_port_phys_state( IN const ib_port_info_t* const p_pi ) { @@ -4317,7 +4532,7 @@ ib_port_info_get_port_phys_state( * * SYNOPSIS */ -AL_INLINE void AL_API +static inline void OSM_API ib_port_info_set_port_phys_state( IN uint8_t const phys_state, IN ib_port_info_t* p_pi ) @@ -4352,7 +4567,7 @@ ib_port_info_set_port_phys_state( * * SYNOPSIS */ -OSM_INLINE uint8_t AL_API +static inline uint8_t OSM_API ib_port_info_get_link_down_def_state( IN const ib_port_info_t* const p_pi ) { @@ -4380,7 +4595,7 @@ ib_port_info_get_link_down_def_state( * * SYNOPSIS */ -AL_INLINE void AL_API +static inline void OSM_API ib_port_info_set_link_down_def_state( IN ib_port_info_t* const p_pi, IN const uint8_t link_dwn_state ) @@ -4412,7 +4627,7 @@ ib_port_info_set_link_down_def_state( * * SYNOPSIS */ -OSM_INLINE uint8_t AL_API +static inline uint8_t OSM_API ib_port_info_get_link_speed_active( IN const ib_port_info_t* const p_pi ) { @@ -4463,8 +4678,7 @@ ib_port_info_get_link_speed_active( * * SYNOPSIS */ - -AL_INLINE uint8_t AL_API +static inline uint8_t OSM_API ib_port_info_compute_rate( IN const ib_port_info_t* const p_pi ) { @@ -4561,7 +4775,7 @@ ib_port_info_compute_rate( * * SYNOPSIS */ -AL_INLINE uint8_t AL_API +static inline uint8_t OSM_API ib_path_get_ipd( IN uint8_t local_link_width_supported, IN uint8_t path_rec_rate ) @@ -4632,7 +4846,7 @@ ib_path_get_ipd( * * SYNOPSIS */ -AL_INLINE uint8_t AL_API +static inline uint8_t OSM_API ib_port_info_get_mtu_cap( IN const ib_port_info_t* const p_pi ) { @@ -4660,7 +4874,7 @@ ib_port_info_get_mtu_cap( * * SYNOPSIS */ -AL_INLINE uint8_t AL_API +static inline uint8_t OSM_API ib_port_info_get_neighbor_mtu( IN const ib_port_info_t* const p_pi ) { @@ -4688,7 +4902,7 @@ ib_port_info_get_neighbor_mtu( * * SYNOPSIS */ -AL_INLINE void AL_API +static inline void OSM_API ib_port_info_set_neighbor_mtu( IN ib_port_info_t* const p_pi, IN const uint8_t mtu ) @@ -4722,7 +4936,7 @@ ib_port_info_set_neighbor_mtu( * * SYNOPSIS */ -OSM_INLINE uint8_t AL_API +static inline uint8_t OSM_API ib_port_info_get_master_smsl( IN const ib_port_info_t* const p_pi ) { @@ -4750,7 +4964,7 @@ ib_port_info_get_master_smsl( * * SYNOPSIS */ -AL_INLINE void AL_API +static inline void OSM_API ib_port_info_set_master_smsl( IN ib_port_info_t* const p_pi, IN const uint8_t smsl ) @@ -4782,7 +4996,7 @@ ib_port_info_set_master_smsl( * * SYNOPSIS */ -AL_INLINE void AL_API +static inline void OSM_API ib_port_info_set_timeout( IN ib_port_info_t* const p_pi, IN const uint8_t timeout ) @@ -4817,7 +5031,7 @@ ib_port_info_set_timeout( * * SYNOPSIS */ -OSM_INLINE void AL_API +static inline void OSM_API ib_port_info_set_client_rereg( IN ib_port_info_t* const p_pi, IN const uint8_t client_rereg ) @@ -4852,7 +5066,7 @@ ib_port_info_set_client_rereg( * * SYNOPSIS */ -OSM_INLINE uint8_t AL_API +static inline uint8_t OSM_API ib_port_info_get_timeout( IN ib_port_info_t const* p_pi ) { @@ -4880,7 +5094,7 @@ ib_port_info_get_timeout( * * SYNOPSIS */ -OSM_INLINE uint8_t AL_API +static inline uint8_t OSM_API ib_port_info_get_client_rereg( IN ib_port_info_t const* p_pi ) { @@ -4909,7 +5123,7 @@ ib_port_info_get_client_rereg( * * SYNOPSIS */ -OSM_INLINE void AL_API +static inline void OSM_API ib_port_info_set_hoq_lifetime( IN ib_port_info_t* const p_pi, IN const uint8_t hoq_life ) @@ -4943,7 +5157,7 @@ ib_port_info_set_hoq_lifetime( * * SYNOPSIS */ -OSM_INLINE uint8_t AL_API +static inline uint8_t OSM_API ib_port_info_get_hoq_lifetime( IN const ib_port_info_t* const p_pi ) { @@ -4973,7 +5187,7 @@ ib_port_info_get_hoq_lifetime( * * SYNOPSIS */ -OSM_INLINE void AL_API +static inline void OSM_API ib_port_info_set_vl_stall_count( IN ib_port_info_t* const p_pi, IN const uint8_t vl_stall_count ) @@ -5007,7 +5221,7 @@ ib_port_info_set_vl_stall_count( * * SYNOPSIS */ -OSM_INLINE uint8_t AL_API +static inline uint8_t OSM_API ib_port_info_get_vl_stall_count( IN const ib_port_info_t* const p_pi ) { @@ -5036,7 +5250,7 @@ ib_port_info_get_vl_stall_count( * * SYNOPSIS */ -AL_INLINE uint8_t AL_API +static inline uint8_t OSM_API ib_port_info_get_lmc( IN const ib_port_info_t* const p_pi ) { @@ -5064,12 +5278,12 @@ ib_port_info_get_lmc( * * SYNOPSIS */ -AL_INLINE void AL_API +static inline void OSM_API ib_port_info_set_lmc( IN ib_port_info_t* const p_pi, IN const uint8_t lmc ) { - CL_ASSERT( lmc <= 0x7 ); + CL_ASSERT( lmc <= IB_PORT_LMC_MAX ); p_pi->mkey_lmc = (uint8_t)((p_pi->mkey_lmc & 0xF8) | lmc); } /* @@ -5097,7 +5311,7 @@ ib_port_info_set_lmc( * * SYNOPSIS */ -OSM_INLINE uint8_t AL_API +static inline uint8_t OSM_API ib_port_info_get_link_speed_enabled( IN const ib_port_info_t* const p_pi ) { @@ -5125,7 +5339,7 @@ ib_port_info_get_link_speed_enabled( * * SYNOPSIS */ -AL_INLINE void AL_API +static inline void OSM_API ib_port_info_set_link_speed_enabled( IN ib_port_info_t* const p_pi, IN const uint8_t link_speed_enabled ) @@ -5157,7 +5371,7 @@ ib_port_info_set_link_speed_enabled( * * SYNOPSIS */ -AL_INLINE uint8_t AL_API +static inline uint8_t OSM_API ib_port_info_get_mpb( IN const ib_port_info_t* const p_pi ) { @@ -5186,7 +5400,7 @@ ib_port_info_get_mpb( * * SYNOPSIS */ -AL_INLINE void AL_API +static inline void OSM_API ib_port_info_set_mpb( IN ib_port_info_t* p_pi, IN uint8_t mpb ) @@ -5218,7 +5432,7 @@ ib_port_info_set_mpb( * * SYNOPSIS */ -OSM_INLINE uint8_t AL_API +static inline uint8_t OSM_API ib_port_info_get_local_phy_err_thd( IN const ib_port_info_t* const p_pi ) { @@ -5246,7 +5460,7 @@ ib_port_info_get_local_phy_err_thd( * * SYNOPSIS */ -OSM_INLINE uint8_t AL_API +static inline uint8_t OSM_API ib_port_info_get_overrun_err_thd( IN const ib_port_info_t* const p_pi ) { @@ -5274,7 +5488,7 @@ ib_port_info_get_overrun_err_thd( * * SYNOPSIS */ -OSM_INLINE void AL_API +static inline void OSM_API ib_port_info_set_phy_and_overrun_err_thd( IN ib_port_info_t* const p_pi, IN uint8_t phy_threshold, @@ -5362,7 +5576,7 @@ typedef struct _ib_sminfo_record * ib_lft_record_t * * DESCRIPTION -* IBA defined LinearForwardingTable. (14.2.5.6) +* IBA defined LinearForwardingTableRecord (15.2.5.6) * * SYNOPSIS */ @@ -5377,6 +5591,26 @@ typedef struct _ib_lft_record #include /************/ +/****s* IBA Base: Types/ib_mft_record_t +* NAME +* ib_mft_record_t +* +* DESCRIPTION +* IBA defined MulticastForwardingTableRecord (15.2.5.8) +* +* SYNOPSIS +*/ +#include +typedef struct _ib_mft_record +{ + ib_net16_t lid; + ib_net16_t position_block_num; + uint32_t resv0; + ib_net16_t mft[IB_MCAST_BLOCK_SIZE]; +} PACK_SUFFIX ib_mft_record_t; +#include +/************/ + /****s* IBA Base: Types/ib_switch_info_t * NAME * ib_switch_info_t @@ -5427,7 +5661,7 @@ typedef struct _ib_switch_info_record * * SYNOPSIS */ -AL_INLINE boolean_t AL_API +static inline boolean_t OSM_API ib_switch_info_get_state_change( IN const ib_switch_info_t* const p_si ) { @@ -5455,7 +5689,7 @@ ib_switch_info_get_state_change( * * SYNOPSIS */ -AL_INLINE void AL_API +static inline void OSM_API ib_switch_info_clear_state_change( IN ib_switch_info_t* const p_si ) { @@ -5474,10 +5708,9 @@ ib_switch_info_clear_state_change( * SEE ALSO *********/ - -/****f* IBA Base: Types/ib_switch_info_is_enhanced_port_0 +/****f* IBA Base: Types/ib_switch_info_is_enhanced_port0 * NAME -* ib_switch_info_is_enhanced_port_0 +* ib_switch_info_is_enhanced_port0 * * DESCRIPTION * Returns TRUE if the enhancedPort0 bit is on (meaning the switch @@ -5486,9 +5719,9 @@ ib_switch_info_clear_state_change( * * SYNOPSIS */ -OSM_INLINE boolean_t AL_API -ib_switch_info_is_enhanced_port_0( - IN const ib_switch_info_t* const p_si ) +static inline boolean_t OSM_API +ib_switch_info_is_enhanced_port0( + IN const ib_switch_info_t* const p_si ) { return( (p_si->flags & 0x08) == 0x08 ); } @@ -5536,6 +5769,316 @@ typedef struct _ib_guidinfo_record } PACK_SUFFIX ib_guidinfo_record_t; #include +#define IB_MULTIPATH_MAX_GIDS 11 /* Support max that can fit into first MAD (for now) */ + +#include +typedef struct _ib_multipath_rec_t +{ + ib_net32_t hop_flow_raw; + uint8_t tclass; + uint8_t num_path; + ib_net16_t pkey; + uint8_t resv0; + uint8_t sl; + uint8_t mtu; + uint8_t rate; + uint8_t pkt_life; + uint8_t resv1; + uint8_t independence; /* formerly resv2 */ + uint8_t sgid_count; + uint8_t dgid_count; + uint8_t resv3[7]; + ib_gid_t gids[IB_MULTIPATH_MAX_GIDS]; +} PACK_SUFFIX ib_multipath_rec_t; +#include +/* +* FIELDS +* hop_flow_raw +* Global routing parameters: hop count, flow label and raw bit. +* +* tclass +* Another global routing parameter. +* +* num_path +* Reversible path - 1 bit to say if path is reversible. +* num_path [6:0] In queries, maximum number of paths to return. +* In responses, undefined. +* +* pkey +* Partition key (P_Key) to use on this path. +* +* sl +* Service level to use on this path. +* +* mtu +* MTU and MTU selector fields to use on this path +* rate +* Rate and rate selector fields to use on this path. +* +* pkt_life +* Packet lifetime +* +* preference +* Indicates the relative merit of this path versus other path +* records returned from the SA. Lower numbers are better. +* +* SEE ALSO +*********/ + +/****f* IBA Base: Types/ib_multipath_rec_num_path +* NAME +* ib_multipath_rec_num_path +* +* DESCRIPTION +* Get max number of paths to return. +* +* SYNOPSIS +*/ +static inline uint8_t OSM_API +ib_multipath_rec_num_path( + IN const ib_multipath_rec_t* const p_rec ) +{ + return( p_rec->num_path &0x7F ); +} +/* +* PARAMETERS +* p_rec +* [in] Pointer to the multipath record object. +* +* RETURN VALUES +* Maximum number of paths to return for each unique SGID_DGID combination. +* +* NOTES +* +* SEE ALSO +* ib_multipath_rec_t +*********/ + +/****f* IBA Base: Types/ib_multipath_rec_sl +* NAME +* ib_multipath_rec_sl +* +* DESCRIPTION +* Get multipath service level. +* +* SYNOPSIS +*/ +static inline uint8_t OSM_API +ib_multipath_rec_sl( + IN const ib_multipath_rec_t* const p_rec ) +{ + return( (uint8_t)((cl_ntoh16( p_rec->sl )) & 0xF) ); +} +/* +* PARAMETERS +* p_rec +* [in] Pointer to the multipath record object. +* +* RETURN VALUES +* SL. +* +* NOTES +* +* SEE ALSO +* ib_multipath_rec_t +*********/ + +/****f* IBA Base: Types/ib_multipath_rec_mtu +* NAME +* ib_multipath_rec_mtu +* +* DESCRIPTION +* Get encoded path MTU. +* +* SYNOPSIS +*/ +static inline uint8_t OSM_API +ib_multipath_rec_mtu( + IN const ib_multipath_rec_t* const p_rec ) +{ + return( (uint8_t)(p_rec->mtu & IB_MULTIPATH_REC_BASE_MASK) ); +} +/* +* PARAMETERS +* p_rec +* [in] Pointer to the multipath record object. +* +* RETURN VALUES +* Encoded path MTU. +* 1: 256 +* 2: 512 +* 3: 1024 +* 4: 2048 +* 5: 4096 +* others: reserved +* +* NOTES +* +* SEE ALSO +* ib_multipath_rec_t +*********/ + +/****f* IBA Base: Types/ib_multipath_rec_mtu_sel +* NAME +* ib_multipath_rec_mtu_sel +* +* DESCRIPTION +* Get encoded multipath MTU selector. +* +* SYNOPSIS +*/ +static inline uint8_t OSM_API +ib_multipath_rec_mtu_sel( + IN const ib_multipath_rec_t* const p_rec ) +{ + return( (uint8_t)((p_rec->mtu & IB_MULTIPATH_REC_SELECTOR_MASK) >> 6) ); +} +/* +* PARAMETERS +* p_rec +* [in] Pointer to the multipath record object. +* +* RETURN VALUES +* Encoded path MTU selector value (for queries). +* 0: greater than MTU specified +* 1: less than MTU specified +* 2: exactly the MTU specified +* 3: largest MTU available +* +* NOTES +* +* SEE ALSO +* ib_multipath_rec_t +*********/ + +/****f* IBA Base: Types/ib_multipath_rec_rate +* NAME +* ib_multipath_rec_rate +* +* DESCRIPTION +* Get encoded multipath rate. +* +* SYNOPSIS +*/ +static inline uint8_t OSM_API +ib_multipath_rec_rate( + IN const ib_multipath_rec_t* const p_rec ) +{ + return( (uint8_t)(p_rec->rate & IB_MULTIPATH_REC_BASE_MASK) ); +} +/* +* PARAMETERS +* p_rec +* [in] Pointer to the multipath record object. +* +* RETURN VALUES +* Encoded multipath rate. +* 2: 2.5 Gb/sec. +* 3: 10 Gb/sec. +* 4: 30 Gb/sec. +* others: reserved +* +* NOTES +* +* SEE ALSO +* ib_multipath_rec_t +*********/ + +/****f* IBA Base: Types/ib_multipath_rec_rate_sel +* NAME +* ib_multipath_rec_rate_sel +* +* DESCRIPTION +* Get encoded multipath rate selector. +* +* SYNOPSIS +*/ +static inline uint8_t OSM_API +ib_multipath_rec_rate_sel( + IN const ib_multipath_rec_t* const p_rec ) +{ + return( (uint8_t)((p_rec->rate & IB_MULTIPATH_REC_SELECTOR_MASK) >> 6) ); +} +/* +* PARAMETERS +* p_rec +* [in] Pointer to the multipath record object. +* +* RETURN VALUES +* Encoded path rate selector value (for queries). +* 0: greater than rate specified +* 1: less than rate specified +* 2: exactly the rate specified +* 3: largest rate available +* +* NOTES +* +* SEE ALSO +* ib_multipath_rec_t +*********/ + +/****f* IBA Base: Types/ib_multipath_rec_pkt_life +* NAME +* ib_multipath_rec_pkt_life +* +* DESCRIPTION +* Get encoded multipath pkt_life. +* +* SYNOPSIS +*/ +static inline uint8_t OSM_API +ib_multipath_rec_pkt_life( + IN const ib_multipath_rec_t* const p_rec ) +{ + return( (uint8_t)(p_rec->pkt_life & IB_MULTIPATH_REC_BASE_MASK) ); +} +/* +* PARAMETERS +* p_rec +* [in] Pointer to the multipath record object. +* +* RETURN VALUES +* Encoded multipath pkt_life = 4.096 µsec * 2 ** PacketLifeTime. +* +* NOTES +* +* SEE ALSO +* ib_multipath_rec_t +*********/ + +/****f* IBA Base: Types/ib_multipath_rec_pkt_life_sel +* NAME +* ib_multipath_rec_pkt_life_sel +* +* DESCRIPTION +* Get encoded multipath pkt_lifetime selector. +* +* SYNOPSIS +*/ +static inline uint8_t OSM_API +ib_multipath_rec_pkt_life_sel( + IN const ib_multipath_rec_t* const p_rec ) +{ + return( (uint8_t)((p_rec->pkt_life & IB_MULTIPATH_REC_SELECTOR_MASK) >> 6 )); +} +/* +* PARAMETERS +* p_rec +* [in] Pointer to the multipath record object. +* +* RETURN VALUES +* Encoded path pkt_lifetime selector value (for queries). +* 0: greater than rate specified +* 1: less than rate specified +* 2: exactly the rate specified +* 3: smallest packet lifetime available +* +* NOTES +* +* SEE ALSO +* ib_multipath_rec_t +*********/ + #define IB_NUM_PKEY_ELEMENTS_IN_BLOCK 32 /****s* IBA Base: Types/ib_pkey_table_t * NAME @@ -5629,7 +6172,7 @@ typedef struct _ib_slvl_table_record * * SYNOPSIS */ -AL_INLINE void AL_API +static inline void OSM_API ib_slvl_table_set( IN ib_slvl_table_t* p_slvl_tbl, IN uint8_t sl_index, @@ -5679,7 +6222,7 @@ ib_slvl_table_set( * * SYNOPSIS */ -OSM_INLINE uint8_t AL_API +static inline uint8_t OSM_API ib_slvl_table_get( IN const ib_slvl_table_t* p_slvl_tbl, IN uint8_t sl_index ) @@ -5797,7 +6340,7 @@ typedef struct _ib_grh * * SYNOPSIS */ -AL_INLINE void AL_API +static inline void OSM_API ib_grh_get_ver_class_flow( IN const ib_net32_t ver_class_flow, OUT uint8_t* const p_ver, @@ -5849,7 +6392,7 @@ ib_grh_get_ver_class_flow( * * SYNOPSIS */ -AL_INLINE ib_net32_t AL_API +static inline ib_net32_t OSM_API ib_grh_set_ver_class_flow( IN const uint8_t ver, IN const uint8_t tclass, @@ -5909,10 +6452,7 @@ typedef struct _ib_member_rec uint8_t pkt_life; ib_net32_t sl_flow_hop; uint8_t scope_state; -/* uint8_t proxy_join:1; */ -/* TODO : Under DDK got C4214 which note that using bitfield can cause problems - in porting to other compilers */ - uint8_t proxy_join; + uint8_t proxy_join:1; uint8_t reserved[2]; uint8_t pad[4]; @@ -5968,27 +6508,26 @@ typedef struct _ib_member_rec * * SYNOPSIS */ -AL_INLINE void AL_API +static inline void OSM_API ib_member_get_sl_flow_hop( IN const ib_net32_t sl_flow_hop, OUT uint8_t* const p_sl, OUT uint32_t* const p_flow_lbl, OUT uint8_t* const p_hop ) { - ib_net32_t tmp_sl_flow_hop; + uint32_t tmp; - if (p_sl) - *p_sl = (uint8_t)(sl_flow_hop & 0x0f); - - tmp_sl_flow_hop = sl_flow_hop >> 4; + tmp = cl_ntoh32(sl_flow_hop); + if (p_hop) + *p_hop = (uint8_t)tmp; + tmp >>= 8; if (p_flow_lbl) - *p_flow_lbl = (uint32_t)(tmp_sl_flow_hop & 0xfffff); - - tmp_sl_flow_hop = tmp_sl_flow_hop >> 20; + *p_flow_lbl = (uint32_t)(tmp & 0xfffff); + tmp >>= 20; - if (p_hop) - *p_hop = (uint8_t)(tmp_sl_flow_hop & 0xff); + if (p_sl) + *p_sl = (uint8_t)tmp; } /* * PARAMETERS @@ -6020,20 +6559,16 @@ ib_member_get_sl_flow_hop( * * SYNOPSIS */ -AL_INLINE ib_net32_t AL_API +static inline ib_net32_t OSM_API ib_member_set_sl_flow_hop( IN const uint8_t sl, IN const uint32_t flow_label, IN const uint8_t hop_limit ) { - ib_net32_t sl_flow_hop; + uint32_t tmp; - sl_flow_hop = hop_limit; - sl_flow_hop = sl_flow_hop << 20; - sl_flow_hop = sl_flow_hop | flow_label; - sl_flow_hop = sl_flow_hop << 2; - sl_flow_hop = sl_flow_hop | sl; - return (sl_flow_hop); + tmp = (sl << 28) | ((flow_label & 0xfffff) << 8) | hop_limit; + return cl_hton32(tmp); } /* * PARAMETERS @@ -6065,7 +6600,7 @@ ib_member_set_sl_flow_hop( * * SYNOPSIS */ -AL_INLINE void AL_API +static inline void OSM_API ib_member_get_scope_state( IN const uint8_t scope_state, OUT uint8_t* const p_scope, @@ -6109,7 +6644,7 @@ ib_member_get_scope_state( * * SYNOPSIS */ -AL_INLINE uint8_t AL_API +static inline uint8_t OSM_API ib_member_set_scope_state( IN const uint8_t scope, IN const uint8_t state ) @@ -6148,7 +6683,7 @@ ib_member_set_scope_state( * * SYNOPSIS */ -AL_INLINE void AL_API +static inline void OSM_API ib_member_set_join_state( IN OUT ib_member_rec_t *p_mc_rec, IN const uint8_t state ) @@ -6311,7 +6846,7 @@ typedef struct _ib_mad_notice_attr // Total Size calc Accumulated * * SYNOPSIS */ -OSM_INLINE boolean_t AL_API +static inline boolean_t OSM_API ib_notice_is_generic( IN const ib_mad_notice_attr_t *p_ntc ) { @@ -6338,7 +6873,7 @@ ib_notice_is_generic( * * SYNOPSIS */ -AL_INLINE uint8_t AL_API +static inline uint8_t OSM_API ib_notice_get_type( IN const ib_mad_notice_attr_t *p_ntc ) { @@ -6365,7 +6900,7 @@ ib_notice_get_type( * * SYNOPSIS */ -AL_INLINE ib_net32_t AL_API +static inline ib_net32_t OSM_API ib_notice_get_prod_type( IN const ib_mad_notice_attr_t *p_ntc ) { @@ -6396,7 +6931,7 @@ ib_notice_get_prod_type( * * SYNOPSIS */ -AL_INLINE void AL_API +static inline void OSM_API ib_notice_set_prod_type( IN ib_mad_notice_attr_t *p_ntc, IN ib_net32_t prod_type_val ) @@ -6420,6 +6955,40 @@ ib_notice_set_prod_type( * ib_mad_notice_attr_t *********/ +/****f* IBA Base: Types/ib_notice_set_prod_type_ho +* NAME +* ib_notice_set_prod_type_ho +* +* DESCRIPTION +* Set the notice Producer Type of Generic Notice given Host Order +* +* SYNOPSIS +*/ +static inline void OSM_API +ib_notice_set_prod_type_ho( + IN ib_mad_notice_attr_t *p_ntc, + IN uint32_t prod_type_val_ho ) +{ + p_ntc->g_or_v.generic.prod_type_lsb = + cl_hton16( (uint16_t)(prod_type_val_ho & 0x0000ffff) ); + p_ntc->g_or_v.generic.prod_type_msb = + (uint8_t)( (prod_type_val_ho & 0x00ff0000) >> 16); +} +/* +* PARAMETERS +* p_ntc +* [in] Pointer to the notice MAD attribute +* +* prod_type +* [in] The producer Type code in host order +* +* RETURN VALUES +* None +* +* SEE ALSO +* ib_mad_notice_attr_t +*********/ + /****f* IBA Base: Types/ib_notice_get_vend_id * NAME * ib_notice_get_vend_id @@ -6429,7 +6998,7 @@ ib_notice_set_prod_type( * * SYNOPSIS */ -AL_INLINE ib_net32_t AL_API +static inline ib_net32_t OSM_API ib_notice_get_vend_id( IN const ib_mad_notice_attr_t *p_ntc ) { @@ -6460,7 +7029,7 @@ ib_notice_get_vend_id( * * SYNOPSIS */ -AL_INLINE void AL_API +static inline void OSM_API ib_notice_set_vend_id( IN ib_mad_notice_attr_t *p_ntc, IN ib_net32_t vend_id ) @@ -6474,8 +7043,42 @@ ib_notice_set_vend_id( * p_ntc * [in] Pointer to the notice MAD attribute * -* vend_id -* [in] The producer Type code +* vend_id +* [in] The producer Type code +* +* RETURN VALUES +* None +* +* SEE ALSO +* ib_mad_notice_attr_t +*********/ + +/****f* IBA Base: Types/ib_notice_set_vend_id_ho +* NAME +* ib_notice_set_vend_id_ho +* +* DESCRIPTION +* Set the notice Producer Type of Generic Notice given a host order value +* +* SYNOPSIS +*/ +static inline void OSM_API +ib_notice_set_vend_id_ho( + IN ib_mad_notice_attr_t *p_ntc, + IN uint32_t vend_id_ho ) +{ + p_ntc->g_or_v.vend.vend_id_lsb = + cl_hton16((uint16_t)(vend_id_ho & 0x0000ffff)); + p_ntc->g_or_v.vend.vend_id_msb = + (uint8_t)((vend_id_ho & 0x00ff0000) >> 16); +} +/* +* PARAMETERS +* p_ntc +* [in] Pointer to the notice MAD attribute +* +* vend_id_ho +* [in] The producer Type code in host order * * RETURN VALUES * None @@ -6528,7 +7131,7 @@ typedef struct _ib_inform_info * * SYNOPSIS */ -OSM_INLINE void AL_API +static inline void OSM_API ib_inform_info_get_qpn_resp_time( IN const ib_net32_t qpn_resp_time_val, OUT ib_net32_t* const p_qpn, @@ -6569,7 +7172,7 @@ ib_inform_info_get_qpn_resp_time( * * SYNOPSIS */ -OSM_INLINE void AL_API +static inline void OSM_API ib_inform_info_set_qpn( IN ib_inform_info_t *p_ii, IN ib_net32_t const qpn) @@ -6600,7 +7203,7 @@ ib_inform_info_set_qpn( * * SYNOPSIS */ -OSM_INLINE ib_net32_t AL_API +static inline ib_net32_t OSM_API ib_inform_info_get_node_type( IN const ib_inform_info_t *p_inf) { @@ -6633,7 +7236,7 @@ ib_inform_info_get_node_type( * * SYNOPSIS */ -OSM_INLINE ib_net32_t AL_API +static inline ib_net32_t OSM_API ib_inform_info_get_vend_id( IN const ib_inform_info_t *p_inf) { @@ -6673,7 +7276,7 @@ typedef struct _ib_inform_info_record ib_net16_t subscriber_enum; uint8_t reserved[6]; ib_inform_info_t inform_info; - + uint8_t pad[4]; } PACK_SUFFIX ib_inform_info_record_t; #include @@ -6784,7 +7387,7 @@ typedef struct _ib_iou_info * * SYNOPSIS */ -AL_INLINE uint8_t AL_API +static inline uint8_t OSM_API ib_iou_info_diag_dev_id( IN const ib_iou_info_t* const p_iou_info ) { @@ -6813,7 +7416,7 @@ ib_iou_info_diag_dev_id( * * SYNOPSIS */ -AL_INLINE uint8_t AL_API +static inline uint8_t OSM_API ib_iou_info_option_rom( IN const ib_iou_info_t* const p_iou_info ) { @@ -6842,7 +7445,7 @@ ib_iou_info_option_rom( * * SYNOPSIS */ -AL_INLINE uint8_t AL_API +static inline uint8_t OSM_API ioc_at_slot( IN const ib_iou_info_t* const p_iou_info, IN uint8_t slot ) @@ -6988,7 +7591,7 @@ typedef struct _ib_ioc_profile * ib_dm_mad_t *********/ -AL_INLINE uint32_t AL_API +static inline uint32_t OSM_API ib_ioc_profile_get_vend_id( IN const ib_ioc_profile_t* const p_ioc_profile ) { @@ -6996,7 +7599,7 @@ ib_ioc_profile_get_vend_id( } -AL_INLINE void AL_API +static inline void OSM_API ib_ioc_profile_set_vend_id( IN ib_ioc_profile_t* const p_ioc_profile, IN const uint32_t vend_id ) @@ -7061,7 +7664,7 @@ typedef struct _ib_svc_entries * ib_dm_mad_t, ib_svc_entry_t *********/ -AL_INLINE void AL_API +static inline void OSM_API ib_dm_get_slot_lo_hi( IN const ib_net32_t slot_lo_hi, OUT uint8_t *const p_slot, @@ -7260,7 +7863,6 @@ typedef struct _ib_rdd* __ptr64 ib_rdd_handle_t; typedef struct _ib_mr* __ptr64 ib_mr_handle_t; typedef struct _ib_mw* __ptr64 ib_mw_handle_t; typedef struct _ib_qp* __ptr64 ib_qp_handle_t; -typedef struct _ib_srq* __ptr64 ib_srq_handle_t; typedef struct _ib_eec* __ptr64 ib_eec_handle_t; typedef struct _ib_cq* __ptr64 ib_cq_handle_t; typedef struct _ib_av* __ptr64 ib_av_handle_t; @@ -7302,6 +7904,7 @@ typedef enum _ib_api_status_t IB_OVERFLOW, IB_MAX_MCAST_QPS_REACHED, IB_INVALID_QP_STATE, + IB_INVALID_EEC_STATE, IB_INVALID_APM_STATE, IB_INVALID_PORT_STATE, IB_INVALID_STATE, @@ -7312,7 +7915,6 @@ typedef enum _ib_api_status_t IB_INVALID_MAX_WRS, IB_INVALID_MAX_SGE, IB_INVALID_CQ_SIZE, - IB_INVALID_SRQ_SIZE, IB_INVALID_SERVICE_TYPE, IB_INVALID_GID, IB_INVALID_LID, @@ -7320,33 +7922,30 @@ typedef enum _ib_api_status_t IB_INVALID_CA_HANDLE, IB_INVALID_AV_HANDLE, IB_INVALID_CQ_HANDLE, + IB_INVALID_EEC_HANDLE, IB_INVALID_QP_HANDLE, - IB_INVALID_SRQ_HANDLE, IB_INVALID_PD_HANDLE, IB_INVALID_MR_HANDLE, - IB_INVALID_FMR_HANDLE, IB_INVALID_MW_HANDLE, + IB_INVALID_RDD_HANDLE, IB_INVALID_MCAST_HANDLE, IB_INVALID_CALLBACK, - IB_INVALID_AL_HANDLE, /* InfiniBand Access Layer */ - IB_INVALID_HANDLE, /* InfiniBand Access Layer */ - IB_ERROR, /* InfiniBand Access Layer */ - IB_REMOTE_ERROR, /* Infiniband Access Layer */ - IB_VERBS_PROCESSING_DONE, /* See Notes above */ + IB_INVALID_AL_HANDLE, /* InfiniBand Access Layer */ + IB_INVALID_HANDLE, /* InfiniBand Access Layer */ + IB_ERROR, /* InfiniBand Access Layer */ + IB_REMOTE_ERROR, /* Infiniband Access Layer */ + IB_VERBS_PROCESSING_DONE, /* See Notes above */ IB_INVALID_WR_TYPE, IB_QP_IN_TIMEWAIT, IB_EE_IN_TIMEWAIT, IB_INVALID_PORT, IB_NOT_DONE, - IB_INVALID_INDEX, - IB_NO_MATCH, - IB_PENDING, - IB_UNKNOWN_ERROR /* ALWAYS LAST ENUM VALUE! */ + IB_UNKNOWN_ERROR /* ALWAYS LAST ENUM VALUE! */ } ib_api_status_t; /*****/ -AL_EXPORT const char* ib_error_str[]; +OSM_EXPORT const char* ib_error_str[]; /****f* IBA Base: Types/ib_get_err_str * NAME @@ -7357,7 +7956,7 @@ AL_EXPORT const char* ib_error_str[]; * * SYNOPSIS */ -AL_INLINE const char* AL_API +static inline const char* OSM_API ib_get_err_str( IN ib_api_status_t status ) { @@ -7533,7 +8132,7 @@ typedef enum _ib_async_event_t * *****/ -AL_EXPORT const char* ib_async_event_str[]; +OSM_EXPORT const char* ib_async_event_str[]; /****f* IBA Base: Types/ib_get_async_event_str * NAME @@ -7544,7 +8143,7 @@ AL_EXPORT const char* ib_async_event_str[]; * * SYNOPSIS */ -AL_INLINE const char* AL_API +static inline const char* OSM_API ib_get_async_event_str( IN ib_async_event_t event ) { @@ -9130,7 +9729,7 @@ typedef enum _ib_wc_status_t * The completed work request was canceled by the user. *****/ -AL_EXPORT const char* ib_wc_status_str[]; +OSM_EXPORT const char* ib_wc_status_str[]; /****f* IBA Base: Types/ib_get_wc_status_str * NAME @@ -9141,7 +9740,7 @@ AL_EXPORT const char* ib_wc_status_str[]; * * SYNOPSIS */ -AL_INLINE const char* AL_API +static inline const char* OSM_API ib_get_wc_status_str( IN ib_wc_status_t wc_status ) { diff --git a/trunk/ulp/opensm/user/include/iba/ib_types_extended.h b/trunk/ulp/opensm/user/include/iba/ib_types_extended.h index 46e446f6..22a20dbe 100644 --- a/trunk/ulp/opensm/user/include/iba/ib_types_extended.h +++ b/trunk/ulp/opensm/user/include/iba/ib_types_extended.h @@ -79,7 +79,7 @@ #define IB_PATH_RECORD_RATE_80_GBS 9 #define IB_PATH_RECORD_RATE_120_GBS 10 - +typedef struct _ib_srq* __ptr64 ib_srq_handle_t; /* * The following definitions are shared between the Access Layer and VPD diff --git a/trunk/ulp/opensm/user/include/opensm/osm_attrib_req.h b/trunk/ulp/opensm/user/include/opensm/osm_attrib_req.h index c532c589..7344b4a2 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_attrib_req.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_attrib_req.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -75,6 +75,7 @@ BEGIN_C_DECLS * Steve King, Intel * *********/ + /****s* OpenSM: Attribute Request/osm_attrib_req_t * NAME * osm_attrib_req_t @@ -115,3 +116,4 @@ typedef struct _osm_attrib_req END_C_DECLS #endif /* _OSM_ATTRIB_REQ_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_base.h b/trunk/ulp/opensm/user/include/opensm/osm_base.h index f06331e6..cc054b3c 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_base.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_base.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -77,6 +77,7 @@ BEGIN_C_DECLS * Steve King, Intel * *********/ + /****h* OpenSM/Base * NAME * Base @@ -93,6 +94,7 @@ BEGIN_C_DECLS * Steve King, Intel * *********/ + /****s* OpenSM: Base/OSM_DEFAULT_M_KEY * NAME * OSM_DEFAULT_M_KEY @@ -173,16 +175,15 @@ BEGIN_C_DECLS * OSM_DEFAULT_TMP_DIR * * DESCRIPTION -* Specifies the default temporary directory for the log file, subnet.lst -* and the other log files (with the exception of osm.log for Linux being -* in /var/log). +* Specifies the default temporary directory for the log file, +* osm-subnet.lst, and other log files. * * SYNOPSIS */ #ifdef __WIN__ #define OSM_DEFAULT_TMP_DIR GetOsmTempPath() #else -#define OSM_DEFAULT_TMP_DIR "/tmp/" +#define OSM_DEFAULT_TMP_DIR "/var/log/" #endif /***********/ @@ -219,6 +220,22 @@ BEGIN_C_DECLS #endif /***********/ +/****d* OpenSM: Base/OSM_DEFAULT_PARTITION_CONFIG_FILE +* NAME +* OSM_DEFAULT_PARTITION_CONFIG_FILE +* +* DESCRIPTION +* Specifies the default partition config file name +* +* SYNOPSIS +*/ +#ifdef __WIN__ +#define OSM_DEFAULT_PARTITION_CONFIG_FILE strcat(GetOsmCachePath(), "osm-partitions.conf") +#else +#define OSM_DEFAULT_PARTITION_CONFIG_FILE "/etc/osm-partitions.conf" +#endif +/***********/ + /****d* OpenSM: Base/OSM_DEFAULT_SWEEP_INTERVAL_SECS * NAME * OSM_DEFAULT_SWEEP_INTERVAL_SECS @@ -230,6 +247,7 @@ BEGIN_C_DECLS */ #define OSM_DEFAULT_SWEEP_INTERVAL_SECS 10 /***********/ + /****d* OpenSM: Base/OSM_DEFAULT_TRANS_TIMEOUT_MILLISEC * NAME * OSM_DEFAULT_TRANS_TIMEOUT_MILLISEC @@ -299,15 +317,30 @@ BEGIN_C_DECLS #define OSM_DEFAULT_LEAF_HEAD_OF_QUEUE_LIFE 0xC /***********/ +/****d* OpenSM: Base/OSM_DEFAULT_VL_STALL_COUNT +* NAME +* OSM_DEFAULT_LEAF_VL_COUNT +* +* DESCRIPTION +* Sets the number of consecutive head of queue life time drops that +* puts the VL into stalled state. In stalled state, the port is supposed +* to drop everything for 8*(head of queue lifetime) +* +* SYNOPSIS +*/ +#define OSM_DEFAULT_VL_STALL_COUNT 0x7 +/***********/ + /****d* OpenSM: Base/OSM_DEFAULT_LEAF_VL_STALL_COUNT * NAME * OSM_DEFAULT_LEAF_VL_STALL_COUNT * * DESCRIPTION -* Sets the number of contiguous head of queue life time drops that -* puts the VL into stalled state. In stalled state the port supposed to -* drop everything for 8*(head of queue lifetime) -* We use here the value of 1 - so any drop due to HOQ means stalling the VL +* Sets the number of consecutive head of queue life time drops that +* puts the VL into stalled state. In stalled state, the port is supposed +* to drop everything for 8*(head of queue lifetime). This value is for +* switch ports driving a CA port. +* We use the value of 1 here - so any drop due to HOQ means stalling the VL * * SYNOPSIS */ @@ -333,7 +366,7 @@ BEGIN_C_DECLS * OSM_DEFAULT_UNHEALTHY_TIMEOUT * * DESCRIPTION -* Specifies the default timeout for setting port as un-healthy. +* Specifies the default timeout for setting port as unhealthy. * timeout time = 60000000us * We use here ~60sec. * @@ -434,11 +467,11 @@ BEGIN_C_DECLS * * DESCRIPTION * Specifies the number of polling retries before the SM goes back -* to DISCOVERY stage. So the total time for handoff is 3min. +* to DISCOVERY stage. So the default total time for handoff is 40 sec. * * SYNOPSIS */ -#define OSM_SM_DEFAULT_POLLING_RETRY_NUMBER 18 +#define OSM_SM_DEFAULT_POLLING_RETRY_NUMBER 4 /**********/ /****d* OpenSM: Base/OSM_NO_PATH @@ -474,20 +507,44 @@ typedef enum _osm_thread_state /***********/ /* - * OSM_CAP ARE C15-0.1.7 Table 152 + * OSM_CAP are from Table 117 and C15-0.1.7 Table 186 */ +/****d* OpenSM: Base/OSM_CAP_IS_TRAP_SUP +* Name +* OSM_CAP_IS_SUBN_TRAP_SUP +* +* DESCRIPTION +* Management class generates Trap() MADs +* +* SYNOPSIS +*/ +#define OSM_CAP_IS_SUBN_TRAP_SUP (1 << 0) +/***********/ + +/****d* OpenSM: Base/OSM_CAP_IS_GET_SET_NOTICE_SUP +* Name +* OSM_CAP_IS_GET_SET_NOTICE_SUP +* +* DESCRIPTION +* Management class supports Get/Set(Notice) +* +* SYNOPSIS +*/ +#define OSM_CAP_IS_SUBN_GET_SET_NOTICE_SUP (1 << 1) +/***********/ + /****d* OpenSM: Base/OSM_CAP_IS_SUBN_OPT_RECS_SUP * Name * OSM_CAP_IS_SUBN_OPT_RECS_SUP * * DESCRIPTION -* Support all optional attributes not including: -* MCMemberRecord, TraceRecord, MultPiathRecord +* Support all optional attributes except: +* MCMemberRecord, TraceRecord, MultiPathRecord * * SYNOPSIS */ -#define OSM_CAP_IS_SUBN_OPT_RECS_SUP (1 << 8); +#define OSM_CAP_IS_SUBN_OPT_RECS_SUP (1 << 8) /***********/ /****d* OpenSM: Base/OSM_CAP_IS_UD_MCAST_SUP @@ -499,19 +556,19 @@ typedef enum _osm_thread_state * * SYNOPSIS */ -#define OSM_CAP_IS_UD_MCAST_SUP (1 << 9); +#define OSM_CAP_IS_UD_MCAST_SUP (1 << 9) /***********/ -/****d* OpenSM: Base/OSM_CAP_IS_MULTI_PATH_SUP +/****d* OpenSM: Base/OSM_CAP_IS_MULTIPATH_SUP * Name -* OSM_CAP_IS_MULTI_PATH_SUP +* OSM_CAP_IS_MULTIPATH_SUP * * DESCRIPTION -* Multi Path is supported +* MultiPathRecord and TraceRecord are supported * * SYNOPSIS */ -#define OSM_CAP_IS_MULTI_PATH_SUP (1 << 10); +#define OSM_CAP_IS_MULTIPATH_SUP (1 << 10) /***********/ /****d* OpenSM: Base/OSM_CAP_IS_REINIT_SUP @@ -523,7 +580,27 @@ typedef enum _osm_thread_state * * SYNOPSIS */ -#define OSM_CAP_IS_REINIT_SUP (1 << 11); +#define OSM_CAP_IS_REINIT_SUP (1 << 11) +/***********/ + +/****d* OpenSM: Base/OSM_CAP_IS_PORT_INFO_CAPMASK_MATCH_SUPPORTED +* Name +* OSM_CAP_IS_PORT_INFO_CAPMASK_MATCH_SUPPORTED +* +* DESCRIPTION +* SM/SA supports enhanced SA PortInfoRecord searches per 1.2 Errata: +* ClassPortInfo:CapabilityMask.IsPortInfoCapMaskMatchSupported is 1, +* then the AttributeModifier of the SubnAdmGet() and SubnAdmGetTable() +* methods affects the matching behavior on the PortInfo:CapabilityMask +* component. If the high-order bit (bit 31) of the AttributeModifier +* is set to 1, matching on the CapabilityMask component will not be an +* exact bitwise match as described in . Instead, +* matching will only be performed on those bits which are set to 1 in +* the PortInfo:CapabilityMask embedded in the query. +* +* SYNOPSIS +*/ +#define OSM_CAP_IS_PORT_INFO_CAPMASK_MATCH_SUPPORTED (1 << 13) /***********/ /****d* OpenSM: Base/osm_sm_state_t @@ -636,11 +713,6 @@ typedef enum _osm_state_mgr_mode * **********/ -#define OSM_REPORT_BUF_SIZE 0x10000 -#define OSM_REPORT_LINE_SIZE 0x256 -#define OSM_REPORT_BUF_THRESHOLD (OSM_REPORT_BUF_SIZE / OSM_REPORT_LINE_SIZE) - - /****d* OpenSM: Base/osm_sm_signal_t * NAME * osm_sm_signal_t @@ -700,6 +772,40 @@ typedef enum _osm_mcast_req_type #define MAX_UPDN_GUID_FILE_LINE_LENGTH 120 /**********/ +/****s* OpenSM: Base/VendorOUIs +* NAME +* VendorOUIs +* +* DESCRIPTION +* Known device vendor ID and GUID OUIs +* +* SYNOPSIS +*/ +#define OSM_VENDOR_ID_INTEL 0x00D0B7 +#define OSM_VENDOR_ID_MELLANOX 0x0002C9 +#define OSM_VENDOR_ID_REDSWITCH 0x000617 +#define OSM_VENDOR_ID_SILVERSTORM 0x00066A +#define OSM_VENDOR_ID_TOPSPIN 0x0005AD +#define OSM_VENDOR_ID_FUJITSU 0x00E000 +#define OSM_VENDOR_ID_FUJITSU2 0x000B5D +#define OSM_VENDOR_ID_VOLTAIRE 0x0008F1 +#define OSM_VENDOR_ID_YOTTAYOTTA 0x000453 +#define OSM_VENDOR_ID_PATHSCALE 0x001175 +#define OSM_VENDOR_ID_IBM 0x000255 +#define OSM_VENDOR_ID_DIVERGENET 0x00084E +#define OSM_VENDOR_ID_FLEXTRONICS 0x000B8C +#define OSM_VENDOR_ID_AGILENT 0x0030D3 +#define OSM_VENDOR_ID_OBSIDIAN 0x001777 +#define OSM_VENDOR_ID_BAYMICRO 0x000BC1 +#define OSM_VENDOR_ID_LSILOGIC 0x00A0B8 +#define OSM_VENDOR_ID_DDN 0x0001FF +#define OSM_VENDOR_ID_PANTA 0x001393 +#define OSM_VENDOR_ID_HP 0x001708 +#define OSM_VENDOR_ID_RIOWORKS 0x005045 + +/**********/ + END_C_DECLS #endif /* _OSM_BASE_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_console.h b/trunk/ulp/opensm/user/include/opensm/osm_console.h index 9addec75..da0fac3a 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_console.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_console.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -31,6 +31,7 @@ * $Id$ */ + #ifndef _OSM_CONSOLE_H_ #define _OSM_CONSOLE_H_ @@ -54,3 +55,4 @@ void osm_console_prompt(void); END_C_DECLS #endif /* _OSM_CONSOLE_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_db.h b/trunk/ulp/opensm/user/include/opensm/osm_db.h index 65286292..cb68b474 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_db.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_db.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -35,7 +35,6 @@ #ifndef _OSM_DB_H_ #define _OSM_DB_H_ - /* * Abstract: * Declaration of the DB interface. @@ -64,7 +63,7 @@ BEGIN_C_DECLS * DESCRIPTION * The OpenSM database interface provide the means to restore persistat * data, query, modify, delete and evemtually commit it back to the -* persistant media. +* persistent media. * * The interface is defined such that it can is not "data dependant": * All keys and data items are texts. @@ -248,7 +247,7 @@ osm_db_domain_init( * osm_db_restore * * DESCRIPTION -* Reads the entire domain from persistant storage - overrides all +* Reads the entire domain from persistent storage - overrides all * existing cached data (if any). * * SYNOPSIS @@ -260,7 +259,7 @@ osm_db_restore( * PARAMETERS * * p_domain -* [in] Pointer to the database domain object to restore from persistant db +* [in] Pointer to the database domain object to restore from persistent db * * RETURN VALUES * 0 if successful 1 otherwize @@ -311,7 +310,7 @@ int osm_db_store( * PARAMETERS * * p_domain -* [in] Pointer to the database domain object to restore from persistant db +* [in] Pointer to the database domain object to restore from persistent db * * RETURN VALUES * 0 if successful 1 otherwize @@ -453,3 +452,4 @@ osm_db_delete( END_C_DECLS #endif /* _OSM_DB_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_db_pack.h b/trunk/ulp/opensm/user/include/opensm/osm_db_pack.h index 4c382a45..52cdaacc 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_db_pack.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_db_pack.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -252,3 +252,4 @@ osm_db_guid2lid_delete( END_C_DECLS #endif /* _OSM_DB_PACK_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_drop_mgr.h b/trunk/ulp/opensm/user/include/opensm/osm_drop_mgr.h index 42d246ab..81c51fa4 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_drop_mgr.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_drop_mgr.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -44,7 +44,6 @@ * $Revision: 1.4 $ */ - #ifndef _OSM_DROP_MGR_H_ #define _OSM_DROP_MGR_H_ @@ -82,6 +81,7 @@ BEGIN_C_DECLS * Steve King, Intel * *********/ + /****s* OpenSM: Drop Manager/osm_drop_mgr_t * NAME * osm_drop_mgr_t @@ -256,3 +256,4 @@ void osm_drop_mgr_process( END_C_DECLS #endif /* _OSM_DROP_MGR_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_errors.h b/trunk/ulp/opensm/user/include/opensm/osm_errors.h index adcd33ef..c1ffb723 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_errors.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_errors.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -103,10 +103,10 @@ Drop Manager 1900 - 19FF - Linear Fowarding Receive Controller + Linear Forwarding Receive Controller 2000 - 20FF - Linear Fowarding Receiver + Linear Forwarding Receiver 2100 - 21FF Vendor Specific @@ -121,10 +121,10 @@ Generic Responder 2500 - 25FF - Linear Fowarding Receive Controller + Linear Forwarding Receive Controller 2600 - 26FF - Linear Fowarding Receiver + Linear Forwarding Receiver 2700 - 27FF SA MAD controller @@ -136,7 +136,7 @@ PortInfo Record Controller 3000 - 30FF - Link Record Controller + Link Record Controller 3100 - 31FF Path Record Controller @@ -157,13 +157,13 @@ SA Response 3700 - 37FF - Link Record Receiver + Link Record Receiver 3800 - 38FF - Multicast Fowarding Receive Controller + Multicast Forwarding Receive Controller 3900 - 39FF - Multicast Fowarding Receiver + Multicast Forwarding Receiver 4000 - 40FF SMInfo Record Receiver @@ -178,3 +178,4 @@ */ #endif /* _OSM_ERRORS_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_fwd_tbl.h b/trunk/ulp/opensm/user/include/opensm/osm_fwd_tbl.h index 0045b21a..ac31131d 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_fwd_tbl.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_fwd_tbl.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -113,8 +113,9 @@ typedef struct _osm_fwd_tbl_t * then this pointer is NULL. * * SEE ALSO -* Forwarding Table object, Random Fowarding Table object. +* Forwarding Table object, Random Forwarding Table object. *********/ + /****f* OpenSM: Forwarding Table/osm_fwd_tbl_init * NAME * osm_fwd_tbl_init @@ -144,6 +145,7 @@ osm_fwd_tbl_init( * * SEE ALSO *********/ + /****f* OpenSM: Forwarding Table/osm_fwd_tbl_destroy * NAME * osm_fwd_tbl_destroy @@ -226,7 +228,6 @@ osm_fwd_tbl_set( else osm_rand_fwd_tbl_set( p_tbl->p_rnd_tbl, lid_ho, port ); } - /* * PARAMETERS * p_tbl @@ -269,7 +270,6 @@ osm_fwd_tbl_set_block( return( osm_rand_fwd_tbl_set_block( p_tbl->p_rnd_tbl, p_block, block_num ) ); } - /* * PARAMETERS * p_tbl @@ -302,7 +302,6 @@ osm_fwd_tbl_get_size( else return( osm_rand_fwd_tbl_get_size( p_tbl->p_rnd_tbl ) ); } - /* * PARAMETERS * p_tbl @@ -386,3 +385,4 @@ osm_fwd_tbl_get_max_block_id_in_use( END_C_DECLS #endif /* _OSM_FWD_TBL_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_helper.h b/trunk/ulp/opensm/user/include/opensm/osm_helper.h index 300bd199..a713c5c6 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_helper.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_helper.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -36,7 +36,7 @@ #define _OSM_HELPER_H_ #include -#include +#include #include #include #include @@ -62,7 +62,6 @@ BEGIN_C_DECLS * $Revision: 1.7 $ */ - /****f* OpenSM: Helper/ib_get_sa_method_str * NAME * ib_get_sa_method_str @@ -213,6 +212,12 @@ osm_dump_path_record( IN const ib_path_rec_t* const p_pr, IN const osm_log_level_t log_level ); +void +osm_dump_multipath_record( + IN osm_log_t* const p_log, + IN const ib_multipath_rec_t* const p_mpr, + IN const osm_log_level_t log_level ); + void osm_dump_node_record( IN osm_log_t* const p_log, @@ -227,7 +232,7 @@ osm_dump_mc_record( void osm_dump_link_record( - IN osm_log_t* const p_log, + IN osm_log_t* const p_log, IN const ib_link_record_t* const p_lr, IN const osm_log_level_t log_level ); @@ -255,6 +260,24 @@ osm_dump_inform_info( IN const ib_inform_info_t* const p_ii, IN const osm_log_level_t log_level ); +void +osm_dump_inform_info_record( + IN osm_log_t* const p_log, + IN const ib_inform_info_record_t* const p_iir, + IN const osm_log_level_t log_level ); + +void +osm_dump_switch_info_record( + IN osm_log_t* const p_log, + IN const ib_switch_info_record_t* const p_sir, + IN const osm_log_level_t log_level ); + +void +osm_dump_sm_info_record( + IN osm_log_t* const p_log, + IN const ib_sminfo_record_t* const p_smir, + IN const osm_log_level_t log_level ); + void osm_dump_pkey_block( IN osm_log_t* const p_log, @@ -594,3 +617,4 @@ osm_get_sm_mgr_state_str( END_C_DECLS #endif /* _OSM_HELPER_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_inform.h b/trunk/ulp/opensm/user/include/opensm/osm_inform.h index e8ad23fd..70849ea7 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_inform.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_inform.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -31,6 +31,7 @@ * $Id$ */ + /* * Abstract: * Declaration of osm_inform_rec_t. @@ -75,7 +76,7 @@ BEGIN_C_DECLS * DESCRIPTION * The Inform record encapsulates the information needed by the * SA to manage InformInfo registrations and sending Reports(Notice) -* when SM receives Traps for registered LIDs. +* when SM receives Traps for registered LIDs. * * The inform records is not thread safe, thus callers must provide * serialization. @@ -87,6 +88,7 @@ BEGIN_C_DECLS * Eitan Zahavi, Mellanox * *********/ + /****s* OpenSM: Inform Record/osm_infr_t * NAME * osm_infr_t @@ -101,18 +103,27 @@ BEGIN_C_DECLS */ typedef struct _osm_infr_t { - cl_list_item_t list_item; - osm_bind_handle_t h_bind; // a handle of lower level mad srvc - osm_infr_rcv_t* p_infr_rcv; // the receiver of inform_info's - osm_mad_addr_t report_addr; - ib_inform_info_record_t inform_record; + cl_list_item_t list_item; + osm_bind_handle_t h_bind; + osm_infr_rcv_t* p_infr_rcv; + osm_mad_addr_t report_addr; + ib_inform_info_record_t inform_record; } osm_infr_t; /* * FIELDS * list_item * List Item for qlist linkage. Must be first element!! * -* inform_record +* h_bind +* A handle of lower level mad srvc +* +* p_infr_rcv +* The receiver of inform_info's +* +* report_addr +* Report address +* +* inform_record * The Inform Info Record * * SEE ALSO @@ -129,7 +140,7 @@ typedef struct _osm_infr_t */ osm_infr_t* osm_infr_new( - IN const osm_infr_t *p_infr_rec ); + IN const osm_infr_t *p_infr_rec ); /* * PARAMETERS * p_inf_rec @@ -145,7 +156,6 @@ osm_infr_new( * Inform Record, osm_infr_construct, osm_infr_destroy *********/ - /****f* OpenSM: Inform Record/osm_infr_init * NAME * osm_infr_new @@ -158,7 +168,7 @@ osm_infr_new( void osm_infr_init( IN osm_infr_t* const p_infr, - IN const osm_infr_t *p_infr_rec ); + IN const osm_infr_t *p_infr_rec ); /* * PARAMETERS * p_infr @@ -212,37 +222,6 @@ osm_infr_destroy( * Inform Record, osm_infr_construct, osm_infr_destroy *********/ -/****f* OpenSM: Inform Record/osm_infr_get_by_rid -* NAME -* osm_infr_get_by_rid -* -* DESCRIPTION -* Find a matching osm_infr_t in the subnet DB by inform_info_record RID -* -* SYNOPSIS -*/ -osm_infr_t* -osm_infr_get_by_rid( - IN osm_subn_t const *p_subn, - IN osm_log_t *p_log, - IN ib_inform_info_record_t* const p_inf_rec ); -/* -* PARAMETERS -* p_subn -* [in] Pointer to the subnet object -* -* p_log -* [in] Pointer to the log object -* -* p_inf_rec -* [in] Pointer to an inform_info record with the search RID -* -* RETURN -* The matching osm_infr_t -* SEE ALSO -* Inform Record, osm_infr_construct, osm_infr_destroy -*********/ - /****f* OpenSM: Inform Record/osm_infr_get_by_rec * NAME * osm_infr_get_by_rec @@ -256,20 +235,20 @@ osm_infr_t* osm_infr_get_by_rec( IN osm_subn_t const *p_subn, IN osm_log_t *p_log, - IN osm_infr_t* const p_infr_rec ); + IN osm_infr_t* const p_infr_rec ); /* * PARAMETERS * p_subn * [in] Pointer to the subnet object * -* p_log -* [in] Pointer to the log object +* p_log +* [in] Pointer to the log object * -* p_inf_rec -* [in] Pointer to an inform_info record +* p_inf_rec +* [in] Pointer to an inform_info record * -* RETURN -* The matching osm_infr_t +* RETURN +* The matching osm_infr_t * SEE ALSO * Inform Record, osm_infr_construct, osm_infr_destroy *********/ @@ -302,19 +281,19 @@ osm_infr_remove_from_db( */ ib_api_status_t osm_report_notice( - IN osm_log_t* const p_log, - IN osm_subn_t* p_subn, - IN ib_mad_notice_attr_t *p_ntc); + IN osm_log_t* const p_log, + IN osm_subn_t* p_subn, + IN ib_mad_notice_attr_t* p_ntc ); /* * PARAMETERS * p_rcv * [in] Pointer to the trap receiver * -* p_ntc -* [in] Pointer to a copy of the incoming trap notice attribute. +* p_ntc +* [in] Pointer to a copy of the incoming trap notice attribute. * -* RETURN -* IB_SUCCESS on good completion +* RETURN +* IB_SUCCESS on good completion * * SEE ALSO * Inform Record, osm_trap_rcv @@ -323,3 +302,4 @@ osm_report_notice( END_C_DECLS #endif /* _OSM_INFR_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_lid_mgr.h b/trunk/ulp/opensm/user/include/opensm/osm_lid_mgr.h index 7fe07c83..0d63d2e5 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_lid_mgr.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_lid_mgr.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -44,11 +44,9 @@ * $Revision: 1.4 $ */ - #ifndef _OSM_LID_MGR_H_ #define _OSM_LID_MGR_H_ - #include #include #include @@ -86,6 +84,7 @@ BEGIN_C_DECLS * Steve King, Intel * *********/ + /****s* OpenSM: LID Manager/osm_lid_mgr_t * NAME * osm_lid_mgr_t @@ -115,8 +114,8 @@ typedef struct _osm_lid_mgr * p_subn * Pointer to the Subnet object for this subnet. * -* p_db -* Pointer to the database (persistency) object +* p_db +* Pointer to the database (persistency) object * * p_req * Pointer to the Requester object sending SMPs. @@ -127,18 +126,18 @@ typedef struct _osm_lid_mgr * p_lock * Pointer to the serializing lock. * -* p_g2l -* Pointer to the database domain storing guid to lid mapping. +* p_g2l +* Pointer to the database domain storing guid to lid mapping. * -* used_lids -* A vector the maps from the lid to its guid. keeps track of -* existing and non existing mapping of guid->lid +* used_lids +* A vector the maps from the lid to its guid. keeps track of +* existing and non existing mapping of guid->lid * -* free_ranges -* A list of available free lid ranges. The list is initialized -* by the code that initializes the lid assignment and is consumed by the -* procedure that finds a free range. It holds elements of type -* osm_lid_mgr_range_t +* free_ranges +* A list of available free lid ranges. The list is initialized +* by the code that initializes the lid assignment and is consumed +* by the procedure that finds a free range. It holds elements of +* type osm_lid_mgr_range_t * * SEE ALSO * LID Manager object @@ -223,7 +222,7 @@ osm_lid_mgr_init( IN osm_lid_mgr_t* const p_mgr, IN osm_req_t* const p_req, IN osm_subn_t* const p_subn, - IN osm_db_t* const p_db, + IN osm_db_t* const p_db, IN osm_log_t* const p_log, IN cl_plock_t* const p_lock ); /* @@ -237,6 +236,9 @@ osm_lid_mgr_init( * p_subn * [in] Pointer to the Subnet object for this subnet. * +* p_db +* [in] Pointer to the database object. +* * p_log * [in] Pointer to the log object. * @@ -317,3 +319,4 @@ osm_lid_mgr_process_subnet( END_C_DECLS #endif /* _OSM_LID_MGR_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_lin_fwd_rcv.h b/trunk/ulp/opensm/user/include/opensm/osm_lin_fwd_rcv.h index 9850a7f7..3ba174d0 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_lin_fwd_rcv.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_lin_fwd_rcv.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -44,7 +44,6 @@ * $Revision: 1.4 $ */ - #ifndef _OSM_LFT_RCV_H_ #define _OSM_LFT_RCV_H_ @@ -81,6 +80,7 @@ BEGIN_C_DECLS * Steve King, Intel * *********/ + /****s* OpenSM: LFT Receiver/osm_lft_rcv_t * NAME * osm_lft_rcv_t @@ -252,3 +252,4 @@ void osm_lft_rcv_process( END_C_DECLS #endif /* _OSM_LFT_RCV_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_lin_fwd_rcv_ctrl.h b/trunk/ulp/opensm/user/include/opensm/osm_lin_fwd_rcv_ctrl.h index a62f5fcc..907034d4 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_lin_fwd_rcv_ctrl.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_lin_fwd_rcv_ctrl.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -48,8 +48,7 @@ #ifndef _OSM_LFT_RCV_CTRL_H_ #define _OSM_LFT_RCV_CTRL_H_ - -#include +#include #include #include #include @@ -83,6 +82,7 @@ BEGIN_C_DECLS * Steve King, Intel * *********/ + /****s* OpenSM: LFT Receive Controller/osm_lft_rcv_ctrl_t * NAME * osm_lft_rcv_ctrl_t @@ -230,3 +230,4 @@ osm_lft_rcv_ctrl_init( END_C_DECLS #endif /* OSM_LFT_RCV_CTRL_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_lin_fwd_tbl.h b/trunk/ulp/opensm/user/include/opensm/osm_lin_fwd_tbl.h index 31fb18f4..b7763aba 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_lin_fwd_tbl.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_lin_fwd_tbl.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -47,6 +47,7 @@ #ifndef _OSM_LIN_FWD_TBL_H_ #define _OSM_LIN_FWD_TBL_H_ +#include #include #include @@ -77,6 +78,7 @@ BEGIN_C_DECLS * Steve King, Intel * *********/ + /****s* OpenSM: Forwarding Table/osm_lin_fwd_tbl_t * NAME * osm_lin_fwd_tbl_t @@ -105,8 +107,9 @@ typedef struct _osm_lin_fwd_tbl * corresponding LID. Index is by LID. * * SEE ALSO -* Forwarding Table object, Random Fowarding Table object. +* Forwarding Table object, Random Forwarding Table object. *********/ + /****f* OpenSM: Forwarding Table/osm_lin_tbl_new * NAME * osm_lin_tbl_new @@ -133,6 +136,7 @@ osm_lin_tbl_new( * * SEE ALSO *********/ + /****f* OpenSM: Forwarding Table/osm_lin_tbl_delete * NAME * osm_lin_tbl_delete @@ -198,7 +202,6 @@ osm_lin_fwd_tbl_set( * SEE ALSO *********/ - /****f* OpenSM: Forwarding Table/osm_lin_fwd_tbl_get * NAME * osm_lin_fwd_tbl_get @@ -261,6 +264,7 @@ osm_lin_fwd_tbl_get_size( * * SEE ALSO *********/ + /****f* OpenSM: Forwarding Table/osm_lin_fwd_tbl_get_lids_per_block * NAME * osm_lin_fwd_tbl_get_lids_per_block @@ -320,7 +324,6 @@ osm_lin_fwd_tbl_get_max_block_id_in_use( * SEE ALSO *********/ - /****f* OpenSM: Forwarding Table/osm_lin_fwd_tbl_set_block * NAME * osm_lin_fwd_tbl_set_block @@ -348,7 +351,7 @@ osm_lin_fwd_tbl_set_block( if( lid_start + num_lids > p_tbl->size ) return( IB_INVALID_PARAMETER ); - cl_memcpy( &p_tbl->port_tbl[lid_start], p_block, num_lids ); + memcpy( &p_tbl->port_tbl[lid_start], p_block, num_lids ); return( IB_SUCCESS ); } /* @@ -373,3 +376,4 @@ osm_lin_fwd_tbl_set_block( END_C_DECLS #endif /* _OSM_LIN_FWD_TBL_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_link_mgr.h b/trunk/ulp/opensm/user/include/opensm/osm_link_mgr.h index 76c9dc81..c61b8a16 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_link_mgr.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_link_mgr.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -44,11 +44,9 @@ * $Revision: 1.4 $ */ - #ifndef _OSM_LINK_MGR_H_ #define _OSM_LINK_MGR_H_ - #include #include #include @@ -83,6 +81,7 @@ BEGIN_C_DECLS * Steve King, Intel * *********/ + /****s* OpenSM: Link Manager/osm_link_mgr_t * NAME * osm_link_mgr_t @@ -269,3 +268,4 @@ osm_link_mgr_process( END_C_DECLS #endif /* _OSM_LINK_MGR_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_log.h b/trunk/ulp/opensm/user/include/opensm/osm_log.h index e5a324e6..f111a6e7 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_log.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_log.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -44,7 +44,6 @@ * $Revision: 1.6 $ */ - #ifndef _OSM_LOG_H_ #define _OSM_LOG_H_ @@ -57,6 +56,12 @@ #include #include +#ifdef __GNUC__ +#define STRICT_OSM_LOG_FORMAT __attribute__((format(printf, 3, 4))) +#else +#define STRICT_OSM_LOG_FORMAT +#endif + #ifdef __cplusplus # define BEGIN_C_DECLS extern "C" { # define END_C_DECLS } @@ -68,7 +73,7 @@ BEGIN_C_DECLS #define LOG_ENTRY_SIZE_MAX 4096 -#define BUF_SIZE LOG_ENTRY_SIZE_MAX +#define BUF_SIZE LOG_ENTRY_SIZE_MAX #define __func__ __FUNCTION__ @@ -91,15 +96,15 @@ BEGIN_C_DECLS *********/ typedef uint8_t osm_log_level_t; -#define OSM_LOG_NONE 0x00 +#define OSM_LOG_NONE 0x00 #define OSM_LOG_ERROR 0x01 -#define OSM_LOG_INFO 0x02 +#define OSM_LOG_INFO 0x02 #define OSM_LOG_VERBOSE 0x04 #define OSM_LOG_DEBUG 0x08 #define OSM_LOG_FUNCS 0x10 #define OSM_LOG_FRAMES 0x20 #define OSM_LOG_ROUTING 0x40 -#define OSM_LOG_SYS 0x80 +#define OSM_LOG_SYS 0x80 /* DEFAULT - turn on ERROR and INFO only @@ -118,12 +123,13 @@ typedef struct _osm_log { osm_log_level_t level; cl_spinlock_t lock; - boolean_t flush; - FILE* out_port; + unsigned long count; + unsigned long max_size; + boolean_t flush; + FILE* out_port; } osm_log_t; /*********/ - /****f* OpenSM: Log/osm_log_construct * NAME * osm_log_construct @@ -148,13 +154,13 @@ osm_log_construct( * This function does not return a value. * * NOTES -* Allows calling osm_log_init, osm_log_destroy +* Allows calling osm_log_init, osm_log_init_v2, osm_log_destroy * * Calling osm_log_construct is a prerequisite to calling any other -* method except osm_log_init. +* method except osm_log_init or osm_log_init_v2. * * SEE ALSO -* Log object, osm_log_init, +* Log object, osm_log_init, osm_log_init_v2, * osm_log_destroy *********/ @@ -177,9 +183,8 @@ osm_log_destroy( fclose(p_log->out_port); p_log->out_port = stdout; } - closelog(); + closelog(); } - /* * PARAMETERS * p_log @@ -193,62 +198,31 @@ osm_log_destroy( * Log object. * Further operations should not be attempted on the destroyed object. * This function should only be called after a call to -* osm_log_construct or osm_log_init. +* osm_log_construct, osm_log_init, or osm_log_init_v2. * * SEE ALSO * Log object, osm_log_construct, -* osm_log_init +* osm_log_init, osm_log_init_v2 *********/ -/****f* OpenSM: Log/osm_log_init +/****f* OpenSM: Log/osm_log_init_v2 * NAME -* osm_log_init +* osm_log_init_v2 * * DESCRIPTION -* The osm_log_init function initializes a +* The osm_log_init_v2 function initializes a * Log object for use. * * SYNOPSIS */ -static inline ib_api_status_t -osm_log_init( +ib_api_status_t +osm_log_init_v2( IN osm_log_t* const p_log, IN const boolean_t flush, IN const uint8_t log_flags, IN const char *log_file, - IN const boolean_t accum_log_file ) -{ - p_log->level = log_flags; - p_log->flush = flush; - - if (log_file == NULL) - { - p_log->out_port = stdout; - } - else - { - if (accum_log_file) - p_log->out_port = fopen(log_file, "a+"); - else - p_log->out_port = fopen(log_file, "w+"); - - if (!p_log->out_port) - { - if (accum_log_file) - printf("Cannot open %s for appending. Permission denied\n", log_file); - else - printf("Cannot open %s for writing. Permission denied\n", log_file); - - return(IB_UNKNOWN_ERROR); - } - } - openlog("OpenSM", LOG_CONS | LOG_PID, LOG_USER); - - if (cl_spinlock_init( &p_log->lock ) == CL_SUCCESS) - return IB_SUCCESS; - else - return IB_ERROR; -} + IN const unsigned long max_size, + IN const boolean_t accum_log_file ); /* * PARAMETERS * p_log @@ -277,6 +251,27 @@ osm_log_init( * osm_log_destroy *********/ +/****f* OpenSM: Log/osm_log_init +* NAME +* osm_log_init +* +* DESCRIPTION +* The osm_log_init function initializes a +* Log object for use. It is a wrapper for osm_log_init_v2(). +* +* SYNOPSIS +*/ +ib_api_status_t +osm_log_init( + IN osm_log_t* const p_log, + IN const boolean_t flush, + IN const uint8_t log_flags, + IN const char *log_file, + IN const boolean_t accum_log_file ); +/* + * Same as osm_log_init_v2() but without max_size parameter + */ + /****f* OpenSM: Log/osm_log_get_level * NAME * osm_log_get_level @@ -306,6 +301,7 @@ osm_log_get_level( * Log object, osm_log_construct, * osm_log_destroy *********/ + /****f* OpenSM: Log/osm_log_set_level * NAME * osm_log_set_level @@ -339,6 +335,7 @@ osm_log_set_level( * Log object, osm_log_construct, * osm_log_destroy *********/ + /****f* OpenSM: Log/osm_log_is_active * NAME * osm_log_is_active @@ -375,12 +372,14 @@ osm_log_is_active( * osm_log_destroy *********/ +extern int osm_log_printf(osm_log_t *p_log, osm_log_level_t level, + const char *fmt, ...); void osm_log( IN osm_log_t* const p_log, IN const osm_log_level_t verbosity, - IN const char *p_str, ... ); + IN const char *p_str, ... ) STRICT_OSM_LOG_FORMAT; void osm_log_raw( @@ -472,3 +471,4 @@ osm_is_debug(void); END_C_DECLS #endif /* _OSM_LOG_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_mad_pool.h b/trunk/ulp/opensm/user/include/opensm/osm_mad_pool.h index 1d55478d..c2512088 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_mad_pool.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_mad_pool.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -402,3 +402,4 @@ osm_mad_pool_get_outstanding( END_C_DECLS #endif /* _OSM_MAD_POOL_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_madw.h b/trunk/ulp/opensm/user/include/opensm/osm_madw.h index c5ac28de..a0aa29ea 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_madw.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_madw.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -44,13 +44,13 @@ * $Revision: 1.5 $ */ - #ifndef _OSM_MADW_H_ #define _OSM_MADW_H_ +#include #include #include -#include +#include #include #include @@ -75,25 +75,24 @@ BEGIN_C_DECLS typedef struct _osm_bind_info { ib_net64_t port_guid; - uint8_t mad_class; - uint8_t class_version; + uint8_t mad_class; + uint8_t class_version; boolean_t is_responder; boolean_t is_trap_processor; boolean_t is_report_processor; uint32_t send_q_size; uint32_t recv_q_size; - } osm_bind_info_t; /* * FIELDS -* portguid -* PortGuid of local port +* portguid +* PortGuid of local port * -* class -* Mgmt Class ID +* class +* Mgmt Class ID * -* class_version -* Mgmt Class version +* class_version +* Mgmt Class version * * is_responder * True if this is a GSI Agent @@ -132,6 +131,7 @@ typedef struct _osm_bind_info * Steve King, Intel * *********/ + /****s* OpenSM: MAD Wrapper/osm_ni_context_t * NAME * osm_ni_context_t @@ -144,8 +144,7 @@ typedef struct _osm_bind_info typedef struct _osm_ni_context { ib_net64_t node_guid; - uint8_t port_num; - + uint8_t port_num; } osm_ni_context_t; /* * FIELDS @@ -162,7 +161,6 @@ typedef struct _osm_ni_context * * SEE ALSO *********/ -/*********/ /****s* OpenSM: MAD Wrapper/osm_pi_context_t * NAME @@ -177,10 +175,11 @@ typedef struct _osm_pi_context { ib_net64_t node_guid; ib_net64_t port_guid; - boolean_t set_method; - boolean_t light_sweep; - boolean_t update_master_sm_base_lid; - boolean_t ignore_errors; + boolean_t set_method; + boolean_t light_sweep; + boolean_t update_master_sm_base_lid; + boolean_t ignore_errors; + boolean_t active_transition; } osm_pi_context_t; /*********/ @@ -196,9 +195,9 @@ typedef struct _osm_pi_context typedef struct _osm_nd_context { ib_net64_t node_guid; - } osm_nd_context_t; /*********/ + /****s* OpenSM: MAD Wrapper/osm_si_context_t * NAME * osm_si_context_t @@ -213,9 +212,9 @@ typedef struct _osm_si_context ib_net64_t node_guid; boolean_t set_method; boolean_t light_sweep; - } osm_si_context_t; /*********/ + /****s* OpenSM: MAD Wrapper/osm_lft_context_t * NAME * osm_lft_context_t @@ -229,9 +228,9 @@ typedef struct _osm_lft_context { ib_net64_t node_guid; boolean_t set_method; - } osm_lft_context_t; /*********/ + /****s* OpenSM: MAD Wrapper/osm_mft_context_t * NAME * osm_mft_context_t @@ -245,9 +244,9 @@ typedef struct _osm_mft_context { ib_net64_t node_guid; boolean_t set_method; - } osm_mft_context_t; /*********/ + /****s* OpenSM: MAD Wrapper/osm_smi_context_t * NAME * osm_smi_context_t @@ -259,11 +258,11 @@ typedef struct _osm_mft_context */ typedef struct _osm_smi_context { - ib_net64_t port_guid; - boolean_t set_method; - + ib_net64_t port_guid; + boolean_t set_method; } osm_smi_context_t; /*********/ + /****s* OpenSM: MAD Wrapper/osm_pkey_context_t * NAME * osm_pkey_context_t @@ -277,9 +276,10 @@ typedef struct _osm_pkey_context { ib_net64_t node_guid; ib_net64_t port_guid; - boolean_t set_method; + boolean_t set_method; } osm_pkey_context_t; /*********/ + /****s* OpenSM: MAD Wrapper/osm_slvl_context_t * NAME * osm_slvl_context_t @@ -293,9 +293,10 @@ typedef struct _osm_slvl_context { ib_net64_t node_guid; ib_net64_t port_guid; - boolean_t set_method; + boolean_t set_method; } osm_slvl_context_t; /*********/ + /****s* OpenSM: MAD Wrapper/osm_vla_context_t * NAME * osm_vla_context_t @@ -309,13 +310,14 @@ typedef struct _osm_vla_context { ib_net64_t node_guid; ib_net64_t port_guid; - boolean_t set_method; + boolean_t set_method; } osm_vla_context_t; /*********/ + #ifndef OSM_VENDOR_INTF_OPENIB /****s* OpenSM: MAD Wrapper/osm_arbitrary_context_t * NAME -* osm_sa_context_t +* osm_arbitrary_context_t * * DESCRIPTION * Context needed by arbitrary recipient. @@ -329,6 +331,7 @@ typedef struct _osm_arbitrary_context } osm_arbitrary_context_t; /*********/ #endif + /****s* OpenSM: MAD Wrapper/osm_madw_context_t * NAME * osm_madw_context_t @@ -340,15 +343,16 @@ typedef struct _osm_arbitrary_context */ typedef union _osm_madw_context { - osm_ni_context_t ni_context; - osm_pi_context_t pi_context; - osm_nd_context_t nd_context; - osm_si_context_t si_context; - osm_lft_context_t lft_context; - osm_mft_context_t mft_context; - osm_smi_context_t smi_context; + osm_ni_context_t ni_context; + osm_pi_context_t pi_context; + osm_nd_context_t nd_context; + osm_si_context_t si_context; + osm_lft_context_t lft_context; + osm_mft_context_t mft_context; + osm_smi_context_t smi_context; osm_slvl_context_t slvl_context; osm_pkey_context_t pkey_context; + osm_vla_context_t vla_context; #ifndef OSM_VENDOR_INTF_OPENIB osm_arbitrary_context_t arb_context; #endif @@ -366,38 +370,35 @@ typedef union _osm_madw_context typedef struct _osm_mad_addr { ib_net16_t dest_lid; - uint8_t path_bits; - uint8_t static_rate; + uint8_t path_bits; + uint8_t static_rate; union addr_type { struct _smi { ib_net16_t source_lid; - uint8_t port_num; + uint8_t port_num; } smi; struct _gsi { ib_net32_t remote_qp; - ib_net32_t remote_qkey; + ib_net32_t remote_qkey; ib_net16_t pkey; uint8_t service_level; - boolean_t global_route; + boolean_t global_route; ib_grh_t grh_info; } gsi; } addr_type; } osm_mad_addr_t; - /* * FIELDS * * SEE ALSO *********/ - - /****s* OpenSM: MAD Wrapper/osm_madw_t * NAME * osm_madw_t @@ -415,12 +416,11 @@ typedef struct _osm_madw osm_mad_addr_t mad_addr; osm_bind_info_t bind_info; osm_madw_context_t context; - uint32_t mad_size; + uint32_t mad_size; ib_api_status_t status; cl_disp_msgid_t fail_msg; - boolean_t resp_expected; + boolean_t resp_expected; const ib_mad_t *p_mad; - } osm_madw_t; /* * FIELDS @@ -485,8 +485,8 @@ osm_madw_construct( Don't touch the pool_item since that is an opaque object. Clear all other objects in the mad wrapper. */ - cl_memclr( ((uint8_t *)p_madw) + sizeof( cl_pool_item_t ), - sizeof(*p_madw) - sizeof( cl_pool_item_t ) ); + memset( ((uint8_t *)p_madw) + sizeof( cl_pool_item_t ), 0, + sizeof(*p_madw) - sizeof( cl_pool_item_t ) ); } /* * PARAMETERS @@ -535,6 +535,7 @@ void osm_madw_destroy( * SEE ALSO * MAD Wrapper object, osm_madw_construct, osm_madw_init *********/ + /****f* OpenSM: MAD Wrapper/osm_madw_init * NAME * osm_madw_init @@ -578,6 +579,7 @@ osm_madw_init( * * SEE ALSO *********/ + /****f* OpenSM: MAD Wrapper/osm_madw_get_smp_ptr * NAME * osm_madw_get_smp_ptr @@ -663,6 +665,7 @@ osm_madw_get_ni_context_ptr( * * SEE ALSO *********/ + /****f* OpenSM: MAD Wrapper/osm_madw_get_pi_context_ptr * NAME * osm_madw_get_pi_context_ptr @@ -690,6 +693,7 @@ osm_madw_get_pi_context_ptr( * * SEE ALSO *********/ + /****f* OpenSM: MAD Wrapper/osm_madw_get_nd_context_ptr * NAME * osm_madw_get_nd_context_ptr @@ -717,6 +721,7 @@ osm_madw_get_nd_context_ptr( * * SEE ALSO *********/ + /****f* OpenSM: MAD Wrapper/osm_madw_get_lft_context_ptr * NAME * osm_madw_get_lft_context_ptr @@ -744,6 +749,7 @@ osm_madw_get_lft_context_ptr( * * SEE ALSO *********/ + /****f* OpenSM: MAD Wrapper/osm_madw_get_mft_context_ptr * NAME * osm_madw_get_mft_context_ptr @@ -771,6 +777,7 @@ osm_madw_get_mft_context_ptr( * * SEE ALSO *********/ + /****f* OpenSM: MAD Wrapper/osm_madw_get_si_context_ptr * NAME * osm_madw_get_si_context_ptr @@ -826,6 +833,7 @@ osm_madw_get_smi_context_ptr( * * SEE ALSO *********/ + /****f* OpenSM: MAD Wrapper/osm_madw_get_pkey_context_ptr * NAME * osm_madw_get_pkey_context_ptr @@ -853,6 +861,7 @@ osm_madw_get_pkey_context_ptr( * * SEE ALSO *********/ + /****f* OpenSM: MAD Wrapper/osm_madw_get_slvl_context_ptr * NAME * osm_madw_get_slvl_context_ptr @@ -1148,3 +1157,4 @@ osm_madw_copy_context( END_C_DECLS #endif /* _OSM_MADW_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_matrix.h b/trunk/ulp/opensm/user/include/opensm/osm_matrix.h index 98ea62ed..a6de3854 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_matrix.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_matrix.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -188,6 +188,7 @@ void osm_lid_matrix_destroy( * SEE ALSO * LID Matrix object, osm_lid_matrix_construct, osm_lid_matrix_init *********/ + /****f* OpenSM: LID Matrix/osm_lid_matrix_init * NAME * osm_lid_matrix_init @@ -286,6 +287,7 @@ osm_lid_matrix_get_max_lid_ho( * * SEE ALSO *********/ + /****f* OpenSM: LID Matrix/osm_lid_matrix_get_num_ports * NAME * osm_lid_matrix_get_num_ports @@ -313,12 +315,13 @@ osm_lid_matrix_get_num_ports( * * SEE ALSO *********/ + /****f* OpenSM: LID Matrix/osm_lid_matrix_get_least_hops * NAME * osm_lid_matrix_get_least_hops * * DESCRIPTION -* Returns the number of ports in this lid matrix. +* Returns the least number of hops for specified lid * * SYNOPSIS */ @@ -342,7 +345,7 @@ osm_lid_matrix_get_least_hops( * [in] LID (host order) for which to retrieve the shortest hop count. * * RETURN VALUES -* Returns the number of ports in this lid matrix. +* Returns the least number of hops for specified lid * * NOTES * @@ -385,6 +388,7 @@ osm_lid_matrix_set( * * SEE ALSO *********/ + /****f* OpenSM: LID Matrix/osm_lid_matrix_set_min_lid_size * NAME * osm_lid_matrix_set_min_lid_size @@ -447,3 +451,4 @@ osm_lid_matrix_clear( END_C_DECLS #endif /* _OSM_MATRIX_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_mcast_fwd_rcv.h b/trunk/ulp/opensm/user/include/opensm/osm_mcast_fwd_rcv.h index 9b73e8c1..0a812167 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_mcast_fwd_rcv.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_mcast_fwd_rcv.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -44,7 +44,6 @@ * $Revision: 1.4 $ */ - #ifndef _OSM_MFT_RCV_H_ #define _OSM_MFT_RCV_H_ @@ -81,6 +80,7 @@ BEGIN_C_DECLS * Steve King, Intel * *********/ + /****s* OpenSM: MFT Receiver/osm_mft_rcv_t * NAME * osm_mft_rcv_t @@ -256,3 +256,4 @@ osm_mft_rcv_process( END_C_DECLS #endif /* _OSM_MFT_RCV_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_mcast_fwd_rcv_ctrl.h b/trunk/ulp/opensm/user/include/opensm/osm_mcast_fwd_rcv_ctrl.h index b9747fa9..c664ecb6 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_mcast_fwd_rcv_ctrl.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_mcast_fwd_rcv_ctrl.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -49,8 +49,7 @@ #ifndef _OSM_MFT_RCV_CTRL_H_ #define _OSM_MFT_RCV_CTRL_H_ - -#include +#include #include #include #include @@ -85,6 +84,7 @@ BEGIN_C_DECLS * Steve King, Intel * *********/ + /****s* OpenSM: MFT Receive Controller/osm_mft_rcv_ctrl_t * NAME * osm_mft_rcv_ctrl_t @@ -232,3 +232,4 @@ osm_mft_rcv_ctrl_init( END_C_DECLS #endif /* OSM_MFT_RCV_CTRL_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_mcast_mgr.h b/trunk/ulp/opensm/user/include/opensm/osm_mcast_mgr.h index 477bf921..c975b96d 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_mcast_mgr.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_mcast_mgr.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -44,11 +44,9 @@ * $Revision: 1.4 $ */ - #ifndef _OSM_MCAST_MGR_H_ #define _OSM_MCAST_MGR_H_ - #include #include #include @@ -86,6 +84,7 @@ BEGIN_C_DECLS * Steve King, Intel * *********/ + /****s* OpenSM: Multicast Manager/osm_mcast_mgr_t * NAME * osm_mcast_mgr_t @@ -265,50 +264,6 @@ osm_mcast_mgr_process( * Multicast Manager, Node Info Response Controller *********/ -/****f* OpenSM: Multicast Manager/osm_mcast_mgr_process_mgrp -* NAME -* osm_mcast_mgr_process_mgrp -* -* DESCRIPTION -* Processes a specific multicast group. This function is called -* by the SM to process a multicast group. Note that this function -* returns BEFORE the switch tables have been configured over the wire, -* and AFTER switch table configuration MADs are all placed in the -* VL15 FIFOs. In other words, the switch table configuration is -* imminent but probably not yet complete at the time this call returns. -* -* SYNOPSIS -*/ -osm_signal_t -osm_mcast_mgr_process_mgrp( - IN osm_mcast_mgr_t* const p_mgr, - IN osm_mgrp_t* const p_mgrp, - IN osm_mcast_req_type_t req_type, - IN ib_net64_t port_guid ); -/* -* PARAMETERS -* p_mgr -* [in] Pointer to an osm_mcast_mgr_t object. -* -* p_mgrp -* [in] Pointer to the multicast group to process. -* -* req_type -* [in] Type of the multicast request that caused this processing -* (MC create/join/leave). -* -* port_guid -* [in] Port guid of the port that was added/removed due to this call. -* -* RETURN VALUES -* OSM_SIGNAL_DONE -* OSM_SIGNAL_DONE_PENDING -* -* NOTES -* -* SEE ALSO -*********/ - /****f* OpenSM: Multicast Manager/osm_mcast_mgr_process_mgrp_cb * NAME * osm_mcast_mgr_process_mgrp_cb @@ -381,3 +336,4 @@ osm_mcast_mgr_process_single( END_C_DECLS #endif /* _OSM_MCAST_MGR_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_mcast_tbl.h b/trunk/ulp/opensm/user/include/opensm/osm_mcast_tbl.h index 7588d9d6..f4adad3c 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_mcast_tbl.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_mcast_tbl.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -74,14 +74,13 @@ BEGIN_C_DECLS */ typedef struct _osm_mcast_fwd_tbl { - uint8_t num_ports; - uint8_t max_position; - uint16_t max_block; - int16_t max_block_in_use; - uint16_t num_entries; - uint16_t max_mlid_ho; - uint16_t (*p_mask_tbl)[][IB_MCAST_POSITION_MAX]; - + uint8_t num_ports; + uint8_t max_position; + uint16_t max_block; + int16_t max_block_in_use; + uint16_t num_entries; + uint16_t max_mlid_ho; + uint16_t (*p_mask_tbl)[][IB_MCAST_POSITION_MAX]; } osm_mcast_tbl_t; /* * FIELDS @@ -142,6 +141,7 @@ osm_mcast_tbl_init( * * SEE ALSO *********/ + /****f* OpenSM: Forwarding Table/osm_mcast_tbl_delete * NAME * osm_mcast_tbl_delete @@ -256,7 +256,6 @@ osm_mcast_tbl_clear_mlid( * SEE ALSO *********/ - /****f* OpenSM: Forwarding Table/osm_mcast_tbl_is_port * NAME * osm_mcast_tbl_is_port @@ -353,9 +352,9 @@ osm_mcast_tbl_set_block( * SEE ALSO *********/ -/****f* OpenSM: Switch/osm_switch_get_mcast_tbl_block +/****f* OpenSM: Forwarding Table/osm_mcast_get_tbl_block * NAME -* osm_switch_get_mcast_tbl_block +* osm_mcast_get_tbl_block * * DESCRIPTION * Retrieve a multicast forwarding table block. @@ -393,9 +392,9 @@ osm_mcast_tbl_get_block( * SEE ALSO *********/ -/****f* OpenSM: Switch/osm_switch_get_max_block +/****f* OpenSM: Forwarding Table/osm_mcast_tbl_get_max_block * NAME -* osm_switch_get_max_block +* osm_mcast_tbl_get_max_block * * DESCRIPTION * Returns the maximum block ID in this table. @@ -421,9 +420,9 @@ osm_mcast_tbl_get_max_block( * SEE ALSO *********/ -/****f* OpenSM: Switch/osm_switch_get_max_block +/****f* OpenSM: Forwarding Table/osm_mcast_tbl_get_max_block_in_use * NAME -* osm_switch_get_max_block +* osm_mcast_tbl_get_max_block_in_use * * DESCRIPTION * Returns the maximum block ID in use in this table. @@ -451,9 +450,9 @@ osm_mcast_tbl_get_max_block_in_use( * SEE ALSO *********/ -/****f* OpenSM: Switch/osm_switch_get_max_position +/****f* OpenSM: Forwarding Table/osm_mcast_tbl_get_max_position * NAME -* osm_switch_get_max_position +* osm_mcast_tbl_get_max_position * * DESCRIPTION * Returns the maximum position in this table. @@ -482,3 +481,4 @@ osm_mcast_tbl_get_max_position( END_C_DECLS #endif /* _OSM_MCAST_TBL_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_mcm_info.h b/trunk/ulp/opensm/user/include/opensm/osm_mcm_info.h index fe7ca2ae..6f6e864c 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_mcm_info.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_mcm_info.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -47,6 +47,7 @@ #ifndef _OSM_MCM_INFO_H_ #define _OSM_MCM_INFO_H_ +#include #include #include #include @@ -105,7 +106,7 @@ static inline void osm_mcm_info_construct( IN osm_mcm_info_t* const p_mcm ) { - cl_memclr( p_mcm, sizeof(*p_mcm) ); + memset( p_mcm, 0, sizeof(*p_mcm) ); } /* * PARAMETERS @@ -233,3 +234,4 @@ osm_mcm_info_delete( END_C_DECLS #endif /* _OSM_MCM_INFO_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_mcm_port.h b/trunk/ulp/opensm/user/include/opensm/osm_mcm_port.h index 7a23240e..78232dd3 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_mcm_port.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_mcm_port.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -31,6 +31,7 @@ * $Id$ */ + /* * Abstract: * Declaration of osm_mcm_port_t. @@ -75,11 +76,10 @@ BEGIN_C_DECLS */ typedef struct _osm_mcm_port { - cl_map_item_t map_item; - ib_gid_t port_gid; - uint8_t scope_state; - boolean_t proxy_join; - + cl_map_item_t map_item; + ib_gid_t port_gid; + uint8_t scope_state; + boolean_t proxy_join; } osm_mcm_port_t; /* * FIELDS @@ -92,10 +92,11 @@ typedef struct _osm_mcm_port * scope_state * ??? * -* proxy_join -* If FALSE - Join was performed by the endport identified by PortGID -* If TRUE - Join was performed on behalf of the endport identified -* by PortGID by another port within the same partition +* proxy_join +* If FALSE - Join was performed by the endport identified +* by PortGID. If TRUE - Join was performed on behalf of +* the endport identified by PortGID by another port within +* the same partition. * * SEE ALSO * MCM Port Object @@ -265,3 +266,4 @@ osm_mcm_port_delete( END_C_DECLS #endif /* _OSM_MCM_PORT_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_msgdef.h b/trunk/ulp/opensm/user/include/opensm/osm_msgdef.h index b6a7946a..8b591d1a 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_msgdef.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_msgdef.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -42,7 +42,6 @@ * $Revision: 1.5 $ */ - #ifndef _OSM_MSGDEF_H_ #define _OSM_MSGDEF_H_ @@ -76,6 +75,7 @@ BEGIN_C_DECLS * Steve King, Intel * *********/ + /****s* OpenSM: Dispatcher Messages/OSM_MSG_REQ * NAME * OSM_MSG_REQ @@ -84,12 +84,12 @@ BEGIN_C_DECLS * Initiates a QP0 attribute request. * * NOTES -* Sent by: osm_sm_t +* Sent by: osm_sm_t * Received by: osm_req_ctrl_t * Delivery notice: yes * -* ***********/ + /****s* OpenSM: Dispatcher Messages/OSM_MSG_MAD_NODE_INFO * NAME * OSM_MSG_MAD_NODE_INFO @@ -98,12 +98,13 @@ BEGIN_C_DECLS * Message for received NodeInfo MADs. * * NOTES -* Sent by: osm_mad_ctrl_t +* Sent by: osm_mad_ctrl_t * Received by: osm_ni_rcv_ctrl_t * Delivery notice: yes * * ***********/ + /****s* OpenSM: Dispatcher Messages/OSM_MSG_MAD_PORT_INFO * NAME * OSM_MSG_MAD_PORT_INFO @@ -112,12 +113,13 @@ BEGIN_C_DECLS * Message for received PortInfo MADs. * * NOTES -* Sent by: osm_mad_ctrl_t +* Sent by: osm_mad_ctrl_t * Received by: osm_pi_rcv_ctrl_t * Delivery notice: yes * * ***********/ + /****s* OpenSM: Dispatcher Messages/OSM_MSG_MAD_SWITCH_INFO * NAME * OSM_MSG_MAD_SWITCH_INFO @@ -126,11 +128,12 @@ BEGIN_C_DECLS * Message for received SwitchInfo MADs. * * NOTES -* Sent by: osm_mad_ctrl_t +* Sent by: osm_mad_ctrl_t * Received by: osm_si_rcv_ctrl_t * Delivery notice: yes * ***********/ + /****s* OpenSM: Dispatcher Messages/OSM_MSG_MAD_NODE_DESC * NAME * OSM_MSG_MAD_NODE_DESC @@ -139,12 +142,13 @@ BEGIN_C_DECLS * Message for received NodeDescription MADs. * * NOTES -* Sent by: osm_mad_ctrl_t +* Sent by: osm_mad_ctrl_t * Received by: osm_nd_rcv_ctrl_t * Delivery notice: yes * * SOURCE ***********/ + /****d* OpenSM: Dispatcher Messages/OSM_MSG_NO_SMPS_OUTSTANDING * NAME * OSM_MSG_NO_SMPS_OUTSTANDING @@ -189,9 +193,16 @@ enum OSM_MSG_MAD_VL_ARB, OSM_MSG_MAD_SLVL, OSM_MSG_MAD_GUIDINFO_RECORD, + OSM_MSG_MAD_INFORM_INFO_RECORD, + OSM_MSG_MAD_SWITCH_INFO_RECORD, + OSM_MSG_MAD_MFT_RECORD, +#if defined (VENDOR_RMPP_SUPPORT) && defined (DUAL_SIDED_RMPP) + OSM_MSG_MAD_MULTIPATH_RECORD, +#endif OSM_MSG_MAX }; END_C_DECLS #endif /* _OSM_MSGDEF_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_mtl_bind.h b/trunk/ulp/opensm/user/include/opensm/osm_mtl_bind.h index c4247726..4394ff22 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_mtl_bind.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_mtl_bind.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -31,6 +31,7 @@ * $Id$ */ + #ifndef _OSM_BIND_H_ #define _OSM_BIND_H_ @@ -140,3 +141,4 @@ osm_mtl_send_mad( END_C_DECLS #endif // _OSM_BIND_H_ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_mtree.h b/trunk/ulp/opensm/user/include/opensm/osm_mtree.h index 77de6e97..24e4a857 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_mtree.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_mtree.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -44,10 +44,10 @@ * $Revision: 1.4 $ */ - #ifndef _OSM_MTREE_H_ #define _OSM_MTREE_H_ +#include #include #include #include @@ -106,12 +106,11 @@ BEGIN_C_DECLS */ typedef struct _osm_mtree_node { - cl_map_item_t map_item; - osm_switch_t *p_sw; - uint8_t max_children; - struct _osm_mtree_node *p_up; - struct _osm_mtree_node *child_array[1]; - + cl_map_item_t map_item; + osm_switch_t *p_sw; + uint8_t max_children; + struct _osm_mtree_node *p_up; + struct _osm_mtree_node *child_array[1]; } osm_mtree_node_t; /* * FIELDS @@ -151,7 +150,7 @@ static inline void osm_mtree_node_construct( IN osm_mtree_node_t* const p_mtn ) { - cl_memclr( p_mtn, sizeof(*p_mtn) ); + memset( p_mtn, 0, sizeof(*p_mtn) ); } /* * PARAMETERS @@ -376,3 +375,4 @@ osm_mtree_node_get_switch_ptr( END_C_DECLS #endif /* _OSM_MTREE_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_multicast.h b/trunk/ulp/opensm/user/include/opensm/osm_multicast.h index 17962caa..b182d3b7 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_multicast.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_multicast.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -31,6 +31,7 @@ * $Id$ */ + /* * Abstract: * Declaration of osm_mgrp_t. @@ -159,15 +160,15 @@ typedef struct osm_mcast_mgr_ctxt */ typedef struct _osm_mgrp { - cl_map_item_t map_item; - ib_net16_t mlid; - osm_mtree_node_t *p_root; - cl_qmap_t mcm_port_tbl; - ib_member_rec_t mcmember_rec; - boolean_t well_known; - boolean_t to_be_deleted; - uint32_t last_change_id; - uint32_t last_tree_id; + cl_map_item_t map_item; + ib_net16_t mlid; + osm_mtree_node_t *p_root; + cl_qmap_t mcm_port_tbl; + ib_member_rec_t mcmember_rec; + boolean_t well_known; + boolean_t to_be_deleted; + uint32_t last_change_id; + uint32_t last_tree_id; } osm_mgrp_t; /* * FIELDS @@ -175,7 +176,8 @@ typedef struct _osm_mgrp * Map Item for qmap linkage. Must be first element!! * * mlid -* The network ordered LID of this Multicast Group (must be >= 0xC000). +* The network ordered LID of this Multicast Group (must be +* >= 0xC000). * * p_root * Pointer to the root "tree node" in the single spanning tree @@ -183,34 +185,33 @@ typedef struct _osm_mgrp * switches. Member ports are not represented in the tree. * * mcm_port_tbl -* Table (sorted by port GUID) of osm_mcm_port_t objects representing -* the member ports of this multicast group. +* Table (sorted by port GUID) of osm_mcm_port_t objects +* representing the member ports of this multicast group. * * mcmember_rec * Hold the parameters of the Multicast Group. * * well_known -* Indicates that this is the wellknow multicast group which is created -* during the initialization of SM/SA and will be present even if -* there are no ports for this group +* Indicates that this is the wellknow multicast group which +* is created during the initialization of SM/SA and will be +* present even if there are no ports for this group * -* to_be_deleted -* Since groups are deleted only after re-route we need to track the -* fact the group is about to be deleted so we can track the fact a -* new join is actually a create request. +* to_be_deleted +* Since groups are deleted only after re-route we need to +* track the fact the group is about to be deleted so we can +* track the fact a new join is actually a create request. * -* last_change_id -* a counter for the number of changes applied to the group. -* this counter shuold be incremented on any modification to the group: -* joining or leaving of ports. +* last_change_id +* a counter for the number of changes applied to the group. +* This counter shuold be incremented on any modification +* to the group: joining or leaving of ports. * -* last_tree_id -* the last change id used for building the current tree. +* last_tree_id +* the last change id used for building the current tree. * * SEE ALSO *********/ - /****f* OpenSM: Vendor API/osm_mgrp_func_t * NAME * osm_mgrp_func_t @@ -517,6 +518,7 @@ osm_mgrp_add_port( * * SEE ALSO *********/ + /****f* OpenSM: Multicast Group/osm_mgrp_is_port_present * NAME * osm_mgrp_is_port_present @@ -553,8 +555,6 @@ osm_mgrp_is_port_present( * SEE ALSO *********/ - - /****f* OpenSM: Multicast Group/osm_mgrp_remove_port * NAME * osm_mgrp_remove_port @@ -695,7 +695,6 @@ osm_mgrp_apply_func( * Multicast Group *********/ - /****f* OpenSM: Multicast Group/osm_mgrp_send_delete_notice * NAME * osm_mgrp_send_delete_notice @@ -767,3 +766,4 @@ osm_mgrp_send_create_notice( END_C_DECLS #endif /* _OSM_MULTICAST_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_node.h b/trunk/ulp/opensm/user/include/opensm/osm_node.h index 244edaf9..db249543 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_node.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_node.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -64,6 +64,8 @@ BEGIN_C_DECLS +struct _osm_switch; + /****h* OpenSM/Node * NAME * Node @@ -98,20 +100,24 @@ BEGIN_C_DECLS */ typedef struct _osm_node { - cl_map_item_t map_item; - ib_node_info_t node_info; - ib_node_desc_t node_desc; - uint32_t discovery_count; - uint32_t physp_tbl_size; - osm_physp_t physp_table[1]; - + cl_map_item_t map_item; + struct _osm_switch *sw; + ib_node_info_t node_info; + ib_node_desc_t node_desc; + uint32_t discovery_count; + uint32_t physp_tbl_size; + osm_physp_t physp_table[1]; } osm_node_t; - /* * FIELDS * map_item * Linkage structure for cl_qmap. MUST BE FIRST MEMBER! * +* sw +* For switch node contains pointer to appropriate osm_switch +* structure. NULL for non-switch nodes. Can be used for fast +* access to switch object and for simple node type detection +* * node_info * The IBA defined NodeInfo data for this node. * @@ -131,8 +137,8 @@ typedef struct _osm_node * phsyp_table * Array of physical port objects belonging to this node. * Index is contiguous by local port number. -* For switches, port 0 is the always the managment port. (14.2.5.6) -* MUST BE LAST MEMBER! - Since it Grows !!!! +* For switches, port 0 is the always the management port (14.2.5.6). +* MUST BE LAST MEMBER! - Since it grows !!!! * * SEE ALSO * Node object @@ -291,6 +297,7 @@ osm_node_get_physp_ptr( * SEE ALSO * Node object *********/ + /****f* OpenSM: Node/osm_node_get_any_physp_ptr * NAME * osm_node_get_any_physp_ptr @@ -391,6 +398,7 @@ osm_node_get_type( * SEE ALSO * Node object *********/ + /****f* OpenSM: Node/osm_node_get_num_physp * NAME * osm_node_get_num_physp @@ -665,6 +673,7 @@ osm_node_discovery_count_get( * SEE ALSO * Node object *********/ + /****f* OpenSM: Node/osm_node_discovery_count_reset * NAME * osm_node_discovery_count_reset @@ -694,6 +703,7 @@ osm_node_discovery_count_reset( * SEE ALSO * Node object *********/ + /****f* OpenSM: Node/osm_node_discovery_count_inc * NAME * osm_node_discovery_count_inc @@ -790,6 +800,7 @@ osm_node_link( * SEE ALSO * Node object *********/ + /****f* OpenSM: Node/osm_node_unlink * NAME * osm_node_unlink @@ -943,3 +954,4 @@ osm_node_link_has_valid_ports( END_C_DECLS #endif /* _OSM_NODE_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_node_desc_rcv.h b/trunk/ulp/opensm/user/include/opensm/osm_node_desc_rcv.h index 72cc1fe0..6e48cd27 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_node_desc_rcv.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_node_desc_rcv.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -45,7 +45,6 @@ * $Revision: 1.4 $ */ - #ifndef _OSM_ND_RCV_H_ #define _OSM_ND_RCV_H_ @@ -82,6 +81,7 @@ BEGIN_C_DECLS * Steve King, Intel * *********/ + /****s* OpenSM: Node Description Receiver/osm_nd_rcv_t * NAME * osm_nd_rcv_t @@ -253,3 +253,4 @@ void osm_nd_rcv_process( END_C_DECLS #endif /* _OSM_ND_RCV_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_node_desc_rcv_ctrl.h b/trunk/ulp/opensm/user/include/opensm/osm_node_desc_rcv_ctrl.h index d62991ab..d838a60c 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_node_desc_rcv_ctrl.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_node_desc_rcv_ctrl.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -48,8 +48,7 @@ #ifndef _OSM_ND_RCV_CTRL_H_ #define _OSM_ND_RCV_CTRL_H_ - -#include +#include #include #include #include @@ -82,6 +81,7 @@ BEGIN_C_DECLS * Steve King, Intel * *********/ + /****s* OpenSM: Node Description Receive Controller/osm_nd_rcv_ctrl_t * NAME * osm_nd_rcv_ctrl_t @@ -229,3 +229,4 @@ osm_nd_rcv_ctrl_init( END_C_DECLS #endif /* OSM_ND_RCV_CTRL_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_node_info_rcv.h b/trunk/ulp/opensm/user/include/opensm/osm_node_info_rcv.h index d5e589dc..ca202fd9 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_node_info_rcv.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_node_info_rcv.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -45,11 +45,9 @@ * $Revision: 1.4 $ */ - #ifndef _OSM_NI_RCV_H_ #define _OSM_NI_RCV_H_ - #include #include #include @@ -86,6 +84,7 @@ BEGIN_C_DECLS * Steve King, Intel * *********/ + /****s* OpenSM: Node Info Receiver/osm_ni_rcv_t * NAME * osm_ni_rcv_t @@ -100,11 +99,11 @@ BEGIN_C_DECLS */ typedef struct _osm_ni_rcv { - osm_subn_t *p_subn; - osm_req_t *p_gen_req; - osm_log_t *p_log; + osm_subn_t *p_subn; + osm_req_t *p_gen_req; + osm_log_t *p_log; osm_state_mgr_t *p_state_mgr; - cl_plock_t *p_lock; + cl_plock_t *p_lock; } osm_ni_rcv_t; /* @@ -262,7 +261,7 @@ boolean_t osm_ni_rcv_is_inited( * * NOTES * The osm_ni_rcv_construct or osm_ni_rcv_init must be -* called before using this function. +* called before using this function. * * SEE ALSO * Node Info Receiver object, osm_ni_rcv_construct, @@ -303,3 +302,4 @@ void osm_ni_rcv_process( END_C_DECLS #endif /* _OSM_NI_RCV_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_node_info_rcv_ctrl.h b/trunk/ulp/opensm/user/include/opensm/osm_node_info_rcv_ctrl.h index d9c9cea0..72b1f671 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_node_info_rcv_ctrl.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_node_info_rcv_ctrl.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -45,12 +45,10 @@ * $Revision: 1.4 $ */ - #ifndef _OSM_NI_RCV_CTRL_H_ #define _OSM_NI_RCV_CTRL_H_ - -#include +#include #include #include #include @@ -83,6 +81,7 @@ BEGIN_C_DECLS * Steve King, Intel * *********/ + /****s* OpenSM: Node Info Receive Controller/osm_ni_rcv_ctrl_t * NAME * osm_ni_rcv_ctrl_t @@ -97,9 +96,9 @@ BEGIN_C_DECLS */ typedef struct _osm_ni_rcv_ctrl { - osm_ni_rcv_t *p_rcv; - osm_log_t *p_log; - cl_dispatcher_t *p_disp; + osm_ni_rcv_t *p_rcv; + osm_log_t *p_log; + cl_dispatcher_t *p_disp; cl_disp_reg_handle_t h_disp; } osm_ni_rcv_ctrl_t; @@ -249,7 +248,7 @@ boolean_t osm_ni_rcv_ctrl_is_inited( * * NOTES * The osm_ni_rcv_ctrl_construct or osm_ni_rcv_ctrl_init must be -* called before using this function. +* called before using this function. * * SEE ALSO * Node Info Receive Controller object, osm_ni_rcv_ctrl_construct, @@ -259,3 +258,4 @@ boolean_t osm_ni_rcv_ctrl_is_inited( END_C_DECLS #endif /* _OSM_NI_RCV_CTRL_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_opensm.h b/trunk/ulp/opensm/user/include/opensm/osm_opensm.h index 52f12e51..9f20488a 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_opensm.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_opensm.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -48,7 +48,7 @@ #define _OSM_OPENSM_H_ #include -#include +#include #include #include #include @@ -59,7 +59,6 @@ #include #include #include -#include #ifdef __cplusplus # define BEGIN_C_DECLS extern "C" { @@ -89,6 +88,47 @@ BEGIN_C_DECLS * *********/ +/****s* OpenSM: OpenSM/osm_routing_engine +* NAME +* struct osm_routing_engine +* +* DESCRIPTION +* OpenSM routing engine module definition. +* NOTES +* routing engine structure - yet limited by ucast_fdb_assign and +* ucast_build_fwd_tables (multicast callbacks may be added later) +*/ +struct osm_routing_engine { + const char *name; + void *context; + int (*build_lid_matrices)(void *context); + int (*ucast_build_fwd_tables)(void *context); + void (*ucast_dump_tables)(void *context); + void (*delete)(void *context); +}; +/* +* FIELDS +* name +* The routing engine name (will be used in logs). +* +* context +* The routing engine context. Will be passed as parameter +* to the callback functions. +* +* build_lid_matrices +* The callback for lid matrices generation. +* +* ucast_build_fwd_tables +* The callback for unicast forwarding table generation. +* +* ucast_dump_tables +* The callback for dumping unicast routing tables. +* +* delete +* The delete method, may be used for routing engine +* internals cleanup. +*/ + /****s* OpenSM: OpenSM/osm_opensm_t * NAME * osm_opensm_t @@ -103,17 +143,17 @@ BEGIN_C_DECLS */ typedef struct _osm_opensm_t { - osm_subn_t subn; - osm_sm_t sm; - osm_sa_t sa; - osm_db_t db; + osm_subn_t subn; + osm_sm_t sm; + osm_sa_t sa; + osm_db_t db; osm_mad_pool_t mad_pool; - osm_vendor_t *p_vendor; + osm_vendor_t *p_vendor; osm_vl15_t vl15; - osm_log_t log; + osm_log_t log; cl_dispatcher_t disp; cl_plock_t lock; - updn_t *p_updn_ucast_routing; + struct osm_routing_engine routing_engine; osm_stats_t stats; } osm_opensm_t; /* @@ -122,13 +162,13 @@ typedef struct _osm_opensm_t * Subnet object for this subnet. * * sm -* The Subnet Manger (SM) object for this subnet. +* The Subnet Manager (SM) object for this subnet. * * sa -* The Subnet Administrator (SA) object for this subnet. +* The Subnet Administration (SA) object for this subnet. * -* db -* Persistant storage of some data required between sessions. +* db +* Persistant storage of some data required between sessions. * * mad_pool * Pool of Management Datagram (MAD) objects. @@ -150,6 +190,9 @@ typedef struct _osm_opensm_t * lock * Shared lock guarding most OpenSM structures. * +* routing_engine +* Routing engine; will be initialized then used. +* * stats * Open SM statistics block * @@ -351,7 +394,7 @@ osm_opensm_bind( static inline cl_status_t osm_opensm_wait_for_subnet_up( IN osm_opensm_t* const p_osm, - IN uint32_t const wait_us, + IN uint32_t const wait_us, IN boolean_t const interruptible ) { return( osm_sm_wait_for_subnet_up( &p_osm->sm, wait_us, interruptible ) ); @@ -394,3 +437,4 @@ extern volatile unsigned int osm_exit_flag; END_C_DECLS #endif /* _OSM_OPENSM_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_partition.h b/trunk/ulp/opensm/user/include/opensm/osm_partition.h index b4e1ed66..0076a349 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_partition.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_partition.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -47,6 +47,12 @@ #ifndef _OSM_PARTITION_H_ #define _OSM_PARTITION_H_ +#include +#include +#include +#include +#include + #ifdef __cplusplus # define BEGIN_C_DECLS extern "C" { # define END_C_DECLS } @@ -91,135 +97,95 @@ BEGIN_C_DECLS */ typedef struct _osm_prtn { - uint16_t pkey; - cl_map port_guid_tbl; - + cl_map_item_t map_item; + uint16_t pkey; + uint8_t sl; + cl_map_t full_guid_tbl; + cl_map_t part_guid_tbl; + char name[32]; } osm_prtn_t; /* * FIELDS +* map_item +* Linkage structure for cl_qmap. MUST BE FIRST MEMBER! +* * pkey * The IBA defined P_KEY of this Partition. * -* port_guid_tbl -* Container of pointers to all Port objects in the Partition, -* indexed by port GUID. +* sl +* The Service Level (SL) associated with this Partiton. * -* SEE ALSO -* Partition -*********/ - -/****f* OpenSM: Partition/osm_prtn_construct -* NAME -* osm_prtn_construct +* full_guid_tbl +* Container of pointers to all Port objects in the Partition +* with full membership, indexed by port GUID. * -* DESCRIPTION -* This function constructs a Partition. +* part_guid_tbl +* Container of pointers to all Port objects in the Partition +* with limited membership, indexed by port GUID. * -* SYNOPSIS -*/ -void osm_prtn_construct( - IN osm_prtn_t* const p_prtn ); -/* -* PARAMETERS -* p_prtn -* [in] Pointer to a Partition to construct. -* -* RETURN VALUE -* This function does not return a value. -* -* NOTES -* Allows calling osm_prtn_init, osm_prtn_destroy, and osm_prtn_is_inited. -* -* Calling osm_prtn_construct is a prerequisite to calling any other -* method except osm_prtn_init. +* name +* Name of the Partition as specified in partition +* configuration. * * SEE ALSO -* Partition, osm_prtn_init, osm_prtn_destroy, osm_prtn_is_inited +* Partition *********/ -/****f* OpenSM: Partition/osm_prtn_destroy +/****f* OpenSM: Partition/osm_prtn_delete * NAME -* osm_prtn_destroy +* osm_prtn_delete * * DESCRIPTION -* The osm_prtn_destroy function destroys a Partition, releasing -* all resources. +* This function destroys and deallocates a Partition object. * * SYNOPSIS */ -void osm_prtn_destroy( - IN osm_prtn_t* const p_prtn ); +void osm_prtn_delete( + IN OUT osm_prtn_t** const pp_prtn ); /* * PARAMETERS -* p_prtn -* [in] Pointer to a Partition to destroy. +* pp_prtn +* [in][out] Pointer to a pointer to a Partition object to +* delete. On return, this pointer is NULL. * * RETURN VALUE * This function does not return a value. * * NOTES -* Performs any necessary cleanup of the specified Partition. -* Further operations should not be attempted on the destroyed object. -* This function should only be called after a call to osm_prtn_construct or -* osm_prtn_init. +* Performs any necessary cleanup of the specified Partition object. * * SEE ALSO -* Partition, osm_prtn_construct, osm_prtn_init +* Partition, osm_prtn_new *********/ -/****f* OpenSM: Partition/osm_prtn_init +/****f* OpenSM: Partition/osm_prtn_new * NAME -* osm_prtn_init +* osm_prtn_new * * DESCRIPTION -* The osm_prtn_init function initializes a Partition for use. +* This function allocates and initializes a Partition object. * * SYNOPSIS */ -ib_api_status_t osm_prtn_init( - IN osm_prtn_t* const p_prtn ); +osm_prtn_t* osm_prtn_new( + IN const char *name, + IN const uint16_t pkey ); /* * PARAMETERS -* p_prtn -* [in] Pointer to an osm_prtn_t object to initialize. -* -* RETURN VALUES -* CL_SUCCESS if initialization was successful. +* name +* [in] Partition name string * -* NOTES -* Allows calling other Partition methods. -* -* SEE ALSO -* Partition, osm_prtn_construct, osm_prtn_destroy, -* osm_prtn_is_inited -*********/ - -/****f* OpenSM: Partition/osm_prtn_is_inited -* NAME -* osm_prtn_is_inited -* -* DESCRIPTION -* Indicates if the object has been initialized with osm_prtn_init. -* -* SYNOPSIS -*/ -boolean_t osm_ptrn_is_inited( - IN const osm_prtn_t* const p_prtn ); -/* -* PARAMETERS -* p_prtn -* [in] Pointer to an osm_prtn_t object. +* pkey +* [in] Partition P_Key value * -* RETURN VALUES -* TRUE if the object was initialized successfully, -* FALSE otherwise. +* RETURN VALUE +* Pointer to the initialize Partition object. * * NOTES -* The osm_prtn_construct or osm_prtn_init must be called before using -* this function. +* Allows calling other partition methods. * * SEE ALSO -* Partition, osm_prtn_construct, osm_prtn_init +* Partition *********/ /****f* OpenSM: Partition/osm_prtn_is_guid @@ -231,9 +197,14 @@ boolean_t osm_ptrn_is_inited( * * SYNOPSIS */ +static inline boolean_t osm_prtn_is_guid( IN const osm_prtn_t* const p_prtn, - IN const uint64 guid ); + IN const ib_net64_t guid ) +{ + return (cl_map_get(&p_prtn->full_guid_tbl, guid) != NULL) || + (cl_map_get(&p_prtn->part_guid_tbl, guid) != NULL); +} /* * PARAMETERS * p_prtn @@ -251,24 +222,28 @@ boolean_t osm_prtn_is_guid( * SEE ALSO *********/ -/****f* OpenSM: Partition/osm_prtn_get_pkey +/****f* OpenSM: Partition/osm_prtn_make_partitions * NAME -* osm_prtn_get_pkey +* osm_prtn_make_partitions * * DESCRIPTION -* Gets the IBA defined P_KEY value for this Partition. +* Makes all partitions in subnet. * * SYNOPSIS */ -uint16_t osm_prtn_get_pkey( - IN const osm_prtn_t* const p_prtn ); +ib_api_status_t osm_prtn_make_partitions( + IN osm_log_t * const p_log, + IN osm_subn_t * const p_subn); /* * PARAMETERS -* p_prtn -* [in] Pointer to an osm_prtn_t object. +* p_log +* [in] Pointer to a log object. +* +* p_subn +* [in] Pointer to subnet object. * * RETURN VALUES -* P_KEY value for this Partition. +* IB_SUCCESS value on success. * * NOTES * @@ -278,3 +253,4 @@ uint16_t osm_prtn_get_pkey( END_C_DECLS #endif /* _OSM_PARTITION_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_path.h b/trunk/ulp/opensm/user/include/opensm/osm_path.h index 21faf3b1..3cc435a7 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_path.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_path.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -35,6 +35,7 @@ #ifndef _OSM_PATH_H_ #define _OSM_PATH_H_ +#include #include #include @@ -72,6 +73,7 @@ BEGIN_C_DECLS * Steve King, Intel * *********/ + /****s* OpenSM: DR Path/osm_dr_path_t * NAME * osm_dr_path_t @@ -118,14 +120,14 @@ osm_dr_path_construct( IN osm_dr_path_t* const p_path ) { /* The first location in the path array is reserved. */ - cl_memclr( p_path, sizeof(*p_path) ); + memset( p_path, 0, sizeof(*p_path) ); p_path->h_bind = OSM_BIND_INVALID_HANDLE; } /* * PARAMETERS * p_path -* [in] Pointer to a directed route path oject to initialize. +* [in] Pointer to a directed route path object to initialize. * * h_bind * [in] Bind handle for the port on which this path applies. @@ -165,13 +167,13 @@ osm_dr_path_init( CL_ASSERT( hop_count < IB_SUBNET_PATH_HOPS_MAX ); p_path->h_bind = h_bind; p_path->hop_count = hop_count; - cl_memcpy( p_path->path, path, IB_SUBNET_PATH_HOPS_MAX ); + memcpy( p_path->path, path, IB_SUBNET_PATH_HOPS_MAX ); } /* * PARAMETERS * p_path -* [in] Pointer to a directed route path oject to initialize. +* [in] Pointer to a directed route path object to initialize. * * h_bind * [in] Bind handle for the port on which this path applies. @@ -214,7 +216,7 @@ osm_dr_path_extend( /* * PARAMETERS * p_path -* [in] Pointer to a directed route path oject to initialize. +* [in] Pointer to a directed route path object to initialize. * * port_num * [in] Additional port to add to the DR path. @@ -246,7 +248,7 @@ osm_dr_path_get_bind_handle( /* * PARAMETERS * p_path -* [in] Pointer to a directed route path oject to initialize. +* [in] Pointer to a directed route path object to initialize. * * port_num * [in] Additional port to add to the DR path. @@ -262,3 +264,4 @@ osm_dr_path_get_bind_handle( END_C_DECLS #endif /* _OSM_PATH_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_pkey.h b/trunk/ulp/opensm/user/include/opensm/osm_pkey.h index c30b14dd..ef8771c4 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_pkey.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_pkey.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -31,11 +31,12 @@ * $Id$ */ + #ifndef _OSM_PKEY_H_ #define _OSM_PKEY_H_ #include -#include +#include #include #include #include @@ -87,16 +88,79 @@ struct _osm_physp; typedef struct _osm_pkey_tbl { cl_ptr_vector_t blocks; + cl_ptr_vector_t new_blocks; cl_map_t keys; + cl_qlist_t pending; + uint16_t used_blocks; + uint16_t max_blocks; } osm_pkey_tbl_t; /* * FIELDS * blocks -* The IBA defined blocks of pkey values +* The IBA defined blocks of pkey values, updated from the subnet +* +* new_blocks +* The blocks of pkey values, will be used for updates by SM * * keys * A set holding all keys * +* pending +* A list of osm_pending_pkey structs that is temporarily set by +* the pkey mgr and used during pkey mgr algorithm only +* +* used_blocks +* Tracks the number of blocks having non-zero pkeys +* +* max_blocks +* The maximal number of blocks this partition table might hold +* this value is based on node_info (for port 0 or CA) or +* switch_info updated on receiving the node_info or switch_info +* GetResp +* +* NOTES +* 'blocks' vector should be used to store pkey values obtained from +* the port and SM pkey manager should not change it directly, for this +* purpose 'new_blocks' should be used. +* +* The only pkey values stored in 'blocks' vector will be mapped with +* 'keys' map +* +*********/ + +/****s* OpenSM: osm_pending_pkey_t +* NAME +* osm_pending_pkey_t +* +* DESCRIPTION +* This objects stores temporary information on pkeys, their target block, +* and index during the pkey manager operation +* +* SYNOPSIS +*/ +typedef struct _osm_pending_pkey { + cl_list_item_t list_item; + uint16_t pkey; + uint16_t block; + uint8_t index; + boolean_t is_new; +} osm_pending_pkey_t; +/* +* FIELDS +* pkey +* The actual P_Key +* +* block +* The block index based on the previous table extracted from the +* device +* +* index +* The index of the pkey within the block +* +* is_new +* TRUE for new P_Keys such that the block and index are invalid +* in that case +* *********/ /****f* OpenSM: osm_pkey_tbl_construct @@ -127,7 +191,8 @@ void osm_pkey_tbl_construct( * * SYNOPSIS */ -int osm_pkey_tbl_init( +ib_api_status_t +osm_pkey_tbl_init( IN osm_pkey_tbl_t *p_pkey_tbl); /* * p_pkey_tbl @@ -194,8 +259,8 @@ osm_pkey_tbl_get_num_blocks( static inline ib_pkey_table_t *osm_pkey_tbl_block_get( const osm_pkey_tbl_t *p_pkey_tbl, uint16_t block) { - CL_ASSERT(block < cl_ptr_vector_get_size(&p_pkey_tbl->blocks)); - return(cl_ptr_vector_get(&p_pkey_tbl->blocks, block)); + return( (block < cl_ptr_vector_get_size(&p_pkey_tbl->blocks)) ? + cl_ptr_vector_get(&p_pkey_tbl->blocks, block) : NULL ); }; /* * p_pkey_tbl @@ -211,6 +276,143 @@ static inline ib_pkey_table_t *osm_pkey_tbl_block_get( * *********/ +/****f* OpenSM: osm_pkey_tbl_new_block_get +* NAME +* osm_pkey_tbl_new_block_get +* +* DESCRIPTION +* The same as above but for new block +* +* SYNOPSIS +*/ +static inline ib_pkey_table_t *osm_pkey_tbl_new_block_get( + const osm_pkey_tbl_t *p_pkey_tbl, uint16_t block) +{ + return (block < cl_ptr_vector_get_size(&p_pkey_tbl->new_blocks)) ? + cl_ptr_vector_get(&p_pkey_tbl->new_blocks, block) : NULL; +}; + +/****f* OpenSM: osm_pkey_tbl_set_new_entry +* NAME +* osm_pkey_tbl_set_new_entry +* +* DESCRIPTION +* Stores the given pkey in the "new" blocks array and update +* the "map" to show that on the "old" blocks +* +* SYNOPSIS +*/ +ib_api_status_t +osm_pkey_tbl_set_new_entry( + IN osm_pkey_tbl_t *p_pkey_tbl, + IN uint16_t block_idx, + IN uint8_t pkey_idx, + IN uint16_t pkey); +/* +* p_pkey_tbl +* [in] Pointer to the PKey table +* +* block_idx +* [in] The block index to use +* +* pkey_idx +* [in] The index within the block +* +* pkey +* [in] PKey to store +* +* RETURN VALUES +* IB_SUCCESS if OK +* IB_ERROR if failed +* +*********/ + +/****f* OpenSM: osm_pkey_find_next_free_entry +* NAME +* osm_pkey_find_next_free_entry +* +* DESCRIPTION +* Find the next free entry in the PKey table starting at the given +* index and block number. The user should increment pkey_idx before +* next call +* Inspect the "new" blocks array for empty space. +* +* SYNOPSIS +*/ +boolean_t +osm_pkey_find_next_free_entry( + IN osm_pkey_tbl_t *p_pkey_tbl, + OUT uint16_t *p_block_idx, + OUT uint8_t *p_pkey_idx); +/* +* p_pkey_tbl +* [in] Pointer to the PKey table +* +* p_block_idx +* [out] The block index to use +* +* p_pkey_idx +* [out] The index within the block to use +* +* RETURN VALUES +* TRUE if found +* FALSE if did not find +* +*********/ + +/****f* OpenSM: osm_pkey_tbl_init_new_blocks +* NAME +* osm_pkey_tbl_init_new_blocks +* +* DESCRIPTION +* Initializes new_blocks vector content (allocate and clear) +* +* SYNOPSIS +*/ +void osm_pkey_tbl_init_new_blocks( + const osm_pkey_tbl_t *p_pkey_tbl); +/* +* p_pkey_tbl +* [in] Pointer to osm_pkey_tbl_t object. +* +* NOTES +* +*********/ + +/****f* OpenSM: osm_pkey_tbl_get_block_and_idx +* NAME +* osm_pkey_tbl_get_block_and_idx +* +* DESCRIPTION +* Set the block index and pkey index the given +* pkey is found in. Return IB_NOT_FOUND if could +* not find it, IB_SUCCESS if OK +* +* SYNOPSIS +*/ +ib_api_status_t +osm_pkey_tbl_get_block_and_idx( + IN osm_pkey_tbl_t *p_pkey_tbl, + IN uint16_t *p_pkey, + OUT uint16_t *block_idx, + OUT uint8_t *pkey_index); +/* +* p_pkey_tbl +* [in] Pointer to osm_pkey_tbl_t object. +* +* p_pkey +* [in] Pointer to the P_Key entry searched +* +* p_block_idx +* [out] Pointer to the block index to be updated +* +* p_pkey_idx +* [out] Pointer to the pkey index (in the block) to be updated +* +* NOTES +* +*********/ + /****f* OpenSM: osm_pkey_tbl_set * NAME * osm_pkey_tbl_set @@ -220,7 +422,8 @@ static inline ib_pkey_table_t *osm_pkey_tbl_block_get( * * SYNOPSIS */ -int osm_pkey_tbl_set( +ib_api_status_t +osm_pkey_tbl_set( IN osm_pkey_tbl_t *p_pkey_tbl, IN uint16_t block, IN ib_pkey_table_t *p_tbl); @@ -241,6 +444,68 @@ int osm_pkey_tbl_set( * *********/ +/****f* OpenSM: osm_physp_share_this_pkey +* NAME +* osm_physp_share_this_pkey +* +* DESCRIPTION +* Checks if the given physical ports share the specified pkey. +* +* SYNOPSIS +*/ +boolean_t osm_physp_share_this_pkey( + IN const struct _osm_physp * const p_physp1, + IN const struct _osm_physp * const p_physp2, + IN const ib_net16_t pkey); +/* +* PARAMETERS +* +* p_physp1 +* [in] Pointer to an osm_physp_t object. +* +* p_physp2 +* [in] Pointer to an osm_physp_t object. +* +* pkey +* [in] value of P_Key to check. +* +* RETURN VALUES +* Returns TRUE if the two ports are matching. +* FALSE otherwise. +* +* NOTES +* +*********/ + +/****f* OpenSM: osm_physp_find_common_pkey +* NAME +* osm_physp_find_common_pkey +* +* DESCRIPTION +* Returns first matching P_Key values for specified physical ports. +* +* SYNOPSIS +*/ +ib_net16_t osm_physp_find_common_pkey( + IN const struct _osm_physp * const p_physp1, + IN const struct _osm_physp * const p_physp2 ); +/* +* PARAMETERS +* +* p_physp1 +* [in] Pointer to an osm_physp_t object. +* +* p_physp2 +* [in] Pointer to an osm_physp_t object. +* +* RETURN VALUES +* Returns value of first shared P_Key or INVALID P_Key (0x0) if not +* found. +* +* NOTES +* +*********/ + /****f* OpenSM: osm_physp_share_pkey * NAME * osm_physp_share_pkey @@ -487,3 +752,4 @@ void osm_pkey_get_tables( END_C_DECLS #endif /* _OSM_PKEY_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_pkey_mgr.h b/trunk/ulp/opensm/user/include/opensm/osm_pkey_mgr.h index 0c1c170a..b750503c 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_pkey_mgr.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_pkey_mgr.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -34,9 +34,8 @@ /* * Abstract: - * Declaration of osm_pkey_mgr_t. - * This object represents the P_Key Manager object. - * This object is part of the OpenSM family of objects. + * Prototype for osm_pkey_mgr_process() function + * This is part of the OpenSM family of objects. * * Environment: * Linux User Mode @@ -44,14 +43,11 @@ * $Revision: 1.4 $ */ - #ifndef _OSM_PKEY_MGR_H_ #define _OSM_PKEY_MGR_H_ -#include -#include -#include -#include +#include +#include #ifdef __cplusplus # define BEGIN_C_DECLS extern "C" { @@ -63,196 +59,32 @@ BEGIN_C_DECLS -/****h* OpenSM/P_Key Manager -* NAME -* P_Key Manager -* -* DESCRIPTION -* The P_Key Manager object manage the p_key tables of all -* objects in the subnet -* -* AUTHOR -* Ofer Gigi, Mellanox -* -*********/ -/****s* OpenSM: P_Key Manager/osm_pkey_mgr_t -* NAME -* osm_pkey_mgr_t -* -* DESCRIPTION -* p_Key Manager structure. -* -* -* SYNOPSIS -*/ - -typedef struct _osm_pkey_mgr -{ - osm_subn_t *p_subn; - osm_log_t *p_log; - osm_req_t *p_req; - cl_plock_t *p_lock; - -} osm_pkey_mgr_t; - -/* -* FIELDS -* p_subn -* Pointer to the Subnet object for this subnet. -* -* p_log -* Pointer to the log object. -* -* p_req -* Pointer to the Request object. -* -* p_lock -* Pointer to the serializing lock. -* -* SEE ALSO -* P_Key Manager object -*********/ - -/****** OpenSM: P_Key Manager/osm_pkey_mgr_construct -* NAME -* osm_pkey_mgr_construct -* -* DESCRIPTION -* This function constructs a P_Key Manager object. -* -* SYNOPSIS -*/ -void -osm_pkey_mgr_construct( - IN osm_pkey_mgr_t* const p_mgr ); -/* -* PARAMETERS -* p_mgr -* [in] Pointer to a P_Key Manager object to construct. -* -* RETURN VALUE -* This function does not return a value. -* -* NOTES -* Allows calling osm_pkey_mgr_init, osm_pkey_mgr_destroy -* -* Calling osm_pkey_mgr_construct is a prerequisite to calling any other -* method except osm_pkey_mgr_init. -* -* SEE ALSO -* P_Key Manager object, osm_pkey_mgr_init, -* osm_pkey_mgr_destroy -*********/ - -/****f* OpenSM: P_Key Manager/osm_pkey_mgr_destroy -* NAME -* osm_pkey_mgr_destroy -* -* DESCRIPTION -* The osm_pkey_mgr_destroy function destroys the object, releasing -* all resources. -* -* SYNOPSIS -*/ -void -osm_pkey_mgr_destroy( - IN osm_pkey_mgr_t* const p_mgr ); -/* -* PARAMETERS -* p_mgr -* [in] Pointer to the object to destroy. -* -* RETURN VALUE -* This function does not return a value. -* -* NOTES -* Performs any necessary cleanup of the specified -* P_Key Manager object. -* Further operations should not be attempted on the destroyed object. -* This function should only be called after a call to -* osm_pkey_mgr_construct or osm_pkey_mgr_init. -* -* SEE ALSO -* P_Key Manager object, osm_pkey_mgr_construct, -* osm_pkey_mgr_init -*********/ - -/****f* OpenSM: P_Key Manager/osm_pkey_mgr_init -* NAME -* osm_pkey_mgr_init -* -* DESCRIPTION -* The osm_pkey_mgr_init function initializes a -* P_Key Manager object for use. -* -* SYNOPSIS -*/ -ib_api_status_t -osm_pkey_mgr_init( - IN osm_pkey_mgr_t* const p_mgr, - IN osm_subn_t* const p_subn, - IN osm_log_t* const p_log, - IN osm_req_t* const p_req, - IN cl_plock_t* const p_lock ); -/* -* PARAMETERS -* p_mgr -* [in] Pointer to an osm_pkey_mgr_t object to initialize. -* -* p_subn -* [in] Pointer to the Subnet object for this subnet. -* -* p_log -* [in] Pointer to the log object. -* -* p_req -* [in] Pointer to an osm_req_t object. -* -* p_lock -* [in] Pointer to the OpenSM serializing lock. -* -* RETURN VALUES -* IB_SUCCESS if the P_Key Manager object was initialized -* successfully. -* -* NOTES -* Allows calling other P_Key Manager methods. -* -* SEE ALSO -* P_Key Manager object, osm_pkey_mgr_construct, -* osm_pkey_mgr_destroy -*********/ - /****f* OpenSM: P_Key Manager/osm_pkey_mgr_process * NAME * osm_pkey_mgr_process * * DESCRIPTION -* This function enforce pkey rules on the SM DB. +* This function enforces the pkey rules on the SM DB. * * SYNOPSIS */ osm_signal_t osm_pkey_mgr_process( - IN const osm_pkey_mgr_t* const p_mgr ); + IN osm_opensm_t *p_osm ); /* * PARAMETERS -* p_mgr -* [in] Pointer to an osm_pkey_mgr_t object. +* p_osm +* [in] Pointer to an osm_opensm_t object. * * RETURN VALUES * None * * NOTES -* Current Operations: -* - Inserts IB_DEFAULT_PKEY to all node objects that don't have -* IB_DEFAULT_PARTIAL_PKEY or IB_DEFAULT_PKEY as part -* of their p_key table * * SEE ALSO -* P_Key Manager *********/ END_C_DECLS #endif /* _OSM_PKEY_MGR_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_pkey_rcv.h b/trunk/ulp/opensm/user/include/opensm/osm_pkey_rcv.h index b97987af..5099e0e3 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_pkey_rcv.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_pkey_rcv.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,11 +32,9 @@ */ - #ifndef _OSM_PKEY_RCV_H_ #define _OSM_PKEY_RCV_H_ - #include #include #include @@ -72,6 +70,7 @@ BEGIN_C_DECLS * Yael Kalka, Mellanox * *********/ + /****s* OpenSM: P_Key Receiver/osm_pkey_rcv_t * NAME * osm_pkey_rcv_t @@ -251,3 +250,4 @@ void osm_pkey_rcv_process( END_C_DECLS #endif /* _OSM_PKEY_RCV_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_pkey_rcv_ctrl.h b/trunk/ulp/opensm/user/include/opensm/osm_pkey_rcv_ctrl.h index 459c1b85..20700d36 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_pkey_rcv_ctrl.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_pkey_rcv_ctrl.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,12 +32,10 @@ */ - #ifndef _OSM_PKEY_RCV_CTRL_H_ #define _OSM_PKEY_RCV_CTRL_H_ - -#include +#include #include #include #include @@ -70,6 +68,7 @@ BEGIN_C_DECLS * Yael Kalka, Mellanox * *********/ + /****s* OpenSM: P_Key Receive Controller/osm_pkey_rcv_ctrl_t * NAME * osm_pkey_rcv_ctrl_t @@ -84,10 +83,10 @@ BEGIN_C_DECLS */ typedef struct _osm_pkey_rcv_ctrl { - osm_pkey_rcv_t *p_rcv; + osm_pkey_rcv_t *p_rcv; osm_log_t *p_log; cl_dispatcher_t *p_disp; - cl_disp_reg_handle_t h_disp; + cl_disp_reg_handle_t h_disp; } osm_pkey_rcv_ctrl_t; /* @@ -236,7 +235,7 @@ boolean_t osm_pkey_rcv_ctrl_is_inited( * * NOTES * The osm_pkey_rcv_ctrl_construct or osm_pkey_rcv_ctrl_init must be -* called before using this function. +* called before using this function. * * SEE ALSO * P_Key Receive Controller object, osm_pkey_rcv_ctrl_construct, @@ -246,3 +245,4 @@ boolean_t osm_pkey_rcv_ctrl_is_inited( END_C_DECLS #endif /* _OSM_PKEY_RCV_CTRL_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_port.h b/trunk/ulp/opensm/user/include/opensm/osm_port.h index 244cb285..b72b16d0 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_port.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_port.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -47,8 +47,9 @@ #ifndef _OSM_PORT_H_ #define _OSM_PORT_H_ +#include +#include #include -#include #include #include #include @@ -94,6 +95,7 @@ struct _osm_node; * Steve King, Intel * *********/ + /****s* OpenSM: Physical Port/osm_physp_t * NAME * osm_physp_t @@ -108,13 +110,13 @@ struct _osm_node; */ typedef struct _osm_physp { - ib_port_info_t port_info; - ib_net64_t port_guid; - uint8_t port_num; - struct _osm_node *p_node; - struct _osm_physp *p_remote_physp; + ib_port_info_t port_info; + ib_net64_t port_guid; + uint8_t port_num; + struct _osm_node *p_node; + struct _osm_physp *p_remote_physp; boolean_t healthy; - osm_dr_path_t dr_path; + osm_dr_path_t dr_path; osm_pkey_tbl_t pkeys; ib_vl_arb_table_t vl_arb[4]; cl_ptr_vector_t slvl_by_port; @@ -144,37 +146,39 @@ typedef struct _osm_physp * Pointer to the Physical Port on the other side of the wire. * If this pointer is NULL no link exists at this port. * -* healthy -* Tracks the health of the port. Normally should be TRUE but -* might change as a result of incoming traps indicating the port -* healthy is questionable. +* healthy +* Tracks the health of the port. Normally should be TRUE but +* might change as a result of incoming traps indicating the port +* healthy is questionable. * * dr_path * The directed route path to this port. * -* pkeys -* osm_pkey_tbl_t object holding the port PKeys. +* pkeys +* osm_pkey_tbl_t object holding the port PKeys. * -* vl_arb[] -* Each Physical Port has 4 sections of VL Arbitration table. +* vl_arb[] +* Each Physical Port has 4 sections of VL Arbitration table. * -* slvl_by_port -* A vector of pointers to the sl2vl tables (ordered by input port). -* On switches have an entry for each other input port (inc SMA=0). -* On CAs only one per port. +* slvl_by_port +* A vector of pointers to the sl2vl tables (ordered by input port). +* On switches have an entry for every other input port (inc SMA=0). +* On CAs only one per port. * -* got_set_resp -* Marks whether or not we got a PortInfoSetResp from this port or not. -* This is used for minimizing the number of PortInfoSet requests sent. -* If we already got a set response from this port, then we will send -* a PortInfoSet only if the values we are updating are different than -* the ones on the port. If the haven't gotten a set response - then we -* want to send the request anyways - since every we need at least one -* PortInfoSet request for every port (by a new SM). +* got_set_resp +* Marks whether or not we got a PortInfoSetResp from this port or not. +* This is used for minimizing the number of PortInfoSet requests sent. +* If we already got a set response from this port, then we will +* send a PortInfoSet only if the values we are updating are +* different than the ones on the port. If the haven't gotten a set +* response - then we want to send the request anyways - since +* every we need at least one PortInfoSet request for every port +* (by a new SM). * * SEE ALSO * Port *********/ + /****f* OpenSM: Physical Port/osm_physp_construct * NAME * osm_physp_construct @@ -200,6 +204,7 @@ osm_physp_construct( * SEE ALSO * Port, Physical Port *********/ + /****f* OpenSM: Physical Port/osm_physp_init * NAME * osm_physp_init @@ -283,8 +288,9 @@ osm_physp_destroy( * osm_physp_init. * * SEE ALSO -* Port, osm_port_init, port_estroy, osm_port_is_inited +* Port, osm_port_init, osm_port_destroy *********/ + /****f* OpenSM: Physical Port/osm_physp_is_valid * NAME * osm_physp_is_valid @@ -404,10 +410,10 @@ osm_physp_set_health( * p_physp * [in] Pointer to an osm_physp_t object. * -* is_healthy -* [in] The health value to be assigned to the port. -* TRUE if the Physical Port should been maked as healthy -* FALSE otherwise. +* is_healthy +* [in] The health value to be assigned to the port. +* TRUE if the Physical Port should been maked as healthy +* FALSE otherwise. * * RETURN VALUES * NONE @@ -423,7 +429,8 @@ osm_physp_set_health( * osm_physp_set_port_info * * DESCRIPTION -* Copies the PortInfo attribute into the Physical Port object. +* Copies the PortInfo attribute into the Physical Port object +* based on the PortState. * * SYNOPSIS */ @@ -434,7 +441,19 @@ osm_physp_set_port_info( { CL_ASSERT( p_pi ); CL_ASSERT( osm_physp_is_valid( p_physp ) ); - p_physp->port_info = *p_pi; + + if (ib_port_info_get_port_state(p_pi) == IB_LINK_DOWN) + { + /* If PortState is down, only copy PortState */ + /* and PortPhysicalState per C14-24-2.1 */ + ib_port_info_set_port_state(&p_physp->port_info, IB_LINK_DOWN); + ib_port_info_set_port_phys_state( + ib_port_info_get_port_phys_state(p_pi), &p_physp->port_info); + } + else + { + p_physp->port_info = *p_pi; + } } /* * PARAMETERS @@ -507,25 +526,26 @@ osm_physp_set_pkey_tbl( IN osm_log_t* p_log, IN const osm_subn_t* p_subn, IN osm_physp_t* const p_physp, IN ib_pkey_table_t *p_pkey_tbl, - IN uint16_t block_num); - + IN uint16_t block_num ); /* * PARAMETERS -* p_log -* [in] Pointer to a log object. +* p_log +* [in] Pointer to a log object. * -* p_subn -* [in] Pointer to the subnet data structure. +* p_subn +* [in] Pointer to the subnet data structure. * -* p_physp -* [in] Pointer to an osm_physp_t object. +* p_physp +* [in] Pointer to an osm_physp_t object. * -* p_pkey_tbl -* [in] Pointer to the IBA defined P_Key table for this port number. +* p_pkey_tbl +* [in] Pointer to the IBA defined P_Key table for this port +* number. * -* block_num -* [in] The part of the P_Key table as defined in the IBA -* (valid values 0-2047, and is further limited by the partitionCap). +* block_num +* [in] The part of the P_Key table as defined in the IBA +* (valid values 0-2047, and is further limited by the +* partitionCap). * * RETURN VALUES * This function does not return a value. @@ -557,8 +577,41 @@ osm_physp_get_pkey_tbl( IN const osm_physp_t* const p_physp ) }; /* * PARAMETERS -* p_physp -* [in] Pointer to an osm_physp_t object. +* p_physp +* [in] Pointer to an osm_physp_t object. +* +* RETURN VALUES +* The pointer to the P_Key table object. +* +* NOTES +* +* SEE ALSO +* Port, Physical Port +*********/ + +/****f* OpenSM: Physical Port/osm_physp_get_mod_pkey_tbl +* NAME +* osm_physp_get_mod_pkey_tbl +* +* DESCRIPTION +* Returns a NON CONST pointer to the P_Key table object of the Physical Port object. +* +* SYNOPSIS +*/ +static inline osm_pkey_tbl_t * +osm_physp_get_mod_pkey_tbl( IN osm_physp_t* const p_physp ) +{ + CL_ASSERT( osm_physp_is_valid( p_physp ) ); + /* + (14.2.5.7) - the block number valid values are 0-2047, and are further + limited by the size of the P_Key table specified by the PartitionCap on the node. + */ + return( &p_physp->pkeys ); +}; +/* +* PARAMETERS +* p_physp +* [in] Pointer to an osm_physp_t object. * * RETURN VALUES * The pointer to the P_Key table object. @@ -580,9 +633,11 @@ osm_physp_get_pkey_tbl( IN const osm_physp_t* const p_physp ) */ static inline void osm_physp_set_slvl_tbl( IN osm_physp_t* const p_physp, - IN ib_slvl_table_t *p_slvl_tbl, - IN uint8_t in_port_num) { + IN ib_slvl_table_t *p_slvl_tbl, + IN uint8_t in_port_num ) +{ ib_slvl_table_t *p_tbl; + CL_ASSERT( p_slvl_tbl ); CL_ASSERT( osm_physp_is_valid( p_physp ) ); p_tbl = cl_ptr_vector_get(&p_physp->slvl_by_port, in_port_num); @@ -596,8 +651,8 @@ osm_physp_set_slvl_tbl( IN osm_physp_t* const p_physp, * p_slvl_tbl * [in] Pointer to the IBA defined SLtoVL map table for this port number. * -* in_port_num -* [in] Input Port Number for this SLtoVL. +* in_port_num +* [in] Input Port Number for this SLtoVL. * * RETURN VALUES * This function does not return a value. @@ -619,8 +674,10 @@ osm_physp_set_slvl_tbl( IN osm_physp_t* const p_physp, */ static inline ib_slvl_table_t * osm_physp_get_slvl_tbl( IN const osm_physp_t* const p_physp, - IN uint8_t in_port_num) { + IN uint8_t in_port_num ) +{ ib_slvl_table_t *p_tbl; + CL_ASSERT( osm_physp_is_valid( p_physp ) ); p_tbl = cl_ptr_vector_get(&p_physp->slvl_by_port, in_port_num); return(p_tbl); @@ -630,8 +687,8 @@ osm_physp_get_slvl_tbl( IN const osm_physp_t* const p_physp, * p_physp * [in] Pointer to an osm_physp_t object. * -* in_port_num -* [in] Input Port Number for this SLtoVL. +* in_port_num +* [in] Input Port Number for this SLtoVL. * * RETURN VALUES * The pointer to the slvl table @@ -653,8 +710,9 @@ osm_physp_get_slvl_tbl( IN const osm_physp_t* const p_physp, */ static inline void osm_physp_set_vla_tbl( IN osm_physp_t* const p_physp, - IN ib_vl_arb_table_t *p_vla_tbl, - IN uint8_t block_num) { + IN ib_vl_arb_table_t *p_vla_tbl, + IN uint8_t block_num ) +{ CL_ASSERT( p_vla_tbl ); CL_ASSERT( osm_physp_is_valid( p_physp ) ); CL_ASSERT( (1 <= block_num) && (block_num <= 4)); @@ -668,8 +726,9 @@ osm_physp_set_vla_tbl( IN osm_physp_t* const p_physp, * p_vla_tbl * [in] Pointer to the IBA defined VL Arbitration table for this port number. * -* block_num -* [in] The part of the VL arbitration as defined in the IBA (valid values 1-4) +* block_num +* [in] The part of the VL arbitration as defined in the IBA +* (valid values 1-4) * * RETURN VALUES * This function does not return a value. @@ -691,7 +750,8 @@ osm_physp_set_vla_tbl( IN osm_physp_t* const p_physp, */ static inline ib_vl_arb_table_t * osm_physp_get_vla_tbl( IN osm_physp_t* const p_physp, - IN uint8_t block_num) { + IN uint8_t block_num ) +{ CL_ASSERT( osm_physp_is_valid( p_physp ) ); CL_ASSERT( (1 <= block_num) && (block_num <= 4)); return(& (p_physp->vl_arb[block_num - 1])); @@ -701,11 +761,12 @@ osm_physp_get_vla_tbl( IN osm_physp_t* const p_physp, * p_physp * [in] Pointer to an osm_physp_t object. * -* block_num -* [in] The part of the VL arbitration as defined in the IBA (valid values 1-4) +* block_num +* [in] The part of the VL arbitration as defined in the IBA +* (valid values 1-4) * * RETURN VALUES -* The pointer to the vl arbitration table +* The pointer to the VL Arbitration table * * NOTES * @@ -743,6 +804,7 @@ osm_physp_get_remote( * SEE ALSO * Port, Physical Port *********/ + /****f* OpenSM: Physical Port/osm_physp_get_port_guid * NAME * osm_physp_get_port_guid @@ -843,7 +905,6 @@ osm_physp_link_exists( * Port, Physical Port *********/ - /****f* OpenSM: Physical Port/osm_physp_link * NAME * osm_physp_link @@ -909,8 +970,7 @@ osm_physp_unlink( * [in] Pointer to the adjacent osm_physp_t object to link. * * RETURN VALUES -* Returns a pointer to the Physical Port on the other side of -* the wire. A return value of NULL means there is no link at this port. +* None. * * NOTES * @@ -918,7 +978,6 @@ osm_physp_unlink( * Port, Physical Port *********/ - /****f* OpenSM: Physical Port/osm_physp_has_any_link * NAME * osm_physp_has_any_link @@ -983,6 +1042,7 @@ osm_physp_get_port_num( * * SEE ALSO *********/ + /****f* OpenSM: Physical Port/osm_physp_get_port_info_ptr * NAME * osm_physp_get_port_info_ptr @@ -1012,6 +1072,7 @@ osm_physp_get_port_info_ptr( * * SEE ALSO *********/ + /****f* OpenSM: Physical Port/osm_physp_get_node_ptr * NAME * osm_physp_get_node_ptr @@ -1071,6 +1132,7 @@ osm_physp_get_port_state( * * SEE ALSO *********/ + /****f* OpenSM: Physical Port/osm_physp_get_base_lid * NAME * osm_physp_get_base_lid @@ -1186,12 +1248,13 @@ osm_physp_get_dr_path_ptr( * Steve King, Intel * *********/ + /****d* OpenSM: Port/osm_port_lid_category_t * NAME * osm_port_lid_category_t * * DESCRIPTION -* Enumerated values for LID dispostion. +* Enumerated values for LID disposition. * * SYNOPSIS */ @@ -1236,15 +1299,14 @@ typedef enum _osm_port_lid_category */ typedef struct _osm_port { - cl_map_item_t map_item; - struct _osm_node *p_node; - ib_net64_t guid; - uint32_t discovery_count; - uint8_t default_port_num; - uint8_t physp_tbl_size; - cl_qlist_t mcm_list; - osm_physp_t *tbl[1]; - + cl_map_item_t map_item; + struct _osm_node *p_node; + ib_net64_t guid; + uint32_t discovery_count; + uint8_t default_port_num; + uint8_t physp_tbl_size; + cl_qlist_t mcm_list; + osm_physp_t *tbl[1]; } osm_port_t; /* * FIELDS @@ -1293,25 +1355,25 @@ static inline void osm_port_construct( IN osm_port_t* const p_port ) { - cl_memclr( p_port, sizeof(*p_port) ); + memset( p_port, 0, sizeof(*p_port) ); cl_qlist_init( &p_port->mcm_list ); } /* * PARAMETERS * p_port -* [in] Pointer to a Port oject to construct. +* [in] Pointer to a Port object to construct. * * RETURN VALUE * This function does not return a value. * * NOTES -* Allows calling osm_port_init, osm_port_destroy, and osm_port_is_inited. +* Allows calling osm_port_init, and osm_port_destroy. * * Calling osm_port_construct is a prerequisite to calling any other * method except osm_port_init. * * SEE ALSO -* Port, osm_port_init, osm_port_destroy, osm_port_is_inited +* Port, osm_port_init, osm_port_destroy *********/ /****f* OpenSM: Port/osm_port_destroy @@ -1329,7 +1391,7 @@ osm_port_destroy( /* * PARAMETERS * p_port -* [in] Pointer to a Port oject to construct. +* [in] Pointer to a Port object to construct. * * RETURN VALUE * This function does not return a value. @@ -1337,12 +1399,13 @@ osm_port_destroy( * NOTES * Performs any necessary cleanup of the specified Port object. * Further operations should not be attempted on the destroyed object. -* This function should only be called after a call to osm_port_construct or -* osm_port_init. +* This function should only be called after a call to osm_port_construct +* or osm_port_init. * * SEE ALSO -* Port, osm_port_init, osm_port_destroy, osm_port_is_inited +* Port, osm_port_init, osm_port_destroy *********/ + /****f* OpenSM: Port/osm_port_delete * NAME * osm_port_delete @@ -1357,13 +1420,13 @@ osm_port_delete( IN OUT osm_port_t** const pp_port ) { osm_port_destroy( *pp_port ); - cl_free( *pp_port ); + free( *pp_port ); *pp_port = NULL; } /* * PARAMETERS * pp_port -* [in][out] Pointer to a pointer to a Port oject to delete. +* [in][out] Pointer to a pointer to a Port object to delete. * On return, this pointer is NULL. * * RETURN VALUE @@ -1375,6 +1438,7 @@ osm_port_delete( * SEE ALSO * Port, osm_port_init, osm_port_destroy *********/ + /****f* OpenSM: Port/osm_port_init * NAME * osm_port_init @@ -1392,7 +1456,7 @@ osm_port_init( /* * PARAMETERS * p_port -* [in] Pointer to a Port oject to initialize. +* [in] Pointer to a Port object to initialize. * * p_ni * [in] Pointer to the NodeInfo attribute relavent for this port. @@ -1410,6 +1474,7 @@ osm_port_init( * SEE ALSO * Port *********/ + /****f* OpenSM: Port/osm_port_new * NAME * osm_port_new @@ -1463,7 +1528,7 @@ osm_port_get_base_lid( /* * PARAMETERS * p_port -* [in] Pointer to a Port oject. +* [in] Pointer to a Port object. * * RETURN VALUE * Base LID of the port. @@ -1474,6 +1539,7 @@ osm_port_get_base_lid( * SEE ALSO * Port *********/ + /****f* OpenSM: Port/osm_port_get_lmc * NAME * osm_port_get_lmc @@ -1492,11 +1558,10 @@ osm_port_get_lmc( CL_ASSERT( osm_physp_is_valid( p_physp ) ); return( osm_physp_get_lmc( p_physp )); } - /* * PARAMETERS * p_port -* [in] Pointer to a Port oject. +* [in] Pointer to a Port object. * * RETURN VALUE * Gets the LMC value of a port. @@ -1525,7 +1590,7 @@ osm_port_get_guid( /* * PARAMETERS * p_port -* [in] Pointer to a Port oject. +* [in] Pointer to a Port object. * * RETURN VALUE * Manufacturer assigned GUID of the port. @@ -1554,7 +1619,7 @@ osm_port_get_num_physp( /* * PARAMETERS * p_port -* [in] Pointer to a Port oject. +* [in] Pointer to a Port object. * * RETURN VALUE * Returns the number of Physical Port objects associated with this port. @@ -1585,7 +1650,7 @@ osm_port_get_phys_ptr( /* * PARAMETERS * p_port -* [in] Pointer to a Port oject. +* [in] Pointer to a Port object. * * port_num * [in] Number of physical port for which to return the @@ -1601,9 +1666,9 @@ osm_port_get_phys_ptr( * Port *********/ -/****f* OpenSM: Port/osm_port_get_phys_ptr +/****f* OpenSM: Port/osm_port_get_default_phys_ptr * NAME -* osm_port_get_phys_ptr +* osm_port_get_default_phys_ptr * * DESCRIPTION * Gets the pointer to the default Physical Port object. @@ -1624,7 +1689,7 @@ osm_port_get_default_phys_ptr( /* * PARAMETERS * p_port -* [in] Pointer to a Port oject. +* [in] Pointer to a Port object. * * RETURN VALUE * Pointer to the Physical Port object. @@ -1640,7 +1705,7 @@ osm_port_get_default_phys_ptr( * osm_port_get_parent_node * * DESCRIPTION -* Gets the pointer to the specified Physical Port object. +* Gets the pointer to the this port's Node object. * * SYNOPSIS */ @@ -1653,7 +1718,7 @@ osm_port_get_parent_node( /* * PARAMETERS * p_port -* [in] Pointer to a Port oject. +* [in] Pointer to a Port object. * * port_num * [in] Number of physical port for which to return the @@ -1686,7 +1751,7 @@ osm_port_get_lid_range_ho( /* * PARAMETERS * p_port -* [in] Pointer to a Port oject. +* [in] Pointer to a Port object. * * p_min_lid * [out] Pointer to the minimum LID value occupied by this port. @@ -1703,6 +1768,42 @@ osm_port_get_lid_range_ho( * Port *********/ +/****f* OpenSM: Port/osm_get_port_by_base_lid +* NAME +* osm_get_port_by_base_lid +* +* DESCRIPTION +* Returns a status on whether a Port was able to be +* determined based on the LID supplied and if so, return the Port. +* +* SYNOPSIS +*/ +ib_api_status_t +osm_get_port_by_base_lid( + IN const osm_subn_t* const p_subn, + IN const ib_net16_t lid, + IN OUT const osm_port_t** const pp_port ); +/* +* PARAMETERS +* p_subn +* [in] Pointer to the subnet data structure. +* +* lid +* [in] LID requested. +* +* pp_port +* [in][out] Pointer to pointer to Port object. +* +* RETURN VALUES +* IB_SUCCESS +* IB_NOT_FOUND +* +* NOTES +* +* SEE ALSO +* Port +*********/ + /****f* OpenSM: Port/osm_port_add_new_physp * NAME * osm_port_add_new_physp @@ -1720,7 +1821,7 @@ osm_port_add_new_physp( /* * PARAMETERS * p_port -* [in] Pointer to a Port oject. +* [in] Pointer to a Port object. * * port_num * [in] Port number to add. @@ -1927,8 +2028,8 @@ osm_physp_calc_link_mtu( IN const osm_physp_t* p_physp ); /* * PARAMETERS -* p_log -* [in] Pointer to a log object. +* p_log +* [in] Pointer to a log object. * * p_physp * [in] Pointer to an osm_physp_t object. @@ -1959,11 +2060,11 @@ osm_physp_calc_link_op_vls( IN const osm_physp_t* p_physp ); /* * PARAMETERS -* p_log -* [in] Pointer to a log object. +* p_log +* [in] Pointer to a log object. * -* p_subn -* [in] Pointer to the subnet object for accessing of the options. +* p_subn +* [in] Pointer to the subnet object for accessing of the options. * * p_physp * [in] Pointer to an osm_physp_t object. @@ -1994,17 +2095,17 @@ osm_physp_replace_dr_path_with_alternate_dr_path( IN osm_bind_handle_t *h_bind ); /* * PARAMETERS -* p_log -* [in] Pointer to a log object. +* p_log +* [in] Pointer to a log object. * -* p_subn -* [in] Pointer to the subnet object for accessing of the options. +* p_subn +* [in] Pointer to the subnet object for accessing of the options. * * p_physp * [in] Pointer to an osm_physp_t object. * -* h_bind -* [in] Pointer to osm_bind_handle_t object. +* h_bind +* [in] Pointer to osm_bind_handle_t object. * * RETURN VALUES * NONE @@ -2018,3 +2119,4 @@ osm_physp_replace_dr_path_with_alternate_dr_path( END_C_DECLS #endif /* _OSM_PORT_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_port_info_rcv.h b/trunk/ulp/opensm/user/include/opensm/osm_port_info_rcv.h index c2e0b21a..67b2a164 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_port_info_rcv.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_port_info_rcv.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -45,11 +45,9 @@ * $Revision: 1.4 $ */ - #ifndef _OSM_PI_RCV_H_ #define _OSM_PI_RCV_H_ - #include #include #include @@ -86,6 +84,7 @@ BEGIN_C_DECLS * Steve King, Intel * *********/ + /****s* OpenSM: Port Info Receiver/osm_pi_rcv_t * NAME * osm_pi_rcv_t @@ -105,7 +104,6 @@ typedef struct _osm_pi_rcv osm_log_t *p_log; osm_state_mgr_t *p_state_mgr; cl_plock_t *p_lock; - } osm_pi_rcv_t; /* * FIELDS @@ -118,7 +116,7 @@ typedef struct _osm_pi_rcv * p_log * Pointer to the log object. * -* p_state_mgr +* p_state_mgr * Pointer to the State Manager object. * * p_lock @@ -205,7 +203,7 @@ ib_api_status_t osm_pi_rcv_init( IN osm_req_t* const p_req, IN osm_subn_t* const p_subn, IN osm_log_t* const p_log, - IN osm_state_mgr_t* const p_state_mgr, + IN osm_state_mgr_t* const p_state_mgr, IN cl_plock_t* const p_lock ); /* * PARAMETERS @@ -221,8 +219,8 @@ ib_api_status_t osm_pi_rcv_init( * p_log * [in] Pointer to the log object. * -* p_state_mgr -* [in] Pointer to the state manager object. +* p_state_mgr +* [in] Pointer to the state manager object. * * p_lock * [in] Pointer to the OpenSM serializing lock. @@ -261,7 +259,7 @@ void osm_pi_rcv_process( * that contains the node's PortInfo attribute. * * RETURN VALUES -* CL_SUCCESS if the PortInfo processing was successful. +* None. * * NOTES * This function processes a PortInfo attribute. @@ -273,3 +271,4 @@ void osm_pi_rcv_process( END_C_DECLS #endif /* _OSM_PI_RCV_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_port_info_rcv_ctrl.h b/trunk/ulp/opensm/user/include/opensm/osm_port_info_rcv_ctrl.h index dd0c1e40..47bf31ea 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_port_info_rcv_ctrl.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_port_info_rcv_ctrl.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -45,12 +45,10 @@ * $Revision: 1.4 $ */ - #ifndef _OSM_PI_RCV_CTRL_H_ #define _OSM_PI_RCV_CTRL_H_ - -#include +#include #include #include #include @@ -83,6 +81,7 @@ BEGIN_C_DECLS * Steve King, Intel * *********/ + /****s* OpenSM: Port Info Receive Controller/osm_pi_rcv_ctrl_t * NAME * osm_pi_rcv_ctrl_t @@ -97,9 +96,9 @@ BEGIN_C_DECLS */ typedef struct _osm_pi_rcv_ctrl { - osm_pi_rcv_t *p_rcv; - osm_log_t *p_log; - cl_dispatcher_t *p_disp; + osm_pi_rcv_t *p_rcv; + osm_log_t *p_log; + cl_dispatcher_t *p_disp; cl_disp_reg_handle_t h_disp; } osm_pi_rcv_ctrl_t; @@ -249,7 +248,7 @@ boolean_t osm_pi_rcv_ctrl_is_inited( * * NOTES * The osm_pi_rcv_ctrl_construct or osm_pi_rcv_ctrl_init must be -* called before using this function. +* called before using this function. * * SEE ALSO * Port Info Receive Controller object, osm_pi_rcv_ctrl_construct, @@ -259,3 +258,4 @@ boolean_t osm_pi_rcv_ctrl_is_inited( END_C_DECLS #endif /* _OSM_PI_RCV_CTRL_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_port_profile.h b/trunk/ulp/opensm/user/include/opensm/osm_port_profile.h index 831f3482..cf55b094 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_port_profile.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_port_profile.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -34,8 +34,8 @@ /* * Abstract: - * Declaration of osm_switch_t. - * This object represents an IBA switch. + * Declaration of Switch/osm_port_profile_t. + * This object represents a port profile for an IBA switch. * This object is part of the OpenSM family of objects. * * Environment: @@ -47,6 +47,7 @@ #ifndef _OSM_PORT_PROFILE_H_ #define _OSM_PORT_PROFILE_H_ +#include #include #include #include @@ -98,7 +99,6 @@ BEGIN_C_DECLS typedef struct _osm_port_profile { uint32_t num_paths; - } osm_port_profile_t; /* * FIELDS @@ -122,7 +122,7 @@ osm_port_prof_construct( IN osm_port_profile_t* const p_prof ) { CL_ASSERT( p_prof ); - cl_memclr( p_prof, sizeof(*p_prof) ); + memset( p_prof, 0, sizeof(*p_prof) ); } /* * PARAMETERS @@ -195,7 +195,6 @@ osm_port_prof_path_count_get( * SEE ALSO *********/ - /****f* OpenSM: Port Profile Opt/osm_port_prof_is_ignored_port * NAME * osm_port_prof_is_ignored_port @@ -208,12 +207,14 @@ osm_port_prof_path_count_get( */ static inline boolean_t osm_port_prof_is_ignored_port( - IN const osm_subn_t *p_subn, - IN uint64_t port_guid, - IN uint8_t port_num) { + IN const osm_subn_t *p_subn, + IN uint64_t port_guid, + IN uint8_t port_num ) +{ const cl_map_t *p_map = &(p_subn->opt.port_prof_ignore_guids); const void *p_obj = cl_map_get(p_map, port_guid); size_t res; + // HACK: we currently support ignoring ports 0 - 31 if (p_obj != NULL) { res = (size_t)p_obj & (size_t)(1 << port_num); @@ -248,12 +249,14 @@ osm_port_prof_is_ignored_port( */ static inline void osm_port_prof_set_ignored_port( - IN osm_subn_t *p_subn, - IN uint64_t port_guid, - IN uint8_t port_num) { + IN osm_subn_t *p_subn, + IN uint64_t port_guid, + IN uint8_t port_num ) +{ cl_map_t *p_map = &(p_subn->opt.port_prof_ignore_guids); const void *p_obj = cl_map_get(p_map, port_guid); size_t value = 0; + // HACK: we currently support ignoring ports 0 - 31 CL_ASSERT(port_num < 32); @@ -285,3 +288,4 @@ osm_port_prof_set_ignored_port( END_C_DECLS #endif /* _OSM_PORT_PROFILE_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_rand_fwd_tbl.h b/trunk/ulp/opensm/user/include/opensm/osm_rand_fwd_tbl.h index 74130c74..bc362adc 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_rand_fwd_tbl.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_rand_fwd_tbl.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -47,6 +47,7 @@ #ifndef _OSM_RAND_FWD_TBL_H_ #define _OSM_RAND_FWD_TBL_H_ +#include #include #include @@ -96,15 +97,15 @@ typedef struct _osm_rand_fwd_tbl { /* PLACE HOLDER STRUCTURE ONLY!! */ uint32_t size; - } osm_rand_fwd_tbl_t; /* * FIELDS * RANDOM FORWARDING TABLES ARE NOT SUPPORTED YET!! * * SEE ALSO -* Forwarding Table object, Random Fowarding Table object. +* Forwarding Table object, Random Forwarding Table object. *********/ + /****f* OpenSM: Forwarding Table/osm_rand_tbl_delete * NAME * osm_rand_tbl_delete @@ -121,7 +122,7 @@ osm_rand_tbl_delete( /* TO DO - This is a place holder function only! */ - cl_free( *pp_tbl ); + free( *pp_tbl ); *pp_tbl = NULL; } /* @@ -138,6 +139,7 @@ osm_rand_tbl_delete( * * SEE ALSO *********/ + /****f* OpenSM: Forwarding Table/osm_rand_fwd_tbl_set * NAME * osm_rand_fwd_tbl_set @@ -177,6 +179,7 @@ osm_rand_fwd_tbl_set( * * SEE ALSO *********/ + /****f* OpenSM: Forwarding Table/osm_rand_fwd_tbl_set_block * NAME * osm_rand_fwd_tbl_set_block @@ -217,6 +220,7 @@ osm_rand_fwd_tbl_set_block( * * SEE ALSO *********/ + /****f* OpenSM: Forwarding Table/osm_rand_fwd_tbl_get * NAME * osm_rand_fwd_tbl_get @@ -252,6 +256,7 @@ osm_rand_fwd_tbl_get( * * SEE ALSO *********/ + /****f* OpenSM: Forwarding Table/osm_rand_fwd_tbl_get_lids_per_block * NAME * osm_rand_fwd_tbl_get_lids_per_block @@ -346,3 +351,4 @@ osm_rand_fwd_tbl_get_size( END_C_DECLS #endif /* _OSM_RAND_FWD_TBL_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_remote_sm.h b/trunk/ulp/opensm/user/include/opensm/osm_remote_sm.h index 8ce22a9e..da4b6f71 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_remote_sm.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_remote_sm.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -78,6 +78,7 @@ BEGIN_C_DECLS * Steve King, Intel * *********/ + /****s* OpenSM: Remote SM/osm_remote_sm_t * NAME * osm_remote_sm_t @@ -92,11 +93,9 @@ BEGIN_C_DECLS */ typedef struct _osm_remote_sm { - cl_map_item_t map_item; - const osm_port_t *p_port; - ib_sm_info_t smi; - boolean_t is_opensm; - + cl_map_item_t map_item; + const osm_port_t *p_port; + ib_sm_info_t smi; } osm_remote_sm_t; /* * FIELDS @@ -108,12 +107,9 @@ typedef struct _osm_remote_sm * smi * The SMInfo attribute for this SM. * -* is_opensm -* TRUE if this SM is an OpenSM. -* FALSE otherwise. -* * SEE ALSO *********/ + /****f* OpenSM: SM/osm_remote_sm_construct * NAME * osm_remote_sm_construct @@ -184,7 +180,7 @@ osm_remote_sm_destroy( * * SYNOPSIS */ -ib_api_status_t +void osm_remote_sm_init( IN osm_remote_sm_t* const p_sm, IN const osm_port_t* const p_port, @@ -201,7 +197,7 @@ osm_remote_sm_init( * [in] Pointer to the SMInfo attribute for this SM. * * RETURN VALUES -* IB_SUCCESS if the SM object was initialized successfully. +* This function does not return a value. * * NOTES * Allows calling other Remote SM methods. @@ -213,3 +209,4 @@ osm_remote_sm_init( END_C_DECLS #endif /* _OSM_REMOTE_SM_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_req.h b/trunk/ulp/opensm/user/include/opensm/osm_req.h index 2260fe44..aed298c1 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_req.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_req.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -45,12 +45,11 @@ * $Revision: 1.4 $ */ - #ifndef _OSM_REQ_H_ #define _OSM_REQ_H_ #include -#include +#include #include #include #include @@ -86,6 +85,7 @@ BEGIN_C_DECLS * Steve King, Intel * *********/ + /****s* OpenSM: Generic Requester/osm_req_t * NAME * osm_req_t @@ -146,15 +146,14 @@ osm_req_construct( * This function does not return a value. * * NOTES -* Allows calling osm_req_init, osm_req_destroy, -* and osm_req_is_inited. +* Allows calling osm_req_init, and osm_req_destroy. * * Calling osm_req_construct is a prerequisite to calling any other * method except osm_req_init. * * SEE ALSO * Generic Requester object, osm_req_init, -* osm_req_destroy, osm_req_is_inited +* osm_req_destroy *********/ /****f* OpenSM: Generic Requester/osm_req_destroy @@ -237,7 +236,7 @@ osm_req_init( * * SEE ALSO * Generic Requester object, osm_req_construct, -* osm_req_destroy, osm_req_is_inited +* osm_req_destroy *********/ /****f* OpenSM: Generic Requester/osm_req_get @@ -352,3 +351,4 @@ osm_req_set( END_C_DECLS #endif /* _OSM_REQ_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_req_ctrl.h b/trunk/ulp/opensm/user/include/opensm/osm_req_ctrl.h index 960143b7..1113d056 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_req_ctrl.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_req_ctrl.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -45,12 +45,11 @@ * $Revision: 1.4 $ */ - #ifndef _OSM_REQ_CTRL_H_ #define _OSM_REQ_CTRL_H_ #include -#include +#include #include #include @@ -81,6 +80,7 @@ BEGIN_C_DECLS * Steve King, Intel * *********/ + /****s* OpenSM: Generic Request Controller/osm_req_ctrl_t * NAME * osm_req_ctrl_t @@ -137,15 +137,14 @@ osm_req_ctrl_construct( * This function does not return a value. * * NOTES -* Allows calling osm_req_ctrl_init, osm_req_ctrl_destroy, -* and osm_req_ctrl_is_inited. +* Allows calling osm_req_ctrl_init, and osm_req_ctrl_destroy. * * Calling osm_req_ctrl_construct is a prerequisite to calling any other * method except osm_req_ctrl_init. * * SEE ALSO * Generic Request Controller object, osm_req_ctrl_init, -* osm_req_ctrl_destroy, osm_req_ctrl_is_inited +* osm_req_ctrl_destroy *********/ /****f* OpenSM: Generic Request Controller/osm_req_ctrl_destroy @@ -220,10 +219,10 @@ osm_req_ctrl_init( * * SEE ALSO * Generic Request Controller object, osm_req_ctrl_construct, -* Generic Requester object, osm_req_ctrl_destroy, -* osm_req_ctrl_is_inited +* Generic Requester object, osm_req_ctrl_destroy *********/ END_C_DECLS #endif /* _OSM_REQ_CTRL_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_resp.h b/trunk/ulp/opensm/user/include/opensm/osm_resp.h index 3d3c107c..9a5977a0 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_resp.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_resp.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -45,13 +45,12 @@ * $Revision: 1.4 $ */ - #ifndef _OSM_RESP_H_ #define _OSM_RESP_H_ #include #include -#include +#include #include #include #include @@ -86,6 +85,7 @@ BEGIN_C_DECLS * Steve King, Intel * *********/ + /****s* OpenSM: Generic Responder/osm_resp_t * NAME * osm_resp_t @@ -276,3 +276,4 @@ osm_resp_send( END_C_DECLS #endif /* _OSM_RESP_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_router.h b/trunk/ulp/opensm/user/include/opensm/osm_router.h new file mode 100644 index 00000000..91b04166 --- /dev/null +++ b/trunk/ulp/opensm/user/include/opensm/osm_router.h @@ -0,0 +1,323 @@ +/* + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. + * + * This software is available to you under the OpenIB.org BSD license + * below: + * + * Redistribution and use in source and binary forms, with or + * without modification, are permitted provided that the following + * conditions are met: + * + * - Redistributions of source code must retain the above + * copyright notice, this list of conditions and the following + * disclaimer. + * + * - Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials + * provided with the distribution. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS + * BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN + * ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN + * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + * + * $Id$ + */ + + +/* + * Abstract: + * Declaration of osm_router_t. + * This object represents an IBA router. + * This object is part of the OpenSM family of objects. + * + * Environment: + * Linux User Mode + * + */ + +#ifndef _OSM_ROUTER_H_ +#define _OSM_ROUTER_H_ + +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#ifdef __cplusplus +# define BEGIN_C_DECLS extern "C" { +# define END_C_DECLS } +#else /* !__cplusplus */ +# define BEGIN_C_DECLS +# define END_C_DECLS +#endif /* __cplusplus */ + +BEGIN_C_DECLS + +/****h* OpenSM/Router +* NAME +* Router +* +* DESCRIPTION +* The Router object encapsulates the information needed by the +* OpenSM to manage routers. The OpenSM allocates one router object +* per router in the IBA subnet. +* +* The Router object is not thread safe, thus callers must provide +* serialization. +* +* This object should be treated as opaque and should be +* manipulated only through the provided functions. +* +* AUTHOR +* Hal Rosenstock, Voltaire +* +*********/ + +/****s* OpenSM: Router/osm_router_t +* NAME +* osm_router_t +* +* DESCRIPTION +* Router structure. +* +* This object should be treated as opaque and should +* be manipulated only through the provided functions. +* +* SYNOPSIS +*/ +typedef struct _osm_router +{ + cl_map_item_t map_item; + osm_port_t *p_port; +} osm_router_t; +/* +* FIELDS +* map_item +* Linkage structure for cl_qmap. MUST BE FIRST MEMBER! +* +* p_port +* Pointer to the Port object for this router. +* +* SEE ALSO +* Router object +*********/ + +/****f* OpenSM: Router/osm_router_construct +* NAME +* osm_router_construct +* +* DESCRIPTION +* This function constructs a Router object. +* +* SYNOPSIS +*/ +void +osm_router_construct( + IN osm_router_t* const p_rtr ); +/* +* PARAMETERS +* p_rtr +* [in] Pointer to a Router object to construct. +* +* RETURN VALUE +* This function does not return a value. +* +* NOTES +* Allows calling osm_router_init, and osm_router_destroy. +* +* Calling osm_router_construct is a prerequisite to calling any other +* method except osm_router_init. +* +* SEE ALSO +* Router object, osm_router_init, osm_router_destroy +*********/ + +/****f* OpenSM: Router/osm_router_destroy +* NAME +* osm_router_destroy +* +* DESCRIPTION +* The osm_router_destroy function destroys the object, releasing +* all resources. +* +* SYNOPSIS +*/ +void +osm_router_destroy( + IN osm_router_t* const p_rtr ); +/* +* PARAMETERS +* p_rtr +* [in] Pointer to the object to destroy. +* +* RETURN VALUE +* None. +* +* NOTES +* Performs any necessary cleanup of the specified object. +* Further operations should not be attempted on the destroyed object. +* This function should only be called after a call to osm_router_construct +* or osm_router_init. +* +* SEE ALSO +* Router object, osm_router_construct, osm_router_init +*********/ + +/****f* OpenSM: Router/osm_router_destroy +* NAME +* osm_router_destroy +* +* DESCRIPTION +* Destroys and deallocates the object. +* +* SYNOPSIS +*/ +void +osm_router_delete( + IN OUT osm_router_t** const pp_rtr ); +/* +* PARAMETERS +* p_rtr +* [in] Pointer to the object to destroy. +* +* RETURN VALUE +* None. +* +* NOTES +* +* SEE ALSO +* Router object, osm_router_construct, osm_router_init +*********/ + +/****f* OpenSM: Router/osm_router_init +* NAME +* osm_router_init +* +* DESCRIPTION +* The osm_router_init function initializes a Router object for use. +* +* SYNOPSIS +*/ +ib_api_status_t +osm_router_init( + IN osm_router_t* const p_rtr, + IN osm_port_t* const p_port ); +/* +* PARAMETERS +* p_rtr +* [in] Pointer to an osm_router_t object to initialize. +* +* p_port +* [in] Pointer to the port object of this router +* +* RETURN VALUES +* IB_SUCCESS if the Router object was initialized successfully. +* +* NOTES +* Allows calling other node methods. +* +* SEE ALSO +* Router object, osm_router_construct, osm_router_destroy +*********/ + +/****f* OpenSM: Router/osm_router_new +* NAME +* osm_router_new +* +* DESCRIPTION +* The osm_router_init function initializes a Router object for use. +* +* SYNOPSIS +*/ +osm_router_t* +osm_router_new( + IN osm_port_t* const p_port ); +/* +* PARAMETERS +* p_node +* [in] Pointer to the node object of this router +* +* RETURN VALUES +* Pointer to the new initialized router object. +* +* NOTES +* +* SEE ALSO +* Router object, osm_router_construct, osm_router_destroy, +*********/ + +/****f* OpenSM: Router/osm_router_get_port_ptr +* NAME +* osm_router_get_port_ptr +* +* DESCRIPTION +* Returns a pointer to the Port object for this router. +* +* SYNOPSIS +*/ +static inline osm_port_t* +osm_router_get_port_ptr( + IN const osm_router_t* const p_rtr ) +{ + return( p_rtr->p_port ); +} +/* +* PARAMETERS +* p_rtr +* [in] Pointer to an osm_router_t object. +* +* RETURN VALUES +* Returns a pointer to the Port object for this router. +* +* NOTES +* +* SEE ALSO +* Router object +*********/ + +/****f* OpenSM: Router/osm_router_get_node_ptr +* NAME +* osm_router_get_node_ptr +* +* DESCRIPTION +* Returns a pointer to the Node object for this router. +* +* SYNOPSIS +*/ +static inline osm_node_t* +osm_router_get_node_ptr( + IN const osm_router_t* const p_rtr ) +{ + return( p_rtr->p_port->p_node ); +} +/* +* PARAMETERS +* p_rtr +* [in] Pointer to an osm_router_t object. +* +* RETURN VALUES +* Returns a pointer to the Node object for this router. +* +* NOTES +* +* SEE ALSO +* Router object +*********/ + +END_C_DECLS + +#endif /* _OSM_ROUTER_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_sa.h b/trunk/ulp/opensm/user/include/opensm/osm_sa.h index db531216..de0f64d0 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_sa.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_sa.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -52,8 +52,8 @@ #include #include #include +#include #include -#include #include #include #include @@ -64,6 +64,7 @@ #include #include #include +#include #include #include #include @@ -74,6 +75,8 @@ #include #include #include +#include +#include #ifdef __cplusplus # define BEGIN_C_DECLS extern "C" { @@ -127,7 +130,7 @@ typedef enum _osm_sa_state * osm_sa_t * * DESCRIPTION -* Subnet Administrator structure. +* Subnet Administration structure. * * This object should be treated as opaque and should * be manipulated only through the provided functions. @@ -137,17 +140,17 @@ typedef enum _osm_sa_state typedef struct _osm_sa { osm_sa_state_t state; - osm_subn_t *p_subn; + osm_subn_t *p_subn; osm_vendor_t *p_vendor; - osm_log_t *p_log; + osm_log_t *p_log; osm_mad_pool_t *p_mad_pool; cl_dispatcher_t *p_disp; - cl_plock_t *p_lock; - atomic32_t sa_trans_id; + cl_plock_t *p_lock; + atomic32_t sa_trans_id; osm_sa_mad_ctrl_t mad_ctrl; osm_sa_resp_t resp; osm_cpi_rcv_t cpi_rcv; - osm_cpi_rcv_ctrl_t cpi_rcv_ctrl; + osm_cpi_rcv_ctrl_t cpi_rcv_ctrl; osm_nr_rcv_t nr_rcv; osm_nr_rcv_ctrl_t nr_rcv_ctrl; osm_pir_rcv_t pir_rcv; @@ -164,32 +167,43 @@ typedef struct _osm_sa osm_mcmr_rcv_ctrl_t mcmr_rcv_ctlr; osm_sr_rcv_t sr_rcv; osm_sr_rcv_ctrl_t sr_rcv_ctrl; - - /* InformInfo Receiver */ - osm_infr_rcv_t infr_rcv; - osm_infr_rcv_ctrl_t infr_rcv_ctrl; +#if defined (VENDOR_RMPP_SUPPORT) && defined (DUAL_SIDED_RMPP) + osm_mpr_rcv_t mpr_rcv; + osm_mpr_rcv_ctrl_t mpr_rcv_ctrl; +#endif - /* VL Arbitrartion Query */ - osm_vlarb_rec_rcv_t vlarb_rec_rcv; - osm_vlarb_rec_rcv_ctrl_t vlarb_rec_rcv_ctrl; + /* InformInfo Receiver */ + osm_infr_rcv_t infr_rcv; + osm_infr_rcv_ctrl_t infr_rcv_ctrl; - /* SLtoVL Map Query */ - osm_slvl_rec_rcv_t slvl_rec_rcv; - osm_slvl_rec_rcv_ctrl_t slvl_rec_rcv_ctrl; - - /* P_Key table Query */ - osm_pkey_rec_rcv_t pkey_rec_rcv; - osm_pkey_rec_rcv_ctrl_t pkey_rec_rcv_ctrl; + /* VL Arbitrartion Query */ + osm_vlarb_rec_rcv_t vlarb_rec_rcv; + osm_vlarb_rec_rcv_ctrl_t vlarb_rec_rcv_ctrl; - /* LinearForwardingTable Query */ - osm_lftr_rcv_t lftr_rcv; - osm_lftr_rcv_ctrl_t lftr_rcv_ctrl; + /* SLtoVL Map Query */ + osm_slvl_rec_rcv_t slvl_rec_rcv; + osm_slvl_rec_rcv_ctrl_t slvl_rec_rcv_ctrl; + /* P_Key table Query */ + osm_pkey_rec_rcv_t pkey_rec_rcv; + osm_pkey_rec_rcv_ctrl_t pkey_rec_rcv_ctrl; + + /* LinearForwardingTable Query */ + osm_lftr_rcv_t lftr_rcv; + osm_lftr_rcv_ctrl_t lftr_rcv_ctrl; + + /* SwitchInfo Query */ + osm_sir_rcv_t sir_rcv; + osm_sir_rcv_ctrl_t sir_rcv_ctrl; + + /* MulticastForwardingTable Query */ + osm_mftr_rcv_t mftr_rcv; + osm_mftr_rcv_ctrl_t mftr_rcv_ctrl; } osm_sa_t; /* * FIELDS * state - State of this SA object +* State of this SA object * p_subn * Pointer to the Subnet object for this subnet. * @@ -439,89 +453,48 @@ osm_sa_bind( * SEE ALSO *********/ -/****f* OpenSM: SA/osm_sa_add_well_known_mc_record +struct _osm_opensm_t; +/****f* OpenSM: SA/osm_sa_db_file_dump * NAME -* osm_sa_add_well_known_mc_record +* osm_sa_db_file_dump * * DESCRIPTION -* Adds the well known Multicast group to the SA database. This -* should be called by SM before programming the switches and after -* SA has been initialized +* Dumps the SA DB to the dump file. * * SYNOPSIS */ - -void -osm_sa_add_well_known_mc_record( - osm_mcmr_recv_t* const p_ctrl, - const ib_member_rec_t * const p_well_know_mc_rec); +int osm_sa_db_file_dump(struct _osm_opensm_t *p_osm); /* * PARAMETERS -* p_ctrl -* [in] Pointer to an osm_mcmr_recv_t object. -* -* p_well_know_mc_rec -* [in] pointer to ib_member_rec_t structure. -* +* p_osm +* [in] Pointer to an osm_opensm_t object. * * RETURN VALUES * None * -* NOTES -* Called by SM after SA has been initialized and before programming the switches -* -* SEE ALSO *********/ - -/****f* OpenSM: SA/osm_sa_create_template_record_ipoib +/****f* OpenSM: SA/osm_sa_db_file_load * NAME -* osm_sa_create_template_record_ipoib +* osm_sa_db_file_load * * DESCRIPTION -* Creates the well known MC record and calls osm_sa_add_well_known_mc_record. This -* should be called by SM before programming the switches and after -* SA has been initialized +* Loads SA DB from the file. * * SYNOPSIS */ -void -osm_sa_create_template_record_ipoib( - IN osm_sa_t* const p_sa, - IN const osm_subn_opt_t* const p_opt ); - +int osm_sa_db_file_load(struct _osm_opensm_t *p_osm); /* * PARAMETERS -* p_sa -* [in] Pointer to an osm_sa_t object. -* -* p_opt -* [in] pointer to cmd line option structure. -* +* p_osm +* [in] Pointer to an osm_opensm_t object. * * RETURN VALUES -* None -* -* NOTES -* Called by SM after SA has been initialized and before programming the switches -* -* SEE ALSO -*********/ - -/****g* OpenSM: SA/osm_ipoib_mgid -* NAME -* osm_ipoib_mgid -* -* DESCRIPTION -* The MGID of the IPoIB Multicast Group +* 0 on success, other value on failure. * -* SYNOPSIS -*/ -extern ib_gid_t osm_ipoib_mgid; -/* -* SEE ALSO *********/ END_C_DECLS #endif /* _OSM_SA_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_sa_class_port_info.h b/trunk/ulp/opensm/user/include/opensm/osm_sa_class_port_info.h index 6ea19295..3869dbce 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_sa_class_port_info.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_sa_class_port_info.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -44,11 +44,9 @@ * $Revision: 1.2 $ */ - #ifndef _OSM_CPI_H_ #define _OSM_CPI_H_ - #include #include #include @@ -86,6 +84,7 @@ BEGIN_C_DECLS * Eitan Zahavi, Mellanox * *********/ + /****s* OpenSM: ClassPort Info Receiver/osm_cpi_rcv_t * NAME * osm_cpi_rcv_t @@ -267,3 +266,4 @@ osm_cpi_rcv_process( END_C_DECLS #endif /* _OSM_CPI_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_sa_class_port_info_ctrl.h b/trunk/ulp/opensm/user/include/opensm/osm_sa_class_port_info_ctrl.h index e7922bf4..58c3c91d 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_sa_class_port_info_ctrl.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_sa_class_port_info_ctrl.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -45,12 +45,10 @@ * $Revision: 1.2 $ */ - #ifndef _OSM_CPICTRL_H_ #define _OSM_CPICTRL_H_ - -#include +#include #include #include #include @@ -83,6 +81,7 @@ BEGIN_C_DECLS * Eitan Zahavi, Mellanox * *********/ + /****s* OpenSM: ClassPort Info Receive Controller/osm_cpi_rcv_ctrl_t * NAME * osm_cpi_rcv_ctrl_t @@ -97,8 +96,8 @@ BEGIN_C_DECLS */ typedef struct _osm_cpi_rcv_ctrl { - osm_cpi_rcv_t *p_rcv; - osm_log_t *p_log; + osm_cpi_rcv_t *p_rcv; + osm_log_t *p_log; cl_dispatcher_t *p_disp; cl_disp_reg_handle_t h_disp; @@ -249,7 +248,7 @@ boolean_t osm_cpi_rcv_ctrl_is_inited( * * NOTES * The osm_cpi_rcv_ctrl_construct or osm_cpi_rcv_ctrl_init must be -* called before using this function. +* called before using this function. * * SEE ALSO * Class Port Info Receive Controller object, osm_cpi_rcv_ctrl_construct, @@ -259,3 +258,4 @@ boolean_t osm_cpi_rcv_ctrl_is_inited( END_C_DECLS #endif /* _OSM_CPICTRL_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_sa_guidinfo_record.h b/trunk/ulp/opensm/user/include/opensm/osm_sa_guidinfo_record.h index 7e30eb45..d9bd48e3 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_sa_guidinfo_record.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_sa_guidinfo_record.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -43,11 +43,9 @@ * */ - #ifndef _OSM_GIR_RCV_H_ #define _OSM_GIR_RCV_H_ - #include #include #include @@ -84,6 +82,7 @@ BEGIN_C_DECLS * Hal Rosenstock, Voltaire * *********/ + /****s* OpenSM: GUIDInfo Record Receiver/osm_gir_rcv_t * NAME * osm_gir_rcv_t @@ -112,7 +111,7 @@ typedef struct _osm_gir_rcv * Pointer to the Subnet object for this subnet. * * p_resp -* Pointer to the SA reponder. +* Pointer to the SA responder. * * p_mad_pool * Pointer to the mad pool. @@ -277,3 +276,4 @@ osm_gir_rcv_process( END_C_DECLS #endif /* _OSM_GIR_RCV_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_sa_guidinfo_record_ctrl.h b/trunk/ulp/opensm/user/include/opensm/osm_sa_guidinfo_record_ctrl.h index 4fd4f77b..f92b5a71 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_sa_guidinfo_record_ctrl.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_sa_guidinfo_record_ctrl.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -44,12 +44,10 @@ * */ - #ifndef _OSM_GIR_CTRL_H_ #define _OSM_GIR_CTRL_H_ - -#include +#include #include #include #include @@ -82,6 +80,7 @@ BEGIN_C_DECLS * Hal Rosenstock, Voltaire * *********/ + /****s* OpenSM: GUID Info Record Receive Controller/osm_gir_rcv_ctrl_t * NAME * osm_gir_rcv_ctrl_t @@ -228,3 +227,4 @@ ib_api_status_t osm_gir_rcv_ctrl_init( END_C_DECLS #endif /* _OSM_GIR_CTRL_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_sa_informinfo.h b/trunk/ulp/opensm/user/include/opensm/osm_sa_informinfo.h index f8d6be86..ac12208e 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_sa_informinfo.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_sa_informinfo.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -48,7 +48,6 @@ #ifndef _OSM_SA_INFR_H_ #define _OSM_SA_INFR_H_ - #include #include #include @@ -87,6 +86,7 @@ BEGIN_C_DECLS * Eitan Zahavi, Mellanox * *********/ + /****s* OpenSM: InformInfo Receiver/osm_infr_rcv_t * NAME * osm_infr_rcv_t @@ -101,11 +101,12 @@ BEGIN_C_DECLS */ typedef struct _osm_infr_rcv { - osm_subn_t *p_subn; - osm_sa_resp_t *p_resp; - osm_mad_pool_t *p_mad_pool; - osm_log_t *p_log; - cl_plock_t *p_lock; + osm_subn_t *p_subn; + osm_sa_resp_t *p_resp; + osm_mad_pool_t *p_mad_pool; + osm_log_t *p_log; + cl_plock_t *p_lock; + cl_qlock_pool_t pool; } osm_infr_rcv_t; /* * FIELDS @@ -121,6 +122,10 @@ typedef struct _osm_infr_rcv * p_lock * Pointer to the serializing lock. * +* pool +* Pool of linkable InformInfo Record objects used to +* generate the query response. +* * SEE ALSO * InformInfo Receiver object *********/ @@ -243,7 +248,7 @@ osm_infr_rcv_init( */ void osm_infr_rcv_process( - IN osm_infr_rcv_t* const p_rcv, + IN osm_infr_rcv_t* const p_rcv, IN const osm_madw_t* const p_madw ); /* * PARAMETERS @@ -260,6 +265,35 @@ osm_infr_rcv_process( * InformInfo Receiver *********/ +/****f* OpenSM: InformInfo Record Receiver/osm_infir_rcv_process +* NAME +* osm_infir_rcv_process +* +* DESCRIPTION +* Process the InformInfo Record request. +* +* SYNOPSIS +*/ +void +osm_infir_rcv_process( + IN osm_infr_rcv_t* const p_rcv, + IN const osm_madw_t* const p_madw ); +/* +* PARAMETERS +* p_rcv +* [in] Pointer to an osm_infr_rcv_t object. +* +* p_madw +* [in] Pointer to the MAD Wrapper containing the MAD +* that contains the node's InformInfo Record attribute. +* NOTES +* This function processes a InformInfo Record attribute. +* +* SEE ALSO +* InformInfo Receiver +*********/ + END_C_DECLS #endif /* _OSM_SA_INFR_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_sa_informinfo_ctrl.h b/trunk/ulp/opensm/user/include/opensm/osm_sa_informinfo_ctrl.h index 69873f70..4c23bd90 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_sa_informinfo_ctrl.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_sa_informinfo_ctrl.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -45,12 +45,10 @@ * $Revision: 1.3 $ */ - #ifndef _OSM_INFR_RCV_CTRL_H_ #define _OSM_INFR_RCV_CTRL_H_ - -#include +#include #include #include #include @@ -83,6 +81,7 @@ BEGIN_C_DECLS * Eitan Zahavi, Mellanox * *********/ + /****s* OpenSM: InformInfo Receive Controller/osm_infr_rcv_ctrl_t * NAME * osm_infr_rcv_ctrl_t @@ -97,11 +96,11 @@ BEGIN_C_DECLS */ typedef struct _osm_infr_rcv_ctrl { - osm_infr_rcv_t *p_rcv; - osm_log_t *p_log; - cl_dispatcher_t *p_disp; + osm_infr_rcv_t *p_rcv; + osm_log_t *p_log; + cl_dispatcher_t *p_disp; cl_disp_reg_handle_t h_disp; - + cl_disp_reg_handle_t h_disp2; } osm_infr_rcv_ctrl_t; /* * FIELDS @@ -132,7 +131,7 @@ typedef struct _osm_infr_rcv_ctrl * SYNOPSIS */ void osm_infr_rcv_ctrl_construct( - IN osm_infr_rcv_ctrl_t* const p_ctrl ); + IN osm_infr_rcv_ctrl_t* const p_ctrl ); /* * PARAMETERS * p_ctrl @@ -146,8 +145,8 @@ void osm_infr_rcv_ctrl_construct( * Allows calling osm_infr_rcv_ctrl_init, osm_infr_rcv_ctrl_destroy, * and osm_infr_rcv_ctrl_is_inited. * -* Calling osm_infr_rcv_ctrl_construct is a prerequisite to calling any other -* method except osm_infr_rcv_ctrl_init. +* Calling osm_infr_rcv_ctrl_construct is a prerequisite to calling any +* other method except osm_infr_rcv_ctrl_init. * * SEE ALSO * InformInfo Receive Controller object, osm_infr_rcv_ctrl_init, @@ -249,7 +248,7 @@ boolean_t osm_infr_rcv_ctrl_is_inited( * * NOTES * The osm_infr_rcv_ctrl_construct or osm_infr_rcv_ctrl_init must be -* called before using this function. +* called before using this function. * * SEE ALSO * InformInfo Receive Controller object, osm_infr_rcv_ctrl_construct, @@ -259,3 +258,4 @@ boolean_t osm_infr_rcv_ctrl_is_inited( END_C_DECLS #endif /* _OSM_INFR_RCV_CTRL_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_sa_lft_record.h b/trunk/ulp/opensm/user/include/opensm/osm_sa_lft_record.h index 83047f26..6b543e66 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_sa_lft_record.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_sa_lft_record.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -45,11 +45,9 @@ * $Revision: 1.4 $ */ - #ifndef _OSM_LFTR_H_ #define _OSM_LFTR_H_ - #include #include #include @@ -86,6 +84,7 @@ BEGIN_C_DECLS * Eitan Zahavi, Mellanox Technologies LTD * *********/ + /****s* OpenSM: Linear Forwarding Table Receiver/osm_lftr_rcv_t * NAME * osm_lftr_rcv_t @@ -101,18 +100,37 @@ BEGIN_C_DECLS typedef struct _osm_lft { osm_subn_t* p_subn; - osm_stats_t* p_stats; + osm_stats_t* p_stats; osm_sa_resp_t* p_resp; osm_mad_pool_t* p_mad_pool; osm_log_t* p_log; cl_plock_t* p_lock; - cl_qlock_pool_t pool; + cl_qlock_pool_t pool; } osm_lftr_rcv_t; /* * FIELDS * p_subn * Pointer to the Subnet object for this subnet. * +* p_stats +* Pointer to the statistics. +* +* p_resp +* Pointer to the SA responder. +* +* p_mad_pool +* Pointer to the mad pool. +* +* p_log +* Pointer to the log object. +* +* p_lock +* Pointer to the serializing lock. +* +* pool +* Pool of linkable Linear Forwarding Table Record objects used to +* generate the query response. +* * SEE ALSO * Linear Forwarding Table Receiver object *********/ @@ -260,3 +278,4 @@ void osm_lftr_rcv_process( END_C_DECLS #endif /* _OSM_LFTR_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_sa_lft_record_ctrl.h b/trunk/ulp/opensm/user/include/opensm/osm_sa_lft_record_ctrl.h index 5ca80cb1..1dd3a837 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_sa_lft_record_ctrl.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_sa_lft_record_ctrl.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -36,7 +36,7 @@ * Abstract: * Declaration of osm_lftr_rcv_ctrl_t. * This object represents a controller that receives the IBA - * LinearForwardingTable attribute from a switch. + * LinearForwardingTable attribute from a switch. * This object is part of the OpenSM family of objects. * * Environment: @@ -45,12 +45,10 @@ * $Revision: 1.4 $ */ - #ifndef _OSM_LFTR_RCV_CTRL_H_ #define _OSM_LFTR_RCV_CTRL_H_ - -#include +#include #include #include #include @@ -72,10 +70,10 @@ BEGIN_C_DECLS * * DESCRIPTION * The Linear Forwarding Table Receive Controller object encapsulates -* the information needed to receive the LinearFowrardingTable attribute +* the information needed to receive the LinearFowardingTable attribute * from a switch node. * -* The Linear Forwarding Table Controller object is thread safe. +* The Linear Forwarding Table Receive Controller object is thread safe. * * This object should be treated as opaque and should be * manipulated only through the provided functions. @@ -99,8 +97,8 @@ BEGIN_C_DECLS */ typedef struct _osm_lftr_rcv_ctrl { - osm_lftr_rcv_t *p_rcv; - osm_log_t *p_log; + osm_lftr_rcv_t *p_rcv; + osm_log_t *p_log; cl_dispatcher_t *p_disp; cl_disp_reg_handle_t h_disp; @@ -232,3 +230,4 @@ ib_api_status_t osm_lftr_rcv_ctrl_init( END_C_DECLS #endif /* _OSM_LFTR_RCV_CTRL_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_sa_link_record.h b/trunk/ulp/opensm/user/include/opensm/osm_sa_link_record.h index 4f8bc440..5c9b291c 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_sa_link_record.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_sa_link_record.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -45,11 +45,9 @@ * $Revision: 1.4 $ */ - #ifndef _OSM_LR_RCV_H_ #define _OSM_LR_RCV_H_ - #include #include #include @@ -115,7 +113,7 @@ typedef struct _osm_lr_rcv * Pointer to the Subnet object for this subnet. * * p_resp -* Pointer to the SA reponder. +* Pointer to the SA responder. * * p_mad_pool * Pointer to the mad pool. @@ -275,3 +273,4 @@ void osm_lr_rcv_process( END_C_DECLS #endif /* _OSM_LR_RCV_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_sa_link_record_ctrl.h b/trunk/ulp/opensm/user/include/opensm/osm_sa_link_record_ctrl.h index 198387ae..2c9355d3 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_sa_link_record_ctrl.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_sa_link_record_ctrl.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -44,12 +44,10 @@ * $Revision: 1.4 $ */ - #ifndef _OSM_LR_CTRL_H_ #define _OSM_LR_CTRL_H_ - -#include +#include #include #include #include @@ -82,6 +80,7 @@ BEGIN_C_DECLS * Ranjit Pandit, Intel * *********/ + /****s* OpenSM: Link Record Receive Controller/osm_lr_rcv_ctrl_t * NAME * osm_lr_rcv_ctrl_t @@ -96,9 +95,9 @@ BEGIN_C_DECLS */ typedef struct _osm_lr_rcv_ctrl { - osm_lr_rcv_t *p_rcv; - osm_log_t *p_log; - cl_dispatcher_t *p_disp; + osm_lr_rcv_t *p_rcv; + osm_log_t *p_log; + cl_dispatcher_t *p_disp; cl_disp_reg_handle_t h_disp; } osm_lr_rcv_ctrl_t; @@ -249,7 +248,7 @@ boolean_t osm_lr_rcv_ctrl_is_inited( * * NOTES * The osm_lr_rcv_ctrl_construct or osm_lr_rcv_ctrl_init must be -* called before using this function. +* called before using this function. * * SEE ALSO * Link Record Receive Controller object, osm_lr_rcv_ctrl_construct, @@ -259,3 +258,4 @@ boolean_t osm_lr_rcv_ctrl_is_inited( END_C_DECLS #endif /* _OSM_LR_CTRL_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_sa_mad_ctrl.h b/trunk/ulp/opensm/user/include/opensm/osm_sa_mad_ctrl.h index 35dfd5f5..378618e5 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_sa_mad_ctrl.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_sa_mad_ctrl.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -45,11 +45,10 @@ * $Revision: 1.4 $ */ - #ifndef _OSM_SA_MAD_CTRL_H_ #define _OSM_SA_MAD_CTRL_H_ -#include +#include #include #include #include @@ -84,6 +83,7 @@ BEGIN_C_DECLS * Ranjit Pandit, Intel * *********/ + /****s* OpenSM: SA MAD Controller/osm_sa_mad_ctrl_t * NAME * osm_sa_mad_ctrl_t @@ -160,15 +160,14 @@ void osm_sa_mad_ctrl_construct( * This function does not return a value. * * NOTES -* Allows calling osm_sa_mad_ctrl_init, osm_sa_mad_ctrl_destroy, -* and osm_sa_mad_ctrl_is_inited. +* Allows calling osm_sa_mad_ctrl_init, and osm_sa_mad_ctrl_destroy. * * Calling osm_sa_mad_ctrl_construct is a prerequisite to calling any other * method except osm_sa_mad_ctrl_init. * * SEE ALSO * SA MAD Controller object, osm_sa_mad_ctrl_init, -* osm_sa_mad_ctrl_destroy, osm_sa_mad_ctrl_is_inited +* osm_sa_mad_ctrl_destroy *********/ /****f* OpenSM: SA MAD Controller/osm_sa_mad_ctrl_destroy @@ -254,7 +253,7 @@ ib_api_status_t osm_sa_mad_ctrl_init( * * SEE ALSO * SA MAD Controller object, osm_sa_mad_ctrl_construct, -* osm_sa_mad_ctrl_destroy, osm_sa_mad_ctrl_is_inited +* osm_sa_mad_ctrl_destroy *********/ /****f* OpenSM: SA/osm_sa_mad_ctrl_bind @@ -350,3 +349,4 @@ osm_sa_mad_ctrl_get_bind_handle( END_C_DECLS #endif /* _OSM_SA_MAD_CTRL_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_sa_mcmember_record.h b/trunk/ulp/opensm/user/include/opensm/osm_sa_mcmember_record.h index ffd6d456..7603f76b 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_sa_mcmember_record.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_sa_mcmember_record.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -45,11 +45,9 @@ * $Revision: 1.7 $ */ - #ifndef _OSM_MCMR_H_ #define _OSM_MCMR_H_ - #include #include #include @@ -87,6 +85,7 @@ BEGIN_C_DECLS * Anil Keshavamurthy, Intel * *********/ + /****s* OpenSM: MCMember Receiver/osm_mcmr_recv_t * NAME * osm_mcmr_recv_t @@ -243,9 +242,9 @@ ib_api_status_t osm_mcmr_rcv_init( * osm_mcmr_rcv_destroy *********/ -/****f* OpenSM: MCMember Receiver/osm_mcmr_mcmrocess +/****f* OpenSM: MCMember Receiver/osm_mcmr_rcv_process * NAME -* osm_mcmr_mcmrocess +* osm_mcmr_rcv_process * * DESCRIPTION * Process the MCMemberRecord attribute. @@ -276,7 +275,7 @@ void osm_mcmr_rcv_process( -/****f* OpenSM: MC Member record Receiver/osm_mcmr_rcv_create_new_mgrp +/****f* OpenSM: MC Member Record Receiver/osm_mcmr_rcv_create_new_mgrp * NAME * osm_mcmr_rcv_create_new_mgrp * @@ -317,6 +316,42 @@ osm_mcmr_rcv_create_new_mgrp( * *********/ +/****f* OpenSM: MC Member Record Receiver/osm_mcmr_rcv_find_or_create_new_mgrp +* NAME +* osm_mcmr_rcv_find_or_create_new_mgrp +* +* DESCRIPTION +* Create new Multicast group +* +* SYNOPSIS +*/ + +ib_api_status_t +osm_mcmr_rcv_find_or_create_new_mgrp( + IN osm_mcmr_recv_t* const p_mcmr, + IN uint64_t comp_mask, + IN ib_member_rec_t* const p_recvd_mcmember_rec, + OUT osm_mgrp_t **pp_mgrp); +/* +* PARAMETERS +* p_mcmr +* [in] Pointer to an osm_mcmr_recv_t object. +* p_recvd_mcmember_rec +* [in] Received Multicast member record +* +* pp_mgrp +* [out] pointer the osm_mgrp_t object +* +* RETURN VALUES +* IB_SUCCESS, IB_ERROR +* +* NOTES +* +* +* SEE ALSO +* +*********/ + #define JOIN_MC_COMP_MASK (IB_MCR_COMPMASK_MGID | \ IB_MCR_COMPMASK_PORT_GID | \ IB_MCR_COMPMASK_JOIN_STATE) @@ -330,39 +365,56 @@ osm_mcmr_rcv_create_new_mgrp( IB_MCR_COMPMASK_FLOW | \ IB_MCR_COMPMASK_SL) -/****d* OpenSM: MC Member record Receiver/OSM_DEFAULT_MGRP_MTU +/****d* OpenSM: MC Member Record Receiver/OSM_DEFAULT_MGRP_MTU * Name * OSM_DEFAULT_MGRP_MTU * * DESCRIPTION -* Default MTU used for new MGRP creation (256 bytes) -* Note it includes the MTUSelector which is set to "Greater Then" -* But this means really greater or equal ... +* Default MTU used for new MGRP creation (2048 bytes) +* Note it includes the MTUSelector which is set to "Greater Than" * * SYNOPSIS */ -#define OSM_DEFAULT_MGRP_MTU 0x01 +#define OSM_DEFAULT_MGRP_MTU 0x04 /***********/ -/****d* OpenSM: MC Member record Receiver/OSM_DEFAULT_MGRP_RATE +/****d* OpenSM: MC Member Record Receiver/OSM_DEFAULT_MGRP_RATE * Name * OSM_DEFAULT_MGRP_RATE * * DESCRIPTION * Default RATE used for new MGRP creation (10Gb/sec) -* Note it includes the RateSelector which is set to "Greater Then" -* But this means really greater or equal ... +* Note it includes the RateSelector which is set to "Greater Than" * * SYNOPSIS */ #define OSM_DEFAULT_MGRP_RATE 0x03 /***********/ -/* These Component Mask fields comply with IB Spec 1.0.M3 */ -#define MC_FULL_MEMBER 0x1 -#define MC_NON_MEMBER 0x2 +/* Scope component definitions from IBA 1.2 (Table 3 p. 146) */ +#define MC_SCOPE_LINK_LOCAL 0x2 +#define MC_SCOPE_SITE_LOCAL 0x5 +#define MC_SCOPE_ORG_LOCAL 0x8 +#define MC_SCOPE_GLOBAL 0xE + +/****d* OpenSM: MC Member Record Receiver/OSM_DEFAULT_MGRP_SCOPE +* Name +* OSM_DEFAULT_MGRP_SCOPE +* +* DESCRIPTION +* Default SCOPE used for new MGRP creation (link local) +* +* SYNOPSIS +*/ +#define OSM_DEFAULT_MGRP_SCOPE MC_SCOPE_LINK_LOCAL +/***********/ + +/* JoinState definitions from IBA 1.2 */ +#define MC_FULL_MEMBER 0x1 +#define MC_NON_MEMBER 0x2 #define MC_SENDONLY_NON_MEMBER 0x4 END_C_DECLS #endif /* _OSM_MCMR_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_sa_mcmember_record_ctrl.h b/trunk/ulp/opensm/user/include/opensm/osm_sa_mcmember_record_ctrl.h index 6b558f9d..22c5606b 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_sa_mcmember_record_ctrl.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_sa_mcmember_record_ctrl.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -49,8 +49,7 @@ #ifndef _OSM_MCMRCTRL_H #define _OSM_MCMRCTRL_H - -#include +#include #include #include #include @@ -83,6 +82,7 @@ BEGIN_C_DECLS * Ranjit Pandit, Intel * *********/ + /****s* OpenSM: MCMember Receive Controller/osm_mcmr_rcv_ctrl_t * NAME * osm_mcmr_rcv_ctrl_t @@ -97,9 +97,9 @@ BEGIN_C_DECLS */ typedef struct _osm_mcmr_rcv_ctrl { - osm_mcmr_recv_t *p_rcv; - osm_log_t *p_log; - cl_dispatcher_t *p_disp; + osm_mcmr_recv_t *p_rcv; + osm_log_t *p_log; + cl_dispatcher_t *p_disp; cl_disp_reg_handle_t h_disp; } osm_mcmr_rcv_ctrl_t; @@ -249,7 +249,7 @@ boolean_t osm_mcmr_ctrl_is_inited( * * NOTES * The osm_mcmr_rcv_ctrl_construct or osm_mcmr_rcv_ctrl_init must be -* called before using this function. +* called before using this function. * * SEE ALSO * MCMember Receive Controller object, osm_mcmr_rcv_ctrl_construct, @@ -259,3 +259,4 @@ boolean_t osm_mcmr_ctrl_is_inited( END_C_DECLS #endif /* _OSM_MCMRCTRL_H */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_sa_multipath_record.h b/trunk/ulp/opensm/user/include/opensm/osm_sa_multipath_record.h new file mode 100644 index 00000000..b55cfb09 --- /dev/null +++ b/trunk/ulp/opensm/user/include/opensm/osm_sa_multipath_record.h @@ -0,0 +1,273 @@ +/* + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. + * + * This software is available to you under the OpenIB.org BSD license + * below: + * + * Redistribution and use in source and binary forms, with or + * without modification, are permitted provided that the following + * conditions are met: + * + * - Redistributions of source code must retain the above + * copyright notice, this list of conditions and the following + * disclaimer. + * + * - Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials + * provided with the distribution. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS + * BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN + * ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN + * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + * + * $Id$ + */ + + +/* + * Abstract: + * Declaration of osm_mpr_rcv_t. + * This object represents the MultiPathRecord Receiver object. + * attribute from a node. + * This object is part of the OpenSM family of objects. + * + * Environment: + * Linux User Mode + * + */ + +#ifndef _OSM_MPR_RCV_H_ +#define _OSM_MPR_RCV_H_ + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#ifdef __cplusplus +# define BEGIN_C_DECLS extern "C" { +# define END_C_DECLS } +#else /* !__cplusplus */ +# define BEGIN_C_DECLS +# define END_C_DECLS +#endif /* __cplusplus */ + +BEGIN_C_DECLS + +/****h* OpenSM/MultiPath Record Receiver +* NAME +* MultiPath Record Receiver +* +* DESCRIPTION +* The MultiPath Record Receiver object encapsulates the information +* needed to receive the PathRecord request from a node. +* +* The MultiPath Record Receiver object is thread safe. +* +* This object should be treated as opaque and should be +* manipulated only through the provided functions. +* +* AUTHOR +* Hal Rosenstock, Voltaire +* +*********/ + +/****s* OpenSM: MultiPath Record Receiver/osm_mpr_rcv_t +* NAME +* osm_mpr_rcv_t +* +* DESCRIPTION +* MultiPath Record Receiver structure. +* +* This object should be treated as opaque and should +* be manipulated only through the provided functions. +* +* SYNOPSIS +*/ +typedef struct _osm_mpr_rcv +{ + osm_subn_t *p_subn; + osm_sa_resp_t *p_resp; + osm_mad_pool_t *p_mad_pool; + osm_log_t *p_log; + cl_plock_t *p_lock; + cl_qlock_pool_t pr_pool; +} osm_mpr_rcv_t; +/* +* FIELDS +* p_subn +* Pointer to the Subnet object for this subnet. +* +* p_gen_req_ctrl +* Pointer to the generic request controller. +* +* p_log +* Pointer to the log object. +* +* p_lock +* Pointer to the serializing lock. +* +* pr_pool +* Pool of multipath record objects used to generate query responses. +* +* SEE ALSO +* MultiPath Record Receiver object +*********/ + +/****f* OpenSM: MultiPath Record Receiver/osm_mpr_rcv_construct +* NAME +* osm_mpr_rcv_construct +* +* DESCRIPTION +* This function constructs a MultiPath Record Receiver object. +* +* SYNOPSIS +*/ +void +osm_mpr_rcv_construct( + IN osm_mpr_rcv_t* const p_rcv ); +/* +* PARAMETERS +* p_rcv +* [in] Pointer to a MultiPath Record Receiver object to construct. +* +* RETURN VALUE +* This function does not return a value. +* +* NOTES +* Allows calling osm_mpr_rcv_init, osm_mpr_rcv_destroy +* +* Calling osm_mpr_rcv_construct is a prerequisite to calling any other +* method except osm_mpr_rcv_init. +* +* SEE ALSO +* MultiPath Record Receiver object, osm_mpr_rcv_init, osm_mpr_rcv_destroy +*********/ + +/****f* OpenSM: MultiPath Record Receiver/osm_mpr_rcv_destroy +* NAME +* osm_mpr_rcv_destroy +* +* DESCRIPTION +* The osm_mpr_rcv_destroy function destroys the object, releasing +* all resources. +* +* SYNOPSIS +*/ +void +osm_mpr_rcv_destroy( + IN osm_mpr_rcv_t* const p_rcv ); +/* +* PARAMETERS +* p_rcv +* [in] Pointer to the object to destroy. +* +* RETURN VALUE +* This function does not return a value. +* +* NOTES +* Performs any necessary cleanup of the specified +* MultiPath Record Receiver object. +* Further operations should not be attempted on the destroyed object. +* This function should only be called after a call to +* osm_mpr_rcv_construct or osm_mpr_rcv_init. +* +* SEE ALSO +* MultiPath Record Receiver object, osm_mpr_rcv_construct, +* osm_mpr_rcv_init +*********/ + +/****f* OpenSM: MultiPath Record Receiver/osm_mpr_rcv_init +* NAME +* osm_mpr_rcv_init +* +* DESCRIPTION +* The osm_mpr_rcv_init function initializes a +* MultiPath Record Receiver object for use. +* +* SYNOPSIS +*/ +ib_api_status_t +osm_mpr_rcv_init( + IN osm_mpr_rcv_t* const p_rcv, + IN osm_sa_resp_t* const p_resp, + IN osm_mad_pool_t* const p_mad_pool, + IN osm_subn_t* const p_subn, + IN osm_log_t* const p_log, + IN cl_plock_t* const p_lock ); +/* +* PARAMETERS +* p_rcv +* [in] Pointer to an osm_mpr_rcv_t object to initialize. +* +* p_subn +* [in] Pointer to the Subnet object for this subnet. +* +* p_log +* [in] Pointer to the log object. +* +* p_lock +* [in] Pointer to the OpenSM serializing lock. +* +* RETURN VALUES +* IB_SUCCESS if the MultiPath Record Receiver object was initialized +* successfully. +* +* NOTES +* Allows calling other MultiPath Record Receiver methods. +* +* SEE ALSO +* MultiPath Record Receiver object, osm_mpr_rcv_construct, +* osm_mpr_rcv_destroy +*********/ + +/****f* OpenSM: MultiPath Record Receiver/osm_mpr_rcv_process +* NAME +* osm_mpr_rcv_process +* +* DESCRIPTION +* Process the MultiPathRecord request. +* +* SYNOPSIS +*/ +void +osm_mpr_rcv_process( + IN osm_mpr_rcv_t* const p_rcv, + IN osm_madw_t* const p_madw ); +/* +* PARAMETERS +* p_rcv +* [in] Pointer to an osm_mpr_rcv_t object. +* +* p_madw +* [in] Pointer to the MAD Wrapper containing the MAD +* that contains the node's MultiPathRecord attribute. +* +* RETURN VALUES +* IB_SUCCESS if the MultiPathRecord processing was successful. +* +* NOTES +* This function processes a MultiPathRecord attribute. +* +* SEE ALSO +* MultiPath Record Receiver, Node Info Response Controller +*********/ + +END_C_DECLS + +#endif /* _OSM_MPR_RCV_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_sa_multipath_record_ctrl.h b/trunk/ulp/opensm/user/include/opensm/osm_sa_multipath_record_ctrl.h new file mode 100644 index 00000000..090dc9e8 --- /dev/null +++ b/trunk/ulp/opensm/user/include/opensm/osm_sa_multipath_record_ctrl.h @@ -0,0 +1,260 @@ +/* + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. + * + * This software is available to you under the OpenIB.org BSD license + * below: + * + * Redistribution and use in source and binary forms, with or + * without modification, are permitted provided that the following + * conditions are met: + * + * - Redistributions of source code must retain the above + * copyright notice, this list of conditions and the following + * disclaimer. + * + * - Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials + * provided with the distribution. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS + * BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN + * ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN + * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + * + * $Id$ + */ + + +/* + * Abstract: + * Declaration of osm_mpr_rcv_ctrl_t. + * This object represents a controller that receives the IBA + * MultiPathRecord attribute from a node. + * This object is part of the OpenSM family of objects. + * + * Environment: + * Linux User Mode + * + */ + +#ifndef _OSM_MPRCTRL_H_ +#define _OSM_MPRCTRL_H_ + +#include +#include +#include +#include +#include + +#ifdef __cplusplus +# define BEGIN_C_DECLS extern "C" { +# define END_C_DECLS } +#else /* !__cplusplus */ +# define BEGIN_C_DECLS +# define END_C_DECLS +#endif /* __cplusplus */ + +BEGIN_C_DECLS + +/****h* OpenSM/MultiPath Record Receive Controller +* NAME +* MultiPath Record Receive Controller +* +* DESCRIPTION +* The MultiPath Record Receive Controller object encapsulates +* the information needed to receive the MultiPathRecord attribute from a node. +* +* The MultiPath record Receive Controller object is thread safe. +* +* This object should be treated as opaque and should be +* manipulated only through the provided functions. +* +* AUTHOR +* Hal Rosenstock, Voltaire +* +*********/ + +/****s* OpenSM: MultiPath Record Receive Controller/osm_mpr_rcv_ctrl_t +* NAME +* osm_mpr_rcv_ctrl_t +* +* DESCRIPTION +* MultiPath Record Receive Controller structure. +* +* This object should be treated as opaque and should +* be manipulated only through the provided functions. +* +* SYNOPSIS +*/ +typedef struct _osm_mpr_rcv_ctrl +{ + osm_mpr_rcv_t *p_rcv; + osm_log_t *p_log; + cl_dispatcher_t *p_disp; + cl_disp_reg_handle_t h_disp; + +} osm_mpr_rcv_ctrl_t; +/* +* FIELDS +* p_rcv +* Pointer to the MultiPath Record Receiver object. +* +* p_log +* Pointer to the log object. +* +* p_disp +* Pointer to the Dispatcher. +* +* h_disp +* Handle returned from dispatcher registration. +* +* SEE ALSO +* MultiPath Record Receive Controller object +* MultiPath Record Receiver object +*********/ + +/****f* OpenSM: MultiPath Record Receive Controller/osm_pr_rcv_ctrl_construct +* NAME +* osm_mpr_rcv_ctrl_construct +* +* DESCRIPTION +* This function constructs a MultiPath Record Receive Controller object. +* +* SYNOPSIS +*/ +void osm_mpr_rcv_ctrl_construct( + IN osm_mpr_rcv_ctrl_t* const p_ctrl ); +/* +* PARAMETERS +* p_ctrl +* [in] Pointer to a MultiPath Record Receive Controller +* object to construct. +* +* RETURN VALUE +* This function does not return a value. +* +* NOTES +* Allows calling osm_mpr_rcv_ctrl_init, osm_mpr_rcv_ctrl_destroy, +* and osm_mpr_rcv_ctrl_is_inited. +* +* Calling osm_mpr_rcv_ctrl_construct is a prerequisite to calling any +* other method except osm_mpr_rcv_ctrl_init. +* +* SEE ALSO +* MultiPath Record Receive Controller object, osm_mpr_rcv_ctrl_init, +* osm_mpr_rcv_ctrl_destroy, osm_mpr_rcv_ctrl_is_inited +*********/ + +/****f* OpenSM: MultiPath Record Receive Controller/osm_mpr_rcv_ctrl_destroy +* NAME +* osm_mpr_rcv_ctrl_destroy +* +* DESCRIPTION +* The osm_mpr_rcv_ctrl_destroy function destroys the object, releasing +* all resources. +* +* SYNOPSIS +*/ +void osm_mpr_rcv_ctrl_destroy( + IN osm_mpr_rcv_ctrl_t* const p_ctrl ); +/* +* PARAMETERS +* p_ctrl +* [in] Pointer to the object to destroy. +* +* RETURN VALUE +* This function does not return a value. +* +* NOTES +* Performs any necessary cleanup of the specified +* MultiPath Record Receive Controller object. +* Further operations should not be attempted on the destroyed object. +* This function should only be called after a call to +* osm_mpr_rcv_ctrl_construct or osm_mpr_rcv_ctrl_init. +* +* SEE ALSO +* MultiPath Record Receive Controller object, osm_mpr_rcv_ctrl_construct, +* osm_mpr_rcv_ctrl_init +*********/ + +/****f* OpenSM: MultiPath Record Receive Controller/osm_mpr_rcv_ctrl_init +* NAME +* osm_mpr_rcv_ctrl_init +* +* DESCRIPTION +* The osm_mpr_rcv_ctrl_init function initializes a +* MultiPath Record Receive Controller object for use. +* +* SYNOPSIS +*/ +ib_api_status_t osm_mpr_rcv_ctrl_init( + IN osm_mpr_rcv_ctrl_t* const p_ctrl, + IN osm_mpr_rcv_t* const p_rcv, + IN osm_log_t* const p_log, + IN cl_dispatcher_t* const p_disp ); +/* +* PARAMETERS +* p_ctrl +* [in] Pointer to an osm_mpr_rcv_ctrl_t object to initialize. +* +* p_rcv +* [in] Pointer to an osm_mpr_t object. +* +* p_log +* [in] Pointer to the log object. +* +* p_disp +* [in] Pointer to the OpenSM central Dispatcher. +* +* RETURN VALUES +* CL_SUCCESS if the MultiPath Record Receive Controller object was +* initialized successfully. +* +* NOTES +* Allows calling other MultiPath Record Receive Controller methods. +* +* SEE ALSO +* MultiPath Record Receive Controller object, osm_pr_rcv_ctrl_construct, +* osm_mpr_rcv_ctrl_destroy, osm_mpr_rcv_ctrl_is_inited +*********/ + +/****f* OpenSM: MultiPath Record Receive Controller/osm_mpr_rcv_ctrl_is_inited +* NAME +* osm_mpr_rcv_ctrl_is_inited +* +* DESCRIPTION +* Indicates if the object has been initialized with osm_mpr_rcv_ctrl_init. +* +* SYNOPSIS +*/ +boolean_t osm_mpr_rcv_ctrl_is_inited( + IN const osm_mpr_rcv_ctrl_t* const p_ctrl ); +/* +* PARAMETERS +* p_ctrl +* [in] Pointer to an osm_mpr_rcv_ctrl_t object. +* +* RETURN VALUES +* TRUE if the object was initialized successfully, +* FALSE otherwise. +* +* NOTES +* The osm_mpr_rcv_ctrl_construct or osm_mpr_rcv_ctrl_init must be +* called before using this function. +* +* SEE ALSO +* MultiPath Record Receive Controller object, osm_mpr_rcv_ctrl_construct, +* osm_mpr_rcv_ctrl_init +*********/ + +END_C_DECLS + +#endif /* _OSM_MPRCTRL_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_sa_node_record.h b/trunk/ulp/opensm/user/include/opensm/osm_sa_node_record.h index 5d41ed22..6af9e2bc 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_sa_node_record.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_sa_node_record.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -45,7 +45,6 @@ * $Revision: 1.4 $ */ - #ifndef _OSM_NR_H_ #define _OSM_NR_H_ @@ -84,6 +83,7 @@ BEGIN_C_DECLS * Anil S Keshavamurthy, Intel * *********/ + /****s* OpenSM: Node Record Receiver/osm_nr_rcv_t * NAME * osm_nr_rcv_t @@ -112,7 +112,7 @@ typedef struct _osm_nr_recv * Pointer to the Subnet object for this subnet. * * p_resp -* Pointer to the SA reponder. +* Pointer to the SA responder. * * p_mad_pool * Pointer to the mad pool. @@ -272,3 +272,4 @@ void osm_nr_rcv_process( END_C_DECLS #endif /* _OSM_NR_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_sa_node_record_ctrl.h b/trunk/ulp/opensm/user/include/opensm/osm_sa_node_record_ctrl.h index 2da33ee7..681e20ff 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_sa_node_record_ctrl.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_sa_node_record_ctrl.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -45,12 +45,10 @@ * $Revision: 1.4 $ */ - #ifndef _OSM_NR_CTRL_H_ #define _OSM_NR_CTRL_H_ - -#include +#include #include #include #include @@ -83,6 +81,7 @@ BEGIN_C_DECLS * Anil S Keshavamurthy, Intel * *********/ + /****s* OpenSM: Node Record Receive Controller/osm_nr_rcv_ctrl_t * NAME * osm_nr_rcv_ctrl_t @@ -229,3 +228,4 @@ ib_api_status_t osm_nr_rcv_ctrl_init( END_C_DECLS #endif /* _OSM_NR_CTRL_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_sa_path_record.h b/trunk/ulp/opensm/user/include/opensm/osm_sa_path_record.h index 0ce7ac25..30a6289e 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_sa_path_record.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_sa_path_record.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -45,11 +45,9 @@ * $Revision: 1.4 $ */ - #ifndef _OSM_PR_H_ #define _OSM_PR_H_ - #include #include #include @@ -88,6 +86,7 @@ BEGIN_C_DECLS * Steve King, Intel * *********/ + /****s* OpenSM: Path Record Receiver/osm_pr_rcv_t * NAME * osm_pr_rcv_t @@ -102,13 +101,12 @@ BEGIN_C_DECLS */ typedef struct _osm_pr_rcv { - osm_subn_t *p_subn; + osm_subn_t *p_subn; osm_sa_resp_t *p_resp; osm_mad_pool_t *p_mad_pool; - osm_log_t *p_log; - cl_plock_t *p_lock; + osm_log_t *p_log; + cl_plock_t *p_lock; cl_qlock_pool_t pr_pool; - } osm_pr_rcv_t; /* * FIELDS @@ -273,3 +271,4 @@ osm_pr_rcv_process( END_C_DECLS #endif /* _OSM_PR_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_sa_path_record_ctrl.h b/trunk/ulp/opensm/user/include/opensm/osm_sa_path_record_ctrl.h index 1fadacbc..1b7f9052 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_sa_path_record_ctrl.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_sa_path_record_ctrl.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -45,12 +45,10 @@ * $Revision: 1.4 $ */ - #ifndef _OSM_PRCTRL_H_ #define _OSM_PRCTRL_H_ - -#include +#include #include #include #include @@ -83,6 +81,7 @@ BEGIN_C_DECLS * Ranjit Pandit, Intel * *********/ + /****s* OpenSM: Path Record Receive Controller/osm_pr_rcv_ctrl_t * NAME * osm_pr_rcv_ctrl_t @@ -259,3 +258,4 @@ boolean_t osm_pr_rcv_ctrl_is_inited( END_C_DECLS #endif /* _OSM_PRCTRL_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_sa_pkey_record.h b/trunk/ulp/opensm/user/include/opensm/osm_sa_pkey_record.h index 89362e8d..a3c016bc 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_sa_pkey_record.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_sa_pkey_record.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,11 +32,9 @@ */ - #ifndef _OSM_PKEY_REC_RCV_H_ #define _OSM_PKEY_REC_RCV_H_ - #include #include #include @@ -73,6 +71,7 @@ BEGIN_C_DECLS * Yael Kalka, Mellanox * *********/ + /****s* OpenSM: P_Key Record Receiver/osm_pkey_rec_rcv_t * NAME * osm_pkey_rec_rcv_t @@ -101,7 +100,7 @@ typedef struct _osm_pkey_rec_rcv * Pointer to the Subnet object for this subnet. * * p_resp -* Pointer to the SA reponder. +* Pointer to the SA responder. * * p_mad_pool * Pointer to the mad pool. @@ -266,3 +265,4 @@ osm_pkey_rec_rcv_process( END_C_DECLS #endif /* _OSM_PKEY_REC_RCV_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_sa_pkey_record_ctrl.h b/trunk/ulp/opensm/user/include/opensm/osm_sa_pkey_record_ctrl.h index b71f33a1..3c861b20 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_sa_pkey_record_ctrl.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_sa_pkey_record_ctrl.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,12 +32,10 @@ */ - #ifndef _OSM_PKEY_REC_CTRL_H_ #define _OSM_PKEY_REC_CTRL_H_ - -#include +#include #include #include #include @@ -70,6 +68,7 @@ BEGIN_C_DECLS * Yael Kalka, Mellanox * *********/ + /****s* OpenSM: P_Key Record Receive Controller/osm_pkey_rec_rcv_ctrl_t * NAME * osm_pkey_rec_rcv_ctrl_t @@ -216,3 +215,4 @@ ib_api_status_t osm_pkey_rec_rcv_ctrl_init( END_C_DECLS #endif /* _OSM_PKEY_REC_CTRL_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_sa_portinfo_record.h b/trunk/ulp/opensm/user/include/opensm/osm_sa_portinfo_record.h index 960b0ee1..242d52eb 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_sa_portinfo_record.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_sa_portinfo_record.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -45,11 +45,9 @@ * $Revision: 1.4 $ */ - #ifndef _OSM_PIR_RCV_H_ #define _OSM_PIR_RCV_H_ - #include #include #include @@ -86,6 +84,7 @@ BEGIN_C_DECLS * Ranjit Pandit, Intel * *********/ + /****s* OpenSM: PortInfo Record Receiver/osm_pir_rcv_t * NAME * osm_pir_rcv_t @@ -100,13 +99,12 @@ BEGIN_C_DECLS */ typedef struct _osm_pir_rcv { - const osm_subn_t *p_subn; + osm_subn_t *p_subn; osm_sa_resp_t *p_resp; osm_mad_pool_t *p_mad_pool; - osm_log_t *p_log; - cl_plock_t *p_lock; - cl_qlock_pool_t pool; - + osm_log_t *p_log; + cl_plock_t *p_lock; + cl_qlock_pool_t pool; } osm_pir_rcv_t; /* * FIELDS @@ -114,7 +112,7 @@ typedef struct _osm_pir_rcv * Pointer to the Subnet object for this subnet. * * p_resp -* Pointer to the SA reponder. +* Pointer to the SA responder. * * p_mad_pool * Pointer to the mad pool. @@ -212,7 +210,7 @@ osm_pir_rcv_init( IN osm_pir_rcv_t* const p_rcv, IN osm_sa_resp_t* const p_resp, IN osm_mad_pool_t* const p_mad_pool, - IN const osm_subn_t* const p_subn, + IN osm_subn_t* const p_subn, IN osm_log_t* const p_log, IN cl_plock_t* const p_lock ); /* @@ -279,3 +277,4 @@ osm_pir_rcv_process( END_C_DECLS #endif /* _OSM_PIR_RCV_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_sa_portinfo_record_ctrl.h b/trunk/ulp/opensm/user/include/opensm/osm_sa_portinfo_record_ctrl.h index 4db1352b..a8ee2b80 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_sa_portinfo_record_ctrl.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_sa_portinfo_record_ctrl.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -45,12 +45,10 @@ * $Revision: 1.4 $ */ - #ifndef _OSM_PIR_CTRL_H_ #define _OSM_PIR_CTRL_H_ - -#include +#include #include #include #include @@ -83,6 +81,7 @@ BEGIN_C_DECLS * Ranjit Pandit, Intel * *********/ + /****s* OpenSM: PortInfo Record Receive Controller/osm_pir_rcv_ctrl_t * NAME * osm_pir_rcv_ctrl_t @@ -229,3 +228,4 @@ ib_api_status_t osm_pir_rcv_ctrl_init( END_C_DECLS #endif /* _OSM_PIR_CTRL_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_sa_response.h b/trunk/ulp/opensm/user/include/opensm/osm_sa_response.h index fcfabe95..7d691609 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_sa_response.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_sa_response.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -44,7 +44,6 @@ * $Revision: 1.4 $ */ - #ifndef _OSM_SA_RESP_H_ #define _OSM_SA_RESP_H_ @@ -81,6 +80,7 @@ BEGIN_C_DECLS * Steve King, Intel * *********/ + /****s* OpenSM: SA Response/osm_sa_resp_t * NAME * osm_sa_resp_t @@ -96,8 +96,7 @@ BEGIN_C_DECLS typedef struct _osm_sa_resp { osm_mad_pool_t *p_pool; - osm_log_t *p_log; - + osm_log_t *p_log; } osm_sa_resp_t; /* * FIELDS @@ -129,15 +128,14 @@ osm_sa_resp_construct( * This function does not return a value. * * NOTES -* Allows calling osm_sa_resp_init, osm_sa_resp_destroy, -* and osm_sa_resp_is_inited. +* Allows calling osm_sa_resp_init, and osm_sa_resp_destroy. * * Calling osm_sa_resp_construct is a prerequisite to calling any other * method except osm_sa_resp_init. * * SEE ALSO * SA Response object, osm_sa_resp_init, -* osm_sa_resp_destroy, osm_sa_resp_is_inited +* osm_sa_resp_destroy *********/ /****f* OpenSM: SA Response/osm_sa_resp_destroy @@ -211,7 +209,7 @@ osm_sa_resp_init( * * SEE ALSO * SA Response object, osm_sa_resp_construct, -* osm_sa_resp_destroy, osm_sa_resp_is_inited +* osm_sa_resp_destroy *********/ /****f* IBA Base: Types/osm_sa_send_error @@ -226,7 +224,7 @@ osm_sa_resp_init( */ void osm_sa_send_error( - IN osm_sa_resp_t* const p_resp, + IN osm_sa_resp_t* const p_resp, IN const osm_madw_t* const p_madw, IN const ib_net16_t sa_status ); /* @@ -248,9 +246,10 @@ osm_sa_send_error( * * SEE ALSO * SA Response object, osm_sa_resp_construct, -* osm_sa_resp_destroy, osm_sa_resp_is_inited +* osm_sa_resp_destroy *********/ END_C_DECLS #endif /* _OSM_SA_RESP_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_sa_service_record.h b/trunk/ulp/opensm/user/include/opensm/osm_sa_service_record.h index e3d9d828..baa15fae 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_sa_service_record.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_sa_service_record.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -45,11 +45,9 @@ * $Revision: 1.4 $ */ - #ifndef _OSM_SR_H_ #define _OSM_SR_H_ - #include #include #include @@ -88,6 +86,7 @@ BEGIN_C_DECLS * Anil S Keshavamurthy * *********/ + /****s* OpenSM: Service Record Receiver/osm_sr_rcv_t * NAME * osm_sr_rcv_t @@ -296,3 +295,4 @@ osm_sr_rcv_lease_cb( END_C_DECLS #endif /* _OSM_SR_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_sa_service_record_ctrl.h b/trunk/ulp/opensm/user/include/opensm/osm_sa_service_record_ctrl.h index 464a28ee..f784090e 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_sa_service_record_ctrl.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_sa_service_record_ctrl.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -45,12 +45,10 @@ * $Revision: 1.4 $ */ - #ifndef _OSM_SRCTRL_H_ #define _OSM_SRCTRL_H_ - -#include +#include #include #include #include @@ -83,6 +81,7 @@ BEGIN_C_DECLS * Anil S Keshavamurthy, Intel * *********/ + /****s* OpenSM: Service Record Receive Controller/osm_sr_rcv_ctrl_t * NAME * osm_sr_rcv_ctrl_t @@ -228,3 +227,4 @@ ib_api_status_t osm_sr_rcv_ctrl_init( END_C_DECLS #endif /* _OSM_SRCTRL_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_sa_slvl_record.h b/trunk/ulp/opensm/user/include/opensm/osm_sa_slvl_record.h index 9a5de461..3f1abfff 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_sa_slvl_record.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_sa_slvl_record.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -45,11 +45,9 @@ * $Revision: 1.3 $ */ - #ifndef _OSM_SLVL_REC_RCV_H_ #define _OSM_SLVL_REC_RCV_H_ - #include #include #include @@ -86,6 +84,7 @@ BEGIN_C_DECLS * Eitan Zahavi, Mellanox * *********/ + /****s* OpenSM: SLtoVL Mapping Record Receiver/osm_slvl_rec_rcv_t * NAME * osm_slvl_rec_rcv_t @@ -114,7 +113,7 @@ typedef struct _osm_slvl_rec_rcv * Pointer to the Subnet object for this subnet. * * p_resp -* Pointer to the SA reponder. +* Pointer to the SA responder. * * p_mad_pool * Pointer to the mad pool. @@ -279,3 +278,4 @@ osm_slvl_rec_rcv_process( END_C_DECLS #endif /* _OSM_SLVL_REC_RCV_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_sa_slvl_record_ctrl.h b/trunk/ulp/opensm/user/include/opensm/osm_sa_slvl_record_ctrl.h index 0acfc624..ae02bba1 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_sa_slvl_record_ctrl.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_sa_slvl_record_ctrl.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -45,12 +45,10 @@ * $Revision: 1.3 $ */ - #ifndef _OSM_SLVL_REC_CTRL_H_ #define _OSM_SLVL_REC_CTRL_H_ - -#include +#include #include #include #include @@ -83,6 +81,7 @@ BEGIN_C_DECLS * Eitan Zahavi, Mellanox * *********/ + /****s* OpenSM: SLtoVL Mapping Record Receive Controller/osm_slvl_rec_rcv_ctrl_t * NAME * osm_slvl_rec_rcv_ctrl_t @@ -229,3 +228,4 @@ ib_api_status_t osm_slvl_rec_rcv_ctrl_init( END_C_DECLS #endif /* _OSM_SLVL_REC_CTRL_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_sa_sminfo_record.h b/trunk/ulp/opensm/user/include/opensm/osm_sa_sminfo_record.h index e472a19b..d9dabcb3 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_sa_sminfo_record.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_sa_sminfo_record.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -45,11 +45,9 @@ * $Revision: 1.4 $ */ - #ifndef _OSM_SMIR_H_ #define _OSM_SMIR_H_ - #include #include #include @@ -100,13 +98,13 @@ BEGIN_C_DECLS */ typedef struct _osm_smir { - osm_subn_t* p_subn; + osm_subn_t* p_subn; osm_stats_t* p_stats; osm_sa_resp_t* p_resp; osm_mad_pool_t* p_mad_pool; - osm_log_t* p_log; - cl_plock_t* p_lock; - + osm_log_t* p_log; + cl_plock_t* p_lock; + cl_qlock_pool_t pool; } osm_smir_rcv_t; /* * FIELDS @@ -257,18 +255,8 @@ void osm_smir_rcv_process( * SEE ALSO * SM Info Receiver, SM Info Response Controller *********/ -#if 0 -/* - These Component Mask fields comply with IB Spec 1.0.M3 -*/ -#define SMIR_LID_COMPMASK 0x1 -#define SMIR_GUID_COMPMASK 0x4 -#define SMIR_SMKEY_COMPMASK 0x8 -#define SMIR_ACTCOUNT_COMPMASK 0x10 -#define SMIR_PRIORITY_COMPMASK 0x20 -#define SMIR_STATE_COMPMASK 0x40 -#endif END_C_DECLS #endif /* _OSM_SMIR_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_sa_sminfo_record_ctrl.h b/trunk/ulp/opensm/user/include/opensm/osm_sa_sminfo_record_ctrl.h index 8b2fc4e6..28aae4dd 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_sa_sminfo_record_ctrl.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_sa_sminfo_record_ctrl.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -45,12 +45,10 @@ * $Revision: 1.4 $ */ - #ifndef _OSM_SMIR_CTRL_H_ #define _OSM_SMIR_CTRL_H_ - -#include +#include #include #include #include @@ -83,6 +81,7 @@ BEGIN_C_DECLS * Ranjit Pandit, Intel * *********/ + /****s* OpenSM: SM Info Receive Controller/osm_smir_ctrl_t * NAME * osm_smir_ctrl_t @@ -229,3 +228,4 @@ ib_api_status_t osm_smir_ctrl_init( END_C_DECLS #endif /* _OSM_SMIR_CTRL_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_sa_sw_info_record.h b/trunk/ulp/opensm/user/include/opensm/osm_sa_sw_info_record.h new file mode 100644 index 00000000..e8cf0bb0 --- /dev/null +++ b/trunk/ulp/opensm/user/include/opensm/osm_sa_sw_info_record.h @@ -0,0 +1,306 @@ +/* + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. + * + * This software is available to you under the OpenIB.org BSD license + * below: + * + * Redistribution and use in source and binary forms, with or + * without modification, are permitted provided that the following + * conditions are met: + * + * - Redistributions of source code must retain the above + * copyright notice, this list of conditions and the following + * disclaimer. + * + * - Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials + * provided with the distribution. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS + * BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN + * ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN + * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + * + * $Id$ + */ + + +/* + * Abstract: + * Declaration of osm_sir_rcv_t. + * This object represents the SwitchInfo Receiver object. + * attribute from a switch node. + * This object is part of the OpenSM family of objects. + * + * Environment: + * Linux User Mode + * + */ + +#ifndef _OSM_SIR_RCV_H_ +#define _OSM_SIR_RCV_H_ + +#include +#include +#include +#include +#include +#include +#include +#include + +#ifdef __cplusplus +# define BEGIN_C_DECLS extern "C" { +# define END_C_DECLS } +#else /* !__cplusplus */ +# define BEGIN_C_DECLS +# define END_C_DECLS +#endif /* __cplusplus */ + +BEGIN_C_DECLS + +/****h* OpenSM/Switch Info Receiver +* NAME +* Switch Info Receiver +* +* DESCRIPTION +* The Switch Info Receiver object encapsulates the information +* needed to receive the SwitchInfo attribute from a switch node. +* +* The Switch Info Receiver object is thread safe. +* +* This object should be treated as opaque and should be +* manipulated only through the provided functions. +* +* AUTHOR +* Hal Rosenstock, Voltaire +* +*********/ + +/****s* OpenSM: Switch Info Receiver/osm_sir_rcv_t +* NAME +* osm_sir_rcv_t +* +* DESCRIPTION +* Switch Info Receiver structure. +* +* This object should be treated as opaque and should +* be manipulated only through the provided functions. +* +* SYNOPSIS +*/ +typedef struct _osm_sir_rcv +{ + osm_subn_t *p_subn; + osm_sa_resp_t *p_resp; + osm_mad_pool_t *p_mad_pool; + osm_log_t *p_log; + osm_req_t *p_req; + osm_state_mgr_t *p_state_mgr; + cl_plock_t *p_lock; + cl_qlock_pool_t pool; +} osm_sir_rcv_t; +/* +* FIELDS +* p_subn +* Pointer to the Subnet object for this subnet. +* +* p_log +* Pointer to the log object. +* +* p_req +* Pointer to the Request object. +* +* p_state_mgr +* Pointer to the State Manager object. +* +* p_lock +* Pointer to the serializing lock. +* +* SEE ALSO +* Switch Info Receiver object +*********/ + +/****f* OpenSM: Switch Info Receiver/osm_sir_rcv_construct +* NAME +* osm_sir_rcv_construct +* +* DESCRIPTION +* This function constructs a Switch Info Receiver object. +* +* SYNOPSIS +*/ +void osm_sir_rcv_construct( + IN osm_sir_rcv_t* const p_ctrl ); +/* +* PARAMETERS +* p_ctrl +* [in] Pointer to a Switch Info Receiver object to construct. +* +* RETURN VALUE +* This function does not return a value. +* +* NOTES +* Allows calling osm_sir_rcv_init, osm_sir_rcv_destroy, +* and osm_sir_rcv_is_inited. +* +* Calling osm_sir_rcv_construct is a prerequisite to calling any other +* method except osm_sir_rcv_init. +* +* SEE ALSO +* Switch Info Receiver object, osm_sir_rcv_init, +* osm_sir_rcv_destroy, osm_sir_rcv_is_inited +*********/ + +/****f* OpenSM: Switch Info Receiver/osm_sir_rcv_destroy +* NAME +* osm_sir_rcv_destroy +* +* DESCRIPTION +* The osm_sir_rcv_destroy function destroys the object, releasing +* all resources. +* +* SYNOPSIS +*/ +void osm_sir_rcv_destroy( + IN osm_sir_rcv_t* const p_ctrl ); +/* +* PARAMETERS +* p_ctrl +* [in] Pointer to the object to destroy. +* +* RETURN VALUE +* This function does not return a value. +* +* NOTES +* Performs any necessary cleanup of the specified +* Switch Info Receiver object. +* Further operations should not be attempted on the destroyed object. +* This function should only be called after a call to +* osm_sir_rcv_construct or osm_sir_rcv_init. +* +* SEE ALSO +* Switch Info Receiver object, osm_sir_rcv_construct, +* osm_sir_rcv_init +*********/ + +/****f* OpenSM: Switch Info Receiver/osm_sir_rcv_init +* NAME +* osm_sir_rcv_init +* +* DESCRIPTION +* The osm_sir_rcv_init function initializes a +* Switch Info Receiver object for use. +* +* SYNOPSIS +*/ +ib_api_status_t osm_sir_rcv_init( + IN osm_sir_rcv_t* const p_rcv, + IN osm_sa_resp_t* const p_resp, + IN osm_mad_pool_t* const p_mad_pool, + IN osm_subn_t* const p_subn, + IN osm_log_t* const p_log, + IN cl_plock_t* const p_lock ); +/* +* PARAMETERS +* p_rcv +* [in] Pointer to an osm_sir_rcv_t object to initialize. +* +* p_resp +* [in] Pointer to the SA Responder object. +* +* p_mad_pool +* [in] Pointer to the mad pool. +* +* p_subn +* [in] Pointer to the Subnet object for this subnet. +* +* p_log +* [in] Pointer to the log object. +* +* p_lock +* [in] Pointer to the OpenSM serializing lock. +* +* RETURN VALUES +* IB_SUCCESS if the Switch Info Receiver object was initialized +* successfully. +* +* NOTES +* Allows calling other Switch Info Receiver methods. +* +* SEE ALSO +* Switch Info Receiver object, osm_sir_rcv_construct, +* osm_sir_rcv_destroy, osm_sir_rcv_is_inited +*********/ + +/****f* OpenSM: Switch Info Receiver/osm_sir_rcv_is_inited +* NAME +* osm_sir_rcv_is_inited +* +* DESCRIPTION +* Indicates if the object has been initialized with osm_sir_rcv_init. +* +* SYNOPSIS +*/ +boolean_t osm_sir_rcv_is_inited( + IN const osm_sir_rcv_t* const p_ctrl ); +/* +* PARAMETERS +* p_ctrl +* [in] Pointer to an osm_sir_rcv_t object. +* +* RETURN VALUES +* TRUE if the object was initialized successfully, +* FALSE otherwise. +* +* NOTES +* The osm_sir_rcv_construct or osm_sir_rcv_init must be +* called before using this function. +* +* SEE ALSO +* Switch Info Receiver object, osm_sir_rcv_construct, +* osm_sir_rcv_init +*********/ + +/****f* OpenSM: Switch Info Receiver/osm_sir_rcv_process +* NAME +* osm_sir_rcv_process +* +* DESCRIPTION +* Process the SwitchInfo attribute. +* +* SYNOPSIS +*/ +void osm_sir_rcv_process( + IN osm_sir_rcv_t* const p_ctrl, + IN const osm_madw_t* const p_madw ); +/* +* PARAMETERS +* p_ctrl +* [in] Pointer to an osm_sir_rcv_t object. +* +* p_madw +* [in] Pointer to the MAD Wrapper containing the MAD +* that contains the node's SwitchInfo attribute. +* +* RETURN VALUES +* CL_SUCCESS if the SwitchInfo processing was successful. +* +* NOTES +* This function processes a SwitchInfo attribute. +* +* SEE ALSO +* Switch Info Receiver, Switch Info Response Controller +*********/ + +END_C_DECLS + +#endif /* _OSM_SIR_RCV_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_sa_sw_info_record_ctrl.h b/trunk/ulp/opensm/user/include/opensm/osm_sa_sw_info_record_ctrl.h new file mode 100644 index 00000000..86b9674f --- /dev/null +++ b/trunk/ulp/opensm/user/include/opensm/osm_sa_sw_info_record_ctrl.h @@ -0,0 +1,259 @@ +/* + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. + * + * This software is available to you under the OpenIB.org BSD license + * below: + * + * Redistribution and use in source and binary forms, with or + * without modification, are permitted provided that the following + * conditions are met: + * + * - Redistributions of source code must retain the above + * copyright notice, this list of conditions and the following + * disclaimer. + * + * - Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials + * provided with the distribution. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS + * BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN + * ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN + * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + * + * $Id$ + */ + + +/* + * Abstract: + * Declaration of osm_sir_rcv_ctrl_t. + * This object represents a controller that receives the IBA SwitchInfo + * attribute from a switch node. + * This object is part of the OpenSM family of objects. + * + * Environment: + * Linux User Mode + * + */ + +#ifndef _OSM_SIR_RCV_CTRL_H_ +#define _OSM_SIR_RCV_CTRL_H_ + +#include +#include +#include +#include +#include + +#ifdef __cplusplus +# define BEGIN_C_DECLS extern "C" { +# define END_C_DECLS } +#else /* !__cplusplus */ +# define BEGIN_C_DECLS +# define END_C_DECLS +#endif /* __cplusplus */ + +BEGIN_C_DECLS + +/****h* OpenSM/Switch Info Receive Controller +* NAME +* Switch Info Receive Controller +* +* DESCRIPTION +* The Switch Info Receive Controller object encapsulates the information +* needed to receive the SwitchInfo attribute from a switch node. +* +* The Switch Info Receive Controller object is thread safe. +* +* This object should be treated as opaque and should be +* manipulated only through the provided functions. +* +* AUTHOR +* Hal Rosenstock, Voltaire +* +*********/ + +/****s* OpenSM: Switch Info Receive Controller/osm_sir_rcv_ctrl_t +* NAME +* osm_sir_rcv_ctrl_t +* +* DESCRIPTION +* Switch Info Receive Controller structure. +* +* This object should be treated as opaque and should +* be manipulated only through the provided functions. +* +* SYNOPSIS +*/ +typedef struct _osm_sir_rcv_ctrl +{ + osm_sir_rcv_t *p_rcv; + osm_log_t *p_log; + cl_dispatcher_t *p_disp; + cl_disp_reg_handle_t h_disp; +} osm_sir_rcv_ctrl_t; +/* +* FIELDS +* p_rcv +* Pointer to the Switch Info Receiver object. +* +* p_log +* Pointer to the log object. +* +* p_disp +* Pointer to the Dispatcher. +* +* h_disp +* Handle returned from dispatcher registration. +* +* SEE ALSO +* Switch Info Receive Controller object +* Switch Info Receiver object +*********/ + +/****f* OpenSM: Switch Info Receive Controller/osm_sir_rcv_ctrl_construct +* NAME +* osm_sir_rcv_ctrl_construct +* +* DESCRIPTION +* This function constructs a Switch Info Receive Controller object. +* +* SYNOPSIS +*/ +void osm_sir_rcv_ctrl_construct( + IN osm_sir_rcv_ctrl_t* const p_ctrl ); +/* +* PARAMETERS +* p_ctrl +* [in] Pointer to a Switch Info Receive Controller +* object to construct. +* +* RETURN VALUE +* This function does not return a value. +* +* NOTES +* Allows calling osm_sir_rcv_ctrl_init, osm_sir_rcv_ctrl_destroy, +* and osm_sir_rcv_ctrl_is_inited. +* +* Calling osm_sir_rcv_ctrl_construct is a prerequisite to calling any +* other method except osm_sir_rcv_ctrl_init. +* +* SEE ALSO +* Switch Info Receive Controller object, osm_sir_rcv_ctrl_init, +* osm_sir_rcv_ctrl_destroy, osm_sir_rcv_ctrl_is_inited +*********/ + +/****f* OpenSM: Switch Info Receive Controller/osm_sir_rcv_ctrl_destroy +* NAME +* osm_sir_rcv_ctrl_destroy +* +* DESCRIPTION +* The osm_sir_rcv_ctrl_destroy function destroys the object, releasing +* all resources. +* +* SYNOPSIS +*/ +void osm_sir_rcv_ctrl_destroy( + IN osm_sir_rcv_ctrl_t* const p_ctrl ); +/* +* PARAMETERS +* p_ctrl +* [in] Pointer to the object to destroy. +* +* RETURN VALUE +* This function does not return a value. +* +* NOTES +* Performs any necessary cleanup of the specified +* Switch Info Receive Controller object. +* Further operations should not be attempted on the destroyed object. +* This function should only be called after a call to +* osm_sir_rcv_ctrl_construct or osm_sir_rcv_ctrl_init. +* +* SEE ALSO +* Switch Info Receive Controller object, osm_sir_rcv_ctrl_construct, +* osm_sir_rcv_ctrl_init +*********/ + +/****f* OpenSM: Switch Info Receive Controller/osm_sir_rcv_ctrl_init +* NAME +* osm_sir_rcv_ctrl_init +* +* DESCRIPTION +* The osm_sir_rcv_ctrl_init function initializes a +* Switch Info Receive Controller object for use. +* +* SYNOPSIS +*/ +ib_api_status_t osm_sir_rcv_ctrl_init( + IN osm_sir_rcv_ctrl_t* const p_ctrl, + IN osm_sir_rcv_t* const p_rcv, + IN osm_log_t* const p_log, + IN cl_dispatcher_t* const p_disp ); +/* +* PARAMETERS +* p_ctrl +* [in] Pointer to an osm_sir_rcv_ctrl_t object to initialize. +* +* p_rcv +* [in] Pointer to an osm_sir_rcv_t object. +* +* p_log +* [in] Pointer to the log object. +* +* p_disp +* [in] Pointer to the OpenSM central Dispatcher. +* +* RETURN VALUES +* CL_SUCCESS if the Switch Info Receive Controller object was initialized +* successfully. +* +* NOTES +* Allows calling other Switch Info Receive Controller methods. +* +* SEE ALSO +* Switch Info Receive Controller object, osm_sir_rcv_ctrl_construct, +* osm_sir_rcv_ctrl_destroy, osm_sir_rcv_ctrl_is_inited +*********/ + +/****f* OpenSM: Switch Info Receive Controller/osm_sir_rcv_ctrl_is_inited +* NAME +* osm_sir_rcv_ctrl_is_inited +* +* DESCRIPTION +* Indicates if the object has been initialized with osm_sir_rcv_ctrl_init. +* +* SYNOPSIS +*/ +boolean_t osm_sir_rcv_ctrl_is_inited( + IN const osm_sir_rcv_ctrl_t* const p_ctrl ); +/* +* PARAMETERS +* p_ctrl +* [in] Pointer to an osm_sir_rcv_ctrl_t object. +* +* RETURN VALUES +* TRUE if the object was initialized successfully, +* FALSE otherwise. +* +* NOTES +* The osm_sir_rcv_ctrl_construct or osm_sir_rcv_ctrl_init must be +* called before using this function. +* +* SEE ALSO +* Switch Info Receive Controller object, osm_sir_rcv_ctrl_construct, +* osm_sir_rcv_ctrl_init +*********/ + +END_C_DECLS + +#endif /* _OSM_SIR_RCV_CTRL_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_sa_vlarb_record.h b/trunk/ulp/opensm/user/include/opensm/osm_sa_vlarb_record.h index 18d65471..c5f3766e 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_sa_vlarb_record.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_sa_vlarb_record.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -45,11 +45,9 @@ * $Revision: 1.3 $ */ - #ifndef _OSM_VLARB_REC_RCV_H_ #define _OSM_VLARB_REC_RCV_H_ - #include #include #include @@ -86,6 +84,7 @@ BEGIN_C_DECLS * Eitan Zahavi, Mellanox * *********/ + /****s* OpenSM: VLArbitration Record Receiver/osm_vlarb_rec_rcv_t * NAME * osm_vlarb_rec_rcv_t @@ -103,10 +102,9 @@ typedef struct _osm_vlarb_rec_rcv const osm_subn_t *p_subn; osm_sa_resp_t *p_resp; osm_mad_pool_t *p_mad_pool; - osm_log_t *p_log; - cl_plock_t *p_lock; - cl_qlock_pool_t pool; - + osm_log_t *p_log; + cl_plock_t *p_lock; + cl_qlock_pool_t pool; } osm_vlarb_rec_rcv_t; /* * FIELDS @@ -114,7 +112,7 @@ typedef struct _osm_vlarb_rec_rcv * Pointer to the Subnet object for this subnet. * * p_resp -* Pointer to the SA reponder. +* Pointer to the SA responder. * * p_mad_pool * Pointer to the mad pool. @@ -279,3 +277,4 @@ osm_vlarb_rec_rcv_process( END_C_DECLS #endif /* _OSM_VLARB_REC_RCV_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_sa_vlarb_record_ctrl.h b/trunk/ulp/opensm/user/include/opensm/osm_sa_vlarb_record_ctrl.h index fd0cd3f2..3cc07568 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_sa_vlarb_record_ctrl.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_sa_vlarb_record_ctrl.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -45,12 +45,10 @@ * $Revision: 1.3 $ */ - #ifndef _OSM_VLARB_REC_CTRL_H_ #define _OSM_VLARB_REC_CTRL_H_ - -#include +#include #include #include #include @@ -83,6 +81,7 @@ BEGIN_C_DECLS * Eitan Zahavi, Mellanox * *********/ + /****s* OpenSM: VLArbitration Record Receive Controller/osm_vlarb_rec_rcv_ctrl_t * NAME * osm_vlarb_rec_rcv_ctrl_t @@ -229,3 +228,4 @@ ib_api_status_t osm_vlarb_rec_rcv_ctrl_init( END_C_DECLS #endif /* _OSM_VLARB_REC_CTRL_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_service.h b/trunk/ulp/opensm/user/include/opensm/osm_service.h index dde23691..7c09a4f6 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_service.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_service.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -35,7 +35,6 @@ #ifndef _OSM_SVCR_H_ #define _OSM_SVCR_H_ - /* * Abstract: * Declaration of osm_service_rec_t. @@ -82,6 +81,7 @@ BEGIN_C_DECLS * Anil S Keshavamurthy, Intel * *********/ + /****s* OpenSM: Service Record/osm_svcr_t * NAME * osm_svcr_t @@ -97,12 +97,10 @@ BEGIN_C_DECLS typedef struct _osm_svcr_t { - cl_list_item_t list_item; - ib_net64_t svc_id; - ib_service_record_t service_record; - uint32_t modified_time; - uint32_t lease_period; - + cl_list_item_t list_item; + ib_service_record_t service_record; + uint32_t modified_time; + uint32_t lease_period; } osm_svcr_t; /* * FIELDS @@ -240,3 +238,4 @@ osm_svcr_remove_from_db( END_C_DECLS #endif /* _OSM_SVCR_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_slvl_map_rcv.h b/trunk/ulp/opensm/user/include/opensm/osm_slvl_map_rcv.h index fddfaae7..9ab13bf7 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_slvl_map_rcv.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_slvl_map_rcv.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -44,11 +44,9 @@ * $Revision: 1.3 $ */ - #ifndef _OSM_SLVL_RCV_H_ #define _OSM_SLVL_RCV_H_ - #include #include #include @@ -84,6 +82,7 @@ BEGIN_C_DECLS * Eitan Zahavi, Mellanox * *********/ + /****s* OpenSM: Slvl Map Receiver/osm_slvl_rcv_t * NAME * osm_slvl_rcv_t @@ -263,3 +262,4 @@ void osm_slvl_rcv_process( END_C_DECLS #endif /* _OSM_SLVL_RCV_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_slvl_map_rcv_ctrl.h b/trunk/ulp/opensm/user/include/opensm/osm_slvl_map_rcv_ctrl.h index 29bfeecc..26f4776f 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_slvl_map_rcv_ctrl.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_slvl_map_rcv_ctrl.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -45,12 +45,10 @@ * $Revision: 1.3 $ */ - #ifndef _OSM_SLVL_RCV_CTRL_H_ #define _OSM_SLVL_RCV_CTRL_H_ - -#include +#include #include #include #include @@ -83,6 +81,7 @@ BEGIN_C_DECLS * Eitan Zahavi, Mellanox * *********/ + /****s* OpenSM: Slvl Map Receive Controller/osm_slvl_rcv_ctrl_t * NAME * osm_slvl_rcv_ctrl_t @@ -97,8 +96,8 @@ BEGIN_C_DECLS */ typedef struct _osm_slvl_rcv_ctrl { - osm_slvl_rcv_t *p_rcv; - osm_log_t *p_log; + osm_slvl_rcv_t *p_rcv; + osm_log_t *p_log; cl_dispatcher_t *p_disp; cl_disp_reg_handle_t h_disp; @@ -249,7 +248,7 @@ boolean_t osm_slvl_rcv_ctrl_is_inited( * * NOTES * The osm_slvl_rcv_ctrl_construct or osm_slvl_rcv_ctrl_init must be -* called before using this function. +* called before using this function. * * SEE ALSO * Slvl Map Receive Controller object, osm_slvl_rcv_ctrl_construct, @@ -259,3 +258,4 @@ boolean_t osm_slvl_rcv_ctrl_is_inited( END_C_DECLS #endif /* _OSM_SLVL_RCV_CTRL_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_sm.h b/trunk/ulp/opensm/user/include/opensm/osm_sm.h index 0934eaf0..07025554 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_sm.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_sm.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -52,7 +52,7 @@ #include #include #include -#include +#include #include #include #include @@ -71,7 +71,6 @@ #include #include #include -#include #include #include #include @@ -159,7 +158,6 @@ typedef struct _osm_sm osm_link_mgr_t link_mgr; osm_state_mgr_t state_mgr; osm_drop_mgr_t drop_mgr; - osm_pkey_mgr_t pkey_mgr; osm_lft_rcv_t lft_rcv; osm_lft_rcv_ctrl_t lft_rcv_ctrl; osm_mft_rcv_t mft_rcv; @@ -177,8 +175,6 @@ typedef struct _osm_sm osm_vla_rcv_ctrl_t vla_rcv_ctrl; osm_pkey_rcv_t pkey_rcv; osm_pkey_rcv_ctrl_t pkey_rcv_ctrl; - char* p_report_buf; - } osm_sm_t; /* * FIELDS @@ -519,9 +515,9 @@ osm_sm_mcgrp_leave( * SEE ALSO *********/ -/****f* OpenSM: OpenSM/osm_opensm_wait_for_subnet_up +/****f* OpenSM: OpenSM/osm_sm_wait_for_subnet_up * NAME -* osm_opensm_wait_for_subnet_up +* osm_sm_wait_for_subnet_up * * DESCRIPTION * Blocks the calling thread until the subnet is up. @@ -531,7 +527,7 @@ osm_sm_mcgrp_leave( static inline cl_status_t osm_sm_wait_for_subnet_up( IN osm_sm_t* const p_sm, - IN uint32_t const wait_us, + IN uint32_t const wait_us, IN boolean_t const interruptible ) { return( cl_event_wait_on( &p_sm->subnet_up_event, @@ -567,3 +563,4 @@ osm_sm_wait_for_subnet_up( END_C_DECLS #endif /* _OSM_SM_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_sm_mad_ctrl.h b/trunk/ulp/opensm/user/include/opensm/osm_sm_mad_ctrl.h index 3cf6bac2..ffba2c75 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_sm_mad_ctrl.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_sm_mad_ctrl.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -45,13 +45,11 @@ * $Revision: 1.4 $ */ - #ifndef _OSM_SM_MAD_CTRL_H_ #define _OSM_SM_MAD_CTRL_H_ - #include -#include +#include #include #include #include @@ -87,6 +85,7 @@ BEGIN_C_DECLS * Steve King, Intel * *********/ + /****s* OpenSM: SM MAD Controller/osm_sm_mad_ctrl_t * NAME * osm_sm_mad_ctrl_t @@ -101,16 +100,16 @@ BEGIN_C_DECLS */ typedef struct _osm_sm_mad_ctrl { - osm_log_t *p_log; - osm_subn_t *p_subn; + osm_log_t *p_log; + osm_subn_t *p_subn; osm_mad_pool_t *p_mad_pool; - osm_vl15_t *p_vl15; + osm_vl15_t *p_vl15; osm_vendor_t *p_vendor; osm_bind_handle_t h_bind; - cl_plock_t *p_lock; + cl_plock_t *p_lock; cl_dispatcher_t *p_disp; - cl_disp_reg_handle_t h_disp; - osm_stats_t *p_stats; + cl_disp_reg_handle_t h_disp; + osm_stats_t *p_stats; } osm_sm_mad_ctrl_t; /* @@ -169,15 +168,14 @@ osm_sm_mad_ctrl_construct( * This function does not return a value. * * NOTES -* Allows calling osm_sm_mad_ctrl_init, osm_sm_mad_ctrl_destroy, -* and osm_sm_mad_ctrl_is_inited. +* Allows calling osm_sm_mad_ctrl_init, and osm_sm_mad_ctrl_destroy. * * Calling osm_sm_mad_ctrl_construct is a prerequisite to calling any other * method except osm_sm_mad_ctrl_init. * * SEE ALSO * SM MAD Controller object, osm_sm_mad_ctrl_init, -* osm_sm_mad_ctrl_destroy, osm_sm_mad_ctrl_is_inited +* osm_sm_mad_ctrl_destroy *********/ /****f* OpenSM: SM MAD Controller/osm_sm_mad_ctrl_destroy @@ -226,7 +224,7 @@ osm_sm_mad_ctrl_destroy( ib_api_status_t osm_sm_mad_ctrl_init( IN osm_sm_mad_ctrl_t* const p_ctrl, - IN osm_subn_t* const p_subn, + IN osm_subn_t* const p_subn, IN osm_mad_pool_t* const p_mad_pool, IN osm_vl15_t* const p_vl15, IN osm_vendor_t* const p_vendor, @@ -269,7 +267,7 @@ osm_sm_mad_ctrl_init( * * SEE ALSO * SM MAD Controller object, osm_sm_mad_ctrl_construct, -* osm_sm_mad_ctrl_destroy, osm_sm_mad_ctrl_is_inited +* osm_sm_mad_ctrl_destroy *********/ /****f* OpenSM: SM/osm_sm_mad_ctrl_bind @@ -338,3 +336,4 @@ osm_sm_mad_ctrl_get_bind_handle( END_C_DECLS #endif /* _OSM_SM_MAD_CTRL_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_sm_state_mgr.h b/trunk/ulp/opensm/user/include/opensm/osm_sm_state_mgr.h index bde34046..2d8282a9 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_sm_state_mgr.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_sm_state_mgr.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -44,11 +44,9 @@ * $Revision: 1.2 $ */ - #ifndef _OSM_SM_STATE_MGR_H_ #define _OSM_SM_STATE_MGR_H_ - #include #include #include @@ -104,43 +102,45 @@ BEGIN_C_DECLS */ typedef struct _osm_sm_state_mgr { - cl_spinlock_t state_lock; - cl_timer_t polling_timer; - uint32_t retry_number; - ib_net64_t master_guid; - osm_state_mgr_t* p_state_mgr; - osm_subn_t* p_subn; - osm_req_t* p_req; - osm_log_t* p_log; - osm_remote_sm_t* p_polling_sm; + cl_spinlock_t state_lock; + cl_timer_t polling_timer; + uint32_t retry_number; + ib_net64_t master_guid; + osm_state_mgr_t* p_state_mgr; + osm_subn_t* p_subn; + osm_req_t* p_req; + osm_log_t* p_log; + osm_remote_sm_t* p_polling_sm; } osm_sm_state_mgr_t; /* * FIELDS * state_lock -* Spinlock gaurding the state and processes. +* Spinlock guarding the state and processes. * * retry_number -* Used on Standby state - to count the number of retries of queries to the master SM. +* Used on Standby state - to count the number of retries +* of queries to the master SM. * -* polling_timer -* Timer for polling +* polling_timer +* Timer for polling * -* p_state_mgr -* Point to the state manager object +* p_state_mgr +* Point to the state manager object * * p_subn * Pointer to the Subnet object for this subnet. * -* p_req +* p_req * Pointer to the generic attribute request object. * * p_log * Pointer to the log object. * -* p_polling_sm -* Pointer to a osm_remote_sm_t object. When our SM needs to poll on a remote -* sm, this will be the pointer of the polled SM. +* p_polling_sm +* Pointer to a osm_remote_sm_t object. When our SM needs +* to poll on a remote sm, this will be the pointer of the +* polled SM. * * SEE ALSO * SM State Manager object @@ -295,7 +295,7 @@ osm_sm_state_mgr_process( * * DESCRIPTION * Signals that the remote Master SM is alive. -* Need to clear the retry_number variable. +* Need to clear the retry_number variable. * * SYNOPSIS */ @@ -350,3 +350,4 @@ osm_sm_state_mgr_check_legality( END_C_DECLS #endif /* _OSM_SM_STATE_MGR_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_sminfo_rcv.h b/trunk/ulp/opensm/user/include/opensm/osm_sminfo_rcv.h index d8cf2182..51b5f985 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_sminfo_rcv.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_sminfo_rcv.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -44,7 +44,6 @@ * $Revision: 1.4 $ */ - #ifndef _OSM_SMINFO_RCV_H_ #define _OSM_SMINFO_RCV_H_ @@ -85,6 +84,7 @@ BEGIN_C_DECLS * Steve King, Intel * *********/ + /****s* OpenSM: SMInfo Receiver/osm_sminfo_rcv_t * NAME * osm_sminfo_rcv_t @@ -288,3 +288,4 @@ void osm_sminfo_rcv_process( END_C_DECLS #endif /* _OSM_SMINFO_RCV_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_sminfo_rcv_ctrl.h b/trunk/ulp/opensm/user/include/opensm/osm_sminfo_rcv_ctrl.h index 1a438da8..08d5dd0b 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_sminfo_rcv_ctrl.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_sminfo_rcv_ctrl.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -48,8 +48,7 @@ #ifndef _OSM_SMINFO_RCV_CTRL_H_ #define _OSM_SMINFO_RCV_CTRL_H_ - -#include +#include #include #include #include @@ -82,6 +81,7 @@ BEGIN_C_DECLS * Steve King, Intel * *********/ + /****s* OpenSM: SMInfo Receive Controller/osm_sminfo_rcv_ctrl_t * NAME * osm_sminfo_rcv_ctrl_t @@ -229,3 +229,4 @@ osm_sminfo_rcv_ctrl_init( END_C_DECLS #endif /* OSM_SMINFO_RCV_CTRL_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_state_mgr.h b/trunk/ulp/opensm/user/include/opensm/osm_state_mgr.h index 17ea7e84..7e701796 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_state_mgr.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_state_mgr.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -44,11 +44,9 @@ * $Revision: 1.5 $ */ - #ifndef _OSM_STATE_MGR_H_ #define _OSM_STATE_MGR_H_ - #include #include #include @@ -57,7 +55,6 @@ #include #include #include -#include #include #include @@ -110,7 +107,6 @@ typedef struct _osm_state_mgr osm_mcast_mgr_t *p_mcast_mgr; osm_link_mgr_t *p_link_mgr; osm_drop_mgr_t *p_drop_mgr; - osm_pkey_mgr_t *p_pkey_mgr; osm_req_t *p_req; osm_stats_t *p_stats; struct _osm_sm_state_mgr *p_sm_state_mgr; @@ -120,7 +116,6 @@ typedef struct _osm_state_mgr cl_qlist_t idle_time_list; cl_plock_t *p_lock; cl_event_t *p_subnet_up_event; - char *p_report_buf; osm_sm_state_t state; osm_state_mgr_mode_t state_step_mode; osm_signal_t next_stage_signal; @@ -148,9 +143,6 @@ typedef struct _osm_state_mgr * p_drop_mgr * Pointer to the Drop Manager object. * -* p_pkey_mgr -* Pointer to the P_Key Manager object. -* * p_req * Pointer to the Requester object sending SMPs. * @@ -164,7 +156,7 @@ typedef struct _osm_state_mgr * Pointer to the SM's MAD Controller object. * * state_lock -* Spinlock gaurding the state and processes. +* Spinlock guarding the state and processes. * * p_lock * lock guarding the subnet object. @@ -172,9 +164,6 @@ typedef struct _osm_state_mgr * p_subnet_up_event * Pointer to the event to set if/when the subnet comes up. * -* p_report_buf -* Pointer to the large log buffer used for user reports. -* * state * State of the SM. * @@ -376,14 +365,12 @@ osm_state_mgr_init( IN osm_mcast_mgr_t* const p_mcast_mgr, IN osm_link_mgr_t* const p_link_mgr, IN osm_drop_mgr_t* const p_drop_mgr, - IN osm_pkey_mgr_t* const p_pkey_mgr, IN osm_req_t* const p_req, IN osm_stats_t* const p_stats, IN struct _osm_sm_state_mgr* const p_sm_state_mgr, IN const osm_sm_mad_ctrl_t* const p_mad_ctrl, IN cl_plock_t* const p_lock, IN cl_event_t* const p_subnet_up_event, - IN char* const p_report_buf, IN osm_log_t* const p_log ); /* * PARAMETERS @@ -408,9 +395,6 @@ osm_state_mgr_init( * p_drop_mgr * [in] Pointer to the Drop Manager object. * -* p_pkey_mgr -* [in] Pointer to the P_Key Manager object. -* * p_req * [in] Pointer to the Request Controller object. * @@ -426,9 +410,6 @@ osm_state_mgr_init( * p_subnet_up_event * [in] Pointer to the event to set if/when the subnet comes up. * -* p_report_buf -* [in] Pointer to the large log buffer used for user reports. -* * p_log * [in] Pointer to the log object. * @@ -534,3 +515,4 @@ osm_state_mgr_process( END_C_DECLS #endif /* _OSM_STATE_MGR_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_state_mgr_ctrl.h b/trunk/ulp/opensm/user/include/opensm/osm_state_mgr_ctrl.h index ad49a8e7..86043a58 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_state_mgr_ctrl.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_state_mgr_ctrl.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -48,8 +48,7 @@ #ifndef _OSM_STATE_MGR_CTRL_H_ #define _OSM_STATE_MGR_CTRL_H_ - -#include +#include #include #include #include @@ -82,6 +81,7 @@ BEGIN_C_DECLS * Steve King, Intel * *********/ + /****s* OpenSM: State Manager Controller/osm_state_mgr_ctrl_t * NAME * osm_state_mgr_ctrl_t @@ -142,11 +142,10 @@ osm_state_mgr_ctrl_construct( * This function does not return a value. * * NOTES -* Allows calling osm_state_mgr_ctrl_init, osm_state_mgr_ctrl_destroy, -* and osm_state_mgr_ctrl_is_inited. +* Allows calling osm_state_mgr_ctrl_init, and osm_state_mgr_ctrl_destroy. * -* Calling osm_state_mgr_ctrl_construct is a prerequisite to calling any other -* method except osm_state_mgr_ctrl_init. +* Calling osm_state_mgr_ctrl_construct is a prerequisite to calling any +* other method except osm_state_mgr_ctrl_init. * * SEE ALSO * State Manager Controller object, osm_state_mgr_ctrl_init, @@ -231,3 +230,4 @@ osm_state_mgr_ctrl_init( END_C_DECLS #endif /* OSM_STATE_MGR_CTRL_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_stats.h b/trunk/ulp/opensm/user/include/opensm/osm_stats.h index 944b9bf1..07c64e1a 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_stats.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_stats.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -72,6 +72,7 @@ BEGIN_C_DECLS * Steve King, Intel * *********/ + /****s* OpenSM: Statistics/osm_stats_t * NAME * osm_stats_t @@ -121,3 +122,4 @@ typedef struct _osm_stats END_C_DECLS #endif /* _OSM_STATS_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_subnet.h b/trunk/ulp/opensm/user/include/opensm/osm_subnet.h index 3ccce640..49a03260 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_subnet.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_subnet.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -47,7 +47,6 @@ #ifndef _OSM_SUBNET_H_ #define _OSM_SUBNET_H_ - #include #include #include @@ -69,6 +68,7 @@ BEGIN_C_DECLS #define OSM_SUBNET_VECTOR_GROW_SIZE 1 #define OSM_SUBNET_VECTOR_CAPACITY 256 +struct _osm_opensm_t; /****h* OpenSM/Subnet * NAME @@ -103,12 +103,12 @@ BEGIN_C_DECLS */ typedef int (*osm_pfn_ui_extension_t)( - IN void* context); + IN void* context ); /* * PARAMETERS * context * [in] Client specific context specified in the subnet opt -* Same prefix as the UI funciton (suffixed by ctx) +* Same prefix as the UI function (suffixed by ctx) * * RETURN VALUE * This function returns an int (the semantic is different between @@ -130,15 +130,15 @@ typedef int */ typedef void (*osm_pfn_ui_mcast_extension_t)( - IN void *context, + IN void *context, IN ib_net16_t mlid, IN osm_mcast_req_type_t request_type, IN ib_net64_t port_guid ); /* * PARAMETERS -* context +* context * [in] Client specific context specified in the subnet opt -* Same prefix as the UI funciton (suffixed by ctx) +* Same prefix as the UI function (suffixed by ctx) * * mlid * [in] multicast lid of the group handled. @@ -171,10 +171,47 @@ typedef enum _osm_testability_modes OSM_TEST_MODE_NONE = 0, OSM_TEST_MODE_EXIT_BEFORE_SEND_HANDOVER, OSM_TEST_MODE_MAX - } osm_testability_modes_t; /***********/ +/****s* OpenSM: Subnet/osm_qos_options_t +* NAME +* osm_qos_options_t +* +* DESCRIPTION +* Subnet QoS options structure. This structure contains the various +* QoS specific configuration parameters for the subnet. +* +* SYNOPSIS +*/ +typedef struct _osm_qos_options_t { + unsigned max_vls; + unsigned high_limit; + char *vlarb_high; + char *vlarb_low; + char *sl2vl; +} osm_qos_options_t; +/* +* FIELDS +* +* max_vls +* The number of maximum VLs on the Subnet +* +* high_limit +* The limit of High Priority component of VL Arbitration +* table (IBA 7.6.9) +* +* vlarb_high +* High priority VL Arbitration table template. +* +* vlarb_low +* Low priority VL Arbitration table template. +* +* sl2vl +* SL2VL Mapping table (IBA 7.6.6) template. +* +*********/ + /****s* OpenSM: Subnet/osm_subn_opt_t * NAME * osm_subn_opt_t @@ -187,54 +224,69 @@ typedef enum _osm_testability_modes */ typedef struct _osm_subn_opt { - ib_net64_t guid; - ib_net64_t m_key; + ib_net64_t guid; + ib_net64_t m_key; ib_net64_t sm_key; - ib_net64_t subnet_prefix; - ib_net16_t m_key_lease_period; - uint32_t sweep_interval; - uint32_t max_wire_smps; - uint32_t transaction_timeout; - uint8_t sm_priority; - uint8_t lmc; - uint8_t max_op_vls; - boolean_t reassign_lids; - boolean_t reassign_lfts; - boolean_t ignore_other_sm; - boolean_t single_thread; - boolean_t no_multicast_option; - boolean_t disable_multicast; - boolean_t force_log_flush; + ib_net64_t subnet_prefix; + ib_net16_t m_key_lease_period; + uint32_t sweep_interval; + uint32_t max_wire_smps; + uint32_t transaction_timeout; + uint8_t sm_priority; + uint8_t lmc; + boolean_t lmc_esp0; + uint8_t max_op_vls; + uint8_t force_link_speed; + boolean_t reassign_lids; + boolean_t reassign_lfts; + boolean_t ignore_other_sm; + boolean_t single_thread; + boolean_t no_multicast_option; + boolean_t disable_multicast; + boolean_t force_log_flush; uint8_t subnet_timeout; uint8_t packet_life_time; + uint8_t vl_stall_count; + uint8_t leaf_vl_stall_count; uint8_t head_of_queue_lifetime; uint8_t leaf_head_of_queue_lifetime; uint8_t local_phy_errors_threshold; uint8_t overrun_errors_threshold; uint32_t sminfo_polling_timeout; uint32_t polling_retry_number; - uint32_t max_msg_fifo_timeout; + uint32_t max_msg_fifo_timeout; boolean_t force_heavy_sweep; uint8_t log_flags; char * dump_files_dir; char * log_file; + unsigned long log_max_size; + char * partition_config_file; + boolean_t no_partition_enforcement; + boolean_t no_qos; boolean_t accum_log_file; boolean_t console; cl_map_t port_prof_ignore_guids; boolean_t port_profile_switch_nodes; - uint32_t max_port_profile; osm_pfn_ui_extension_t pfn_ui_pre_lid_assign; void * ui_pre_lid_assign_ctx; - osm_pfn_ui_extension_t pfn_ui_ucast_fdb_assign; - void * ui_ucast_fdb_assign_ctx; osm_pfn_ui_mcast_extension_t pfn_ui_mcast_fdb_assign; void * ui_mcast_fdb_assign_ctx; boolean_t sweep_on_trap; osm_testability_modes_t testability_mode; - boolean_t updn_activate; + char * routing_engine_name; + char * lid_matrix_dump_file; + char * ucast_dump_file; char * updn_guid_file; + char * sa_db_file; boolean_t exit_on_fatal; boolean_t honor_guid2lid_file; + osm_qos_options_t qos_options; + osm_qos_options_t qos_ca_options; + osm_qos_options_t qos_sw0_options; + osm_qos_options_t qos_swe_options; + osm_qos_options_t qos_rtr_options; + boolean_t enable_quirks; + boolean_t no_clients_rereg; } osm_subn_opt_t; /* * FIELDS @@ -245,8 +297,8 @@ typedef struct _osm_subn_opt * m_key * M_Key value sent to all ports qualifing all Set(PortInfo). * -* sm_key -* SM_Key value of the SM to qualify rcv SA queries as "trusted". +* sm_key +* SM_Key value of the SM to qualify rcv SA queries as "trusted". * * subnet_prefix * Subnet prefix used on this subnet. @@ -265,127 +317,168 @@ typedef struct _osm_subn_opt * lmc * The LMC value used on this subnet. * -* max_op_vls -* Limit the maximal operational VLs. default is 1. +* lmc_esp0 +* Whether LMC value used on subnet should be used for +* enhanced switch port 0 or not. If TRUE, it is used. +* Otherwise (the default), LMC is set to 0 for ESP0. +* +* max_op_vls +* Limit the maximal operational VLs. default is 1. * * reassign_lids * If TRUE cause all lids to be re-assigend. -* Otherwise (the default) -* OpenSM always try to preserve as much LIDs as posible. +* Otherwise (the default), +* OpenSM always tries to preserve as LIDs as much as possible. * -* reassign_lfts -* If TRUE ignore existing LFT entries on first sweep (default). -* Otherwise only non minimal hop cases are modified. -* NOTE: A standby SM clears its first sweep flag - since the -* master SM already sweeps... +* reassign_lfts +* If TRUE ignore existing LFT entries on first sweep (default). +* Otherwise only non minimal hop cases are modified. +* NOTE: A standby SM clears its first sweep flag - since the +* master SM already sweeps... * * ignore_other_sm_option -* This flag is TRUE if other SM's on the subnet should be ignored. +* This flag is TRUE if other SMs on the subnet should be ignored. * * no_multicast_option * This flag is TRUE if OpenSM should disable multicast support. * -* max_msg_fifo_timeout -* The maximal time a message can stay in the incoming message queue. -* If there is more then one message in the queue and the last message -* stayed in the queue more then this value the SA request will be -* immediately returned with a BUSY status. +* max_msg_fifo_timeout +* The maximal time a message can stay in the incoming message queue. +* If there is more than one message in the queue and the last +* message stayed in the queue more than this value the SA request +* will be immediately returned with a BUSY status. * -* subnet_timeout -* The subnet_timeout that will be set for all the ports in the -* design SubnMgt.Set(PortInfo.vl_stall_life)) +* subnet_timeout +* The subnet_timeout that will be set for all the ports in the +* design SubnMgt.Set(PortInfo.vl_stall_life)) * -* head_of_queue_lifetime -* The maximal time a packet can live at the head of a VL queue -* on any port not driving an HCA port +* vl_stall_count +* The number of sequential packets dropped that cause the port +* to enter the VLStalled state. * -* leaf_head_of_queue_lifetime -* The maximal time a packet can live at the head of a VL queue -* on switch ports driving a CA +* leaf_vl_stall_count +* The number of sequential packets dropped that cause the port +* to enter the VLStalled state. This is for switch ports driving +* a CA or router port. +* +* head_of_queue_lifetime +* The maximal time a packet can live at the head of a VL queue +* on any port not driving a CA or router port. +* +* leaf_head_of_queue_lifetime +* The maximal time a packet can live at the head of a VL queue +* on switch ports driving a CA or router. * * local_phy_errors_threshold -* Threshold of local phy errors for sending Trap 129 +* Threshold of local phy errors for sending Trap 129 * * overrun_errors_threshold -* Threshold of credits over-run errors for sending Trap 129 +* Threshold of credits overrun errors for sending Trap 129 +* +* sminfo_polling_timeout +* Specifies the polling timeout (in milliseconds) - the timeout +* between one poll to another. +* +* packet_life_time +* The maximal time a packet can stay in a switch. +* The value is send to all switches as SubnMgt.Set(SwitchInfo.life_state) * -* sminfo_polling_timeout -* Specifies the polling timeout (in milliseconds) - the timeout -* between one poll to another. +* dump_files_dir +* The directory to be used for subnet.lst osm.fdbs, osm.mcfdbs +* and default log file (the latter for Windows, not Linux). * -* packet_life_time -* The maximal time a packet can stay in a switch. -* The value is send to all switches as SubnMgt.Set(SwitchInfo.life_state) +* log_file +* Name of the log file (or NULL) for stdout. * -* dump_files_dir -* The directory to be used for subnet.lst osm.fdbs, osm.mcfdbs and default -* log file (the latter for Windows, not Linux); +* log_max_size +* This option defines maximal log file size in MB. When +* specified the log file will be truncated upon reaching +* this limit. * -* log_file -* Name of the log file (or NULL) for stdout. +* accum_log_file +* If TRUE (default) - the log file will be accumulated. +* If FALSE - the log file will be erased before starting current opensm run. * -* accum_log_file -* If TRUE (default) - the log file will be accumulated. -* If FALSE - the log file will be erased before starting current opensm run. +* port_prof_ignore_guids +* A map of guids to be ignored by port profiling. * -* port_prof_ignore_guids -* A map of guids to be ignored by port profiling. +* port_profile_switch_nodes +* If TRUE will count the number of switch nodes routed through +* the link. If FALSE - only CA/RT nodes are counted. * -* port_profile_switch_nodes -* If TRUE will count the number of switch nodes routed through -* the link. If FALSE - only CA/RT nodes are counted. +* pfn_ui_pre_lid_assign +* A UI function to be invoked prior to lid assigment. It should +* return 1 if any change was made to any lid or 0 otherwise. * -* max_port_profile -* Prevent routing through a port subscribed with more then this -* number of routes. +* ui_pre_lid_assign_ctx +* A UI context (void *) to be provided to the pfn_ui_pre_lid_assign * -* pfn_ui_pre_lid_assign -* A UI function to be invoked prior to lid assigment. It should return 1 -* if any change was made to any lid or 0 otherwise. +* pfn_ui_mcast_fdb_assign +* A UI function to be called inside the mcast manager instead of +* the call for the build spanning tree. This will be called on +* every multicast call for create, join and leave, and is +* responsible for the mcast FDB configuration. * -* ui_pre_lid_assign_ctx -* A UI context (void *) to be provided to the pfn_ui_pre_lid_assign +* ui_mcast_fdb_assign_ctx +* A UI context (void *) to be provided to the pfn_ui_mcast_fdb_assign * -* pfn_ui_ucast_fdb_assign -* A UI function to be called instead of the ucast manager FDB -* configuration. +* sweep_on_trap +* Received traps will initiate a new sweep. * -* ui_ucast_fdb_assign_ctx -* A UI context (void *) to be provided to the pfn_ui_ucast_fdb_assign +* testability_mode +* Object that indicates if we are running in a special testability mode. * -* pfn_ui_mcast_fdb_assign -* A UI function to be called inside the mcast manager instead of the -* call for the build spanning tree. This will be called on every -* multicast call for create, join and leave, and is responsible for -* the mcast FDB configuration. +* routing_engine_name +* Name of used routing engine +* (other than default Min Hop Algorithm) * -* ui_mcast_fdb_assign_ctx -* A UI context (void *) to be provided to the pfn_ui_mcast_fdb_assign +* lid_matrix_dump_file +* Name of the lid matrix dump file from where switch +* lid matrices (min hops tables) will be loaded * -* sweep_on_trap -* Received traps will initiate a new sweep. +* ucast_dump_file +* Name of the unicast routing dump file from where switch +* forwarding tables will be loaded * -* testability_mode -* Object that indicates if we are running in a special testability mode. +* updn_guid_file +* Pointer to name of the UPDN guid file given by User * -* updn_activate -* Object that indicates if we are running the UPDN algorithm (TRUE) or -* Min Hop Algorithm (FALSE) +* sa_db_file +* Name of the SA database file. * -* updn_guid_file -* Pointer to name of the UPDN guid file given by User +* exit_on_fatal +* If TRUE (default) - SM will exit on fatal subnet initialization issues. +* If FALSE - SM will not exit. +* Fatal initialization issues: +* a. SM recognizes 2 different nodes with the same guid, or +* 12x link with lane reversal badly configured. * -* exit_on_fatal -* If TRUE (default) - SM will exit on fatal subnet initialization issues. -* If FALSE - SM will not exit. -* Fatal initialization issues: -* a. SM recognizes 2 different nodes with the same guid, or 12x link with -* lane reversal badly configured. +* honor_guid2lid_file +* Always honor the guid2lid file if it exists and is valid. This +* means that the file will be honored when SM is coming out of +* STANDBY. By default this is FALSE. * -* honor_guid2lid_file -* Always honor the guid2lid file if it exists and is valid. This means that -* the file will be honored when SM is coming out of STANDBY. -* By default this is FALSE. +* qos_options +* Default set of QoS options +* +* qos_ca_options +* QoS options for CA ports +* +* qos_sw0_options +* QoS options for switches' port 0 +* +* qos_swe_options +* QoS options for switches' external ports +* +* qos_rtr_options +* QoS options for router ports +* +* enable_quirks +* Enable high risk new features and not fully qualified +* hardware specific work arounds +* +* no_clients_rereg +* When TRUE disables clients reregistration request. * * SEE ALSO * Subnet object @@ -406,32 +499,33 @@ typedef struct _osm_subn_opt */ typedef struct _osm_subn { - cl_qmap_t sw_guid_tbl; - cl_qmap_t node_guid_tbl; - cl_qmap_t port_guid_tbl; - cl_qmap_t rtr_guid_tbl; - cl_qmap_t prtn_pkey_tbl; - cl_qmap_t mgrp_mlid_tbl; - cl_qmap_t sm_guid_tbl; + struct _osm_opensm_t *p_osm; + cl_qmap_t sw_guid_tbl; + cl_qmap_t node_guid_tbl; + cl_qmap_t port_guid_tbl; + cl_qmap_t rtr_guid_tbl; + cl_qmap_t prtn_pkey_tbl; + cl_qmap_t mgrp_mlid_tbl; + cl_qmap_t sm_guid_tbl; cl_list_t light_sweep_physp_list; - cl_qlist_t sa_sr_list; - cl_qlist_t sa_infr_list; - cl_ptr_vector_t node_lid_tbl; - cl_ptr_vector_t port_lid_tbl; - ib_net16_t master_sm_base_lid; - ib_net16_t sm_base_lid; - ib_net64_t sm_port_guid; - uint8_t sm_state; - osm_subn_opt_t opt; - uint16_t max_unicast_lid_ho; - uint16_t max_multicast_lid_ho; + cl_qlist_t sa_sr_list; + cl_qlist_t sa_infr_list; + cl_ptr_vector_t node_lid_tbl; + cl_ptr_vector_t port_lid_tbl; + ib_net16_t master_sm_base_lid; + ib_net16_t sm_base_lid; + ib_net64_t sm_port_guid; + uint8_t sm_state; + osm_subn_opt_t opt; + uint16_t max_unicast_lid_ho; + uint16_t max_multicast_lid_ho; uint8_t min_ca_mtu; uint8_t min_ca_rate; boolean_t ignore_existing_lfts; boolean_t subnet_initialization_error; boolean_t force_immediate_heavy_sweep; boolean_t force_delayed_heavy_sweep; - cl_list_t new_ports_list; + cl_list_t new_ports_list; boolean_t in_sweep_hop_0; boolean_t moved_to_master_state; boolean_t first_time_master_sweep; @@ -464,13 +558,13 @@ typedef struct _osm_subn * Indexed by MLID. * * sm_guid_tbl -* Container of pointers to Other SM objects representing other SM's +* Container of pointers to SM objects representing other SMs * on the subnet. * -* light_sweep_physp_list -* A list of all phys ports to scan for a change in remote -* side state in next light sweep. These ports are not down -* but for some reason the remote side did not answer. +* light_sweep_physp_list +* A list of all phys ports to scan for a change in remote +* side state in next light sweep. These ports are not down +* but for some reason the remote side did not answer. * * node_lid_tbl * Container of pointers to all Node objects in the subent. @@ -502,25 +596,25 @@ typedef struct _osm_subn * max_multicast_lid_ho * The minimal max multicast lid reported by all switches * -* min_ca_mtu -* The minimal MTU reported by all CAs ports on the subnet +* min_ca_mtu +* The minimal MTU reported by all CAs ports on the subnet * -* min_ca_rate -* The minimal rate reported by all CA ports on the subnet +* min_ca_rate +* The minimal rate reported by all CA ports on the subnet * * ignore_existing_lfts -* This flag is a dynamic flag to instruct the LFT asssign to +* This flag is a dynamic flag to instruct the LFT assignment to * ignore existing legal LFT settings. * The value will be set according to : * - During SM init set to the reassign_lfts flag value -* - Comming out of STANDBY it will be cleared (other SM worked) +* - Coming out of STANDBY it will be cleared (other SM worked) * - Any change to the list of switches will set it to high -* - Set to FALSE on end of all lft assignments. +* - Set to FALSE upon end of all lft assignments. * * subnet_initalization_error * Similar to the force_immediate_heavy_sweep flag. If TRUE - * means that we had errors during initialization (due to SubnSet requests -* that failed). We want to declare the subnet as un-healthy, and force +* that failed). We want to declare the subnet as unhealthy, and force * another heavy sweep. * * force_immediate_heavy_sweep @@ -561,12 +655,12 @@ typedef struct _osm_subn * (meaning after moving from Standby|Discovering state), the SM must send * a PortInfoSet to all ports. After that - we want to minimize the number of * PortInfoSet requests sent, and to send only requests that change the value -* from what is updated in the port (or send a first request if this is a new port). -* We will set this flag to TRUE when entering the master state, and set it back -* to FALSE at the end of the drop manager. This is done since at the end of the -* drop manager we have updated all the ports that are reachable, and from now on -* these are the only ports we have data of. We don't want to send extra set requests -* to these ports anymore. +* from what is updated in the port (or send a first request if this is a new +* port). We will set this flag to TRUE when entering the master state, and +* set it back to FALSE at the end of the drop manager. This is done since at +* the end of the drop manager we have updated all the ports that are +* reachable, and from now on these are the only ports we have data of. We +* don't want to send extra set requests to these ports anymore. * * coming_out_of_standby * TRUE on the first sweep after the SM was in standby. @@ -599,13 +693,13 @@ osm_subn_construct( * This function does not return a value. * * NOTES -* Allows calling osm_subn_init, osm_subn_destroy, and osm_subn_is_inited. +* Allows calling osm_subn_init, and osm_subn_destroy. * * Calling osm_subn_construct is a prerequisite to calling any other * method except osm_subn_init. * * SEE ALSO -* Subnet object, osm_subn_init, osm_subn_destroy, osm_subn_is_inited +* Subnet object, osm_subn_init, osm_subn_destroy *********/ /****f* OpenSM: Subnet/osm_subn_destroy @@ -651,6 +745,7 @@ osm_subn_destroy( ib_api_status_t osm_subn_init( IN osm_subn_t* const p_subn, + IN struct _osm_opensm_t * const p_osm, IN const osm_subn_opt_t* const p_opt ); /* * PARAMETERS @@ -667,12 +762,11 @@ osm_subn_init( * Allows calling other Subnet methods. * * SEE ALSO -* Subnet object, osm_subn_construct, osm_subn_destroy, -* osm_subn_is_inited +* Subnet object, osm_subn_construct, osm_subn_destroy *********/ /* - Forward reference. + Forward references. */ struct _osm_mad_addr; struct _osm_log; @@ -692,11 +786,12 @@ struct _osm_port; * * SYNOPSIS */ -ib_gid_t +ib_api_status_t osm_get_gid_by_mad_addr( IN struct _osm_log *p_log, IN const osm_subn_t *p_subn, - IN const struct _osm_mad_addr *p_mad_addr ); + IN const struct _osm_mad_addr *p_mad_addr, + OUT ib_gid_t *p_gid); /* * PARAMETERS * p_log @@ -705,11 +800,14 @@ osm_get_gid_by_mad_addr( * p_subn * [in] Pointer to subnet object. * -* p_mad_addr -* [in] Pointer to mad address object. +* p_mad_addr +* [in] Pointer to mad address object. * +* p_gid +* [out] Pointer to the GID structure to fill in. +* * RETURN VALUES -* Requestor gid object if found. Null otherwise. +* IB_SUCCESS if able to find the GID by address given. * * NOTES * @@ -732,7 +830,7 @@ struct _osm_physp * osm_get_physp_by_mad_addr( IN struct _osm_log *p_log, IN const osm_subn_t *p_subn, - IN struct _osm_mad_addr *p_mad_addr ); + IN struct _osm_mad_addr *p_mad_addr ); /* * PARAMETERS * p_log @@ -741,8 +839,8 @@ osm_get_physp_by_mad_addr( * p_subn * [in] Pointer to subnet object. * -* p_mad_addr -* [in] Pointer to mad address object. +* p_mad_addr +* [in] Pointer to mad address object. * * RETURN VALUES * Pointer to requester physical port object if found. Null otherwise. @@ -768,7 +866,7 @@ struct _osm_port * osm_get_port_by_mad_addr( IN struct _osm_log *p_log, IN const osm_subn_t *p_subn, - IN struct _osm_mad_addr *p_mad_addr ); + IN struct _osm_mad_addr *p_mad_addr ); /* * PARAMETERS * p_log @@ -777,8 +875,8 @@ osm_get_port_by_mad_addr( * p_subn * [in] Pointer to subnet object. * -* p_mad_addr -* [in] Pointer to mad address object. +* p_mad_addr +* [in] Pointer to mad address object. * * RETURN VALUES * Pointer to requester port object if found. Null otherwise. @@ -793,7 +891,7 @@ osm_get_port_by_mad_addr( * osm_get_switch_by_guid * * DESCRIPTION -* The looks for the given switch guid in the subnet table of switches by guid. +* Looks for the given switch guid in the subnet table of switches by guid. * NOTE: this code is not thread safe. Need to grab the lock before * calling it. * @@ -801,8 +899,8 @@ osm_get_port_by_mad_addr( */ struct _osm_switch * osm_get_switch_by_guid( - IN const osm_subn_t *p_subn, - IN uint64_t guid); + IN const osm_subn_t *p_subn, + IN uint64_t guid ); /* * PARAMETERS * p_subn @@ -813,13 +911,12 @@ osm_get_switch_by_guid( * * RETURN VALUES * The switch structure pointer if found. NULL otherwise. -* NOTE: should be called only after osm_subn_is_inited * -* SEE ALSO g529 - +* SEE ALSO * Subnet object, osm_subn_construct, osm_subn_destroy, -* osm_subn_is_inited, osm_switch_t +* osm_switch_t *********/ + /****f* OpenSM: Subnet/osm_get_node_by_guid * NAME * osm_get_node_by_guid @@ -833,8 +930,8 @@ osm_get_switch_by_guid( */ struct _osm_node * osm_get_node_by_guid( - IN osm_subn_t const *p_subn, - IN uint64_t guid); + IN osm_subn_t const *p_subn, + IN uint64_t guid ); /* * PARAMETERS * p_subn @@ -845,11 +942,10 @@ osm_get_node_by_guid( * * RETURN VALUES * The node structure pointer if found. NULL otherwise. -* NOTE: should be called only after osm_subn_is_inited * * SEE ALSO * Subnet object, osm_subn_construct, osm_subn_destroy, -* osm_subn_is_inited, osm_node_t +* osm_node_t *********/ /****f* OpenSM: Subnet/osm_get_port_by_guid @@ -865,8 +961,8 @@ osm_get_node_by_guid( */ struct _osm_port * osm_get_port_by_guid( - IN osm_subn_t const *p_subn, - IN uint64_t guid); + IN osm_subn_t const *p_subn, + IN uint64_t guid ); /* * PARAMETERS * p_subn @@ -877,11 +973,10 @@ osm_get_port_by_guid( * * RETURN VALUES * The port structure pointer if found. NULL otherwise. -* NOTE: should be called only after osm_subn_is_inited * * SEE ALSO * Subnet object, osm_subn_construct, osm_subn_destroy, -* osm_subn_is_inited, osm_port_t +* osm_port_t *********/ /****f* OpenSM: Helper/osm_get_physp_by_mad_addr @@ -900,7 +995,7 @@ struct _osm_physp * osm_get_physp_by_mad_addr( IN struct _osm_log *p_log, IN const osm_subn_t *p_subn, - IN struct _osm_mad_addr *p_mad_addr ); + IN struct _osm_mad_addr *p_mad_addr ); /* * PARAMETERS * p_log @@ -909,8 +1004,8 @@ osm_get_physp_by_mad_addr( * p_subn * [in] Pointer to subnet object. * -* p_mad_addr -* [in] Pointer to mad address object. +* p_mad_addr +* [in] Pointer to mad address object. * * RETURN VALUES * Pointer to requester physical port object if found. Null otherwise. @@ -944,8 +1039,7 @@ osm_subn_set_default_opt( * NOTES * * SEE ALSO -* Subnet object, osm_subn_construct, osm_subn_destroy, -* osm_subn_is_inited +* Subnet object, osm_subn_construct, osm_subn_destroy *********/ /****f* OpenSM: Subnet/osm_subn_set_default_opt @@ -972,8 +1066,7 @@ osm_subn_set_default_opt( * NOTES * * SEE ALSO -* Subnet object, osm_subn_construct, osm_subn_destroy, -* osm_subn_is_inited +* Subnet object, osm_subn_construct, osm_subn_destroy *********/ /****f* OpenSM: Subnet/osm_subn_parse_conf_file @@ -1003,8 +1096,34 @@ osm_subn_parse_conf_file( * OSM_DEFAULT_CACHE_DIR or OSM_CACHE_DIR the name is opensm.opts * * SEE ALSO -* Subnet object, osm_subn_construct, osm_subn_destroy, -* osm_subn_is_inited +* Subnet object, osm_subn_construct, osm_subn_destroy +*********/ + +/****f* OpenSM: Subnet/osm_subn_parse_conf_file +* NAME +* osm_subn_rescan_conf_file +* +* DESCRIPTION +* The osm_subn_rescan_conf_file function parses the configuration +* file and update selected subnet options +* +* SYNOPSIS +*/ +void +osm_subn_rescan_conf_file( + IN osm_subn_opt_t* const p_opts ); +/* +* PARAMETERS +* +* p_opt +* [in] Pointer to the subnet options structure. +* +* RETURN VALUES +* None +* +* NOTES +* This uses the same file as osm_subn_parse_conf_file() +* *********/ /****f* OpenSM: Subnet/osm_subn_write_conf_file @@ -1033,10 +1152,10 @@ osm_subn_write_conf_file( * OSM_DEFAULT_CACHE_DIR or OSM_CACHE_DIR the name is opensm.opts * * SEE ALSO -* Subnet object, osm_subn_construct, osm_subn_destroy, -* osm_subn_is_inited +* Subnet object, osm_subn_construct, osm_subn_destroy *********/ END_C_DECLS #endif /* _OSM_SUBNET_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_sw_info_rcv.h b/trunk/ulp/opensm/user/include/opensm/osm_sw_info_rcv.h index ff238d04..3695e3db 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_sw_info_rcv.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_sw_info_rcv.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -45,7 +45,6 @@ * $Revision: 1.4 $ */ - #ifndef _OSM_SI_RCV_H_ #define _OSM_SI_RCV_H_ @@ -84,6 +83,7 @@ BEGIN_C_DECLS * Steve King, Intel * *********/ + /****s* OpenSM: Switch Info Receiver/osm_si_rcv_t * NAME * osm_si_rcv_t @@ -98,11 +98,11 @@ BEGIN_C_DECLS */ typedef struct _osm_si_rcv { - osm_subn_t *p_subn; - osm_log_t *p_log; - osm_req_t *p_req; + osm_subn_t *p_subn; + osm_log_t *p_log; + osm_req_t *p_req; osm_state_mgr_t *p_state_mgr; - cl_plock_t *p_lock; + cl_plock_t *p_lock; } osm_si_rcv_t; /* @@ -260,7 +260,7 @@ boolean_t osm_si_rcv_is_inited( * * NOTES * The osm_si_rcv_construct or osm_si_rcv_init must be -* called before using this function. +* called before using this function. * * SEE ALSO * Switch Info Receiver object, osm_si_rcv_construct, @@ -301,3 +301,4 @@ void osm_si_rcv_process( END_C_DECLS #endif /* _OSM_SI_RCV_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_sw_info_rcv_ctrl.h b/trunk/ulp/opensm/user/include/opensm/osm_sw_info_rcv_ctrl.h index f282d16f..5e745960 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_sw_info_rcv_ctrl.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_sw_info_rcv_ctrl.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -45,12 +45,10 @@ * $Revision: 1.4 $ */ - #ifndef _OSM_SI_RCV_CTRL_H_ #define _OSM_SI_RCV_CTRL_H_ - -#include +#include #include #include #include @@ -83,6 +81,7 @@ BEGIN_C_DECLS * Steve King, Intel * *********/ + /****s* OpenSM: Switch Info Receive Controller/osm_si_rcv_ctrl_t * NAME * osm_si_rcv_ctrl_t @@ -97,9 +96,9 @@ BEGIN_C_DECLS */ typedef struct _osm_si_rcv_ctrl { - osm_si_rcv_t *p_rcv; - osm_log_t *p_log; - cl_dispatcher_t *p_disp; + osm_si_rcv_t *p_rcv; + osm_log_t *p_log; + cl_dispatcher_t *p_disp; cl_disp_reg_handle_t h_disp; } osm_si_rcv_ctrl_t; @@ -249,7 +248,7 @@ boolean_t osm_si_rcv_ctrl_is_inited( * * NOTES * The osm_si_rcv_ctrl_construct or osm_si_rcv_ctrl_init must be -* called before using this function. +* called before using this function. * * SEE ALSO * Switch Info Receive Controller object, osm_si_rcv_ctrl_construct, @@ -259,3 +258,4 @@ boolean_t osm_si_rcv_ctrl_is_inited( END_C_DECLS #endif /* _OSM_SI_RCV_CTRL_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_sweep_fail_ctrl.h b/trunk/ulp/opensm/user/include/opensm/osm_sweep_fail_ctrl.h index 0f515b22..3d0d35ec 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_sweep_fail_ctrl.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_sweep_fail_ctrl.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -45,12 +45,10 @@ * $Revision: 1.4 $ */ - #ifndef _OSM_SWEEP_FAIL_CTRL_H_ #define _OSM_SWEEP_FAIL_CTRL_H_ - -#include +#include #include #include #include @@ -84,6 +82,7 @@ BEGIN_C_DECLS * Steve King, Intel * *********/ + /****s* OpenSM: Sweep Fail Controller/osm_sweep_fail_ctrl_t * NAME * osm_sweep_fail_ctrl_t @@ -237,3 +236,4 @@ osm_sweep_fail_ctrl_init( END_C_DECLS #endif /* _OSM_SWEEP_FAIL_CTRL_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_switch.h b/trunk/ulp/opensm/user/include/opensm/osm_switch.h index ffcfa8ba..2f7ca2f1 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_switch.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_switch.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -87,25 +87,6 @@ BEGIN_C_DECLS * *********/ -/****h* OpenSM/Switch -* NAME -* Switch -* -* DESCRIPTION -* The Switch object encapsulates the information needed by the -* OpenSM to manage switches. The OpenSM allocates one switch object -* per switch in the IBA subnet. -* -* The Switch object is not thread safe, thus callers must provide -* serialization. -* -* This object should be treated as opaque and should be -* manipulated only through the provided functions. -* -* AUTHOR -* Steve King, Intel -* -*********/ /****s* OpenSM: Switch/osm_switch_t * NAME * osm_switch_t @@ -121,14 +102,14 @@ BEGIN_C_DECLS typedef struct _osm_switch { cl_map_item_t map_item; - osm_node_t *p_node; + osm_node_t *p_node; ib_switch_info_t switch_info; osm_fwd_tbl_t fwd_tbl; osm_lid_matrix_t lmx; + uint16_t max_lid_ho; osm_port_profile_t *p_prof; osm_mcast_tbl_t mcast_tbl; - uint32_t discovery_count; - + uint32_t discovery_count; } osm_switch_t; /* * FIELDS @@ -148,6 +129,9 @@ typedef struct _osm_switch * LID Matrix for this switch containing the hop count * to every LID from every port. * +* max_lid_ho +* Max LID that is accessible from this switch. +* * p_pro * Pointer to array of Port Profile objects for this switch. * @@ -184,13 +168,13 @@ osm_switch_construct( * This function does not return a value. * * NOTES -* Allows calling osm_switch_init, osm_switch_destroy, and osm_switch_is_inited. +* Allows calling osm_switch_init, and osm_switch_destroy. * * Calling osm_switch_construct is a prerequisite to calling any other * method except osm_switch_init. * * SEE ALSO -* Switch object, osm_switch_init, osm_switch_destroy, osm_switch_is_inited +* Switch object, osm_switch_init, osm_switch_destroy *********/ /****f* OpenSM: Switch/osm_switch_destroy @@ -250,7 +234,6 @@ osm_switch_delete( * Switch object, osm_switch_construct, osm_switch_init *********/ - /****f* OpenSM: Switch/osm_switch_init * NAME * osm_switch_init @@ -284,9 +267,9 @@ osm_switch_init( * Allows calling other node methods. * * SEE ALSO -* Switch object, osm_switch_construct, osm_switch_destroy, -* osm_switch_is_inited +* Switch object, osm_switch_construct, osm_switch_destroy *********/ + /****f* OpenSM: Switch/osm_switch_new * NAME * osm_switch_new @@ -457,9 +440,9 @@ osm_switch_set_hops( * SEE ALSO *********/ -/****f* OpenSM: Switch/osm_switch_set_hops +/****f* OpenSM: Switch/osm_switch_set_min_lid_size * NAME -* osm_switch_set_hops +* osm_switch_set_min_lid_size * * DESCRIPTION * Sets the size of the switch's routing table to at least accomodate the @@ -559,33 +542,6 @@ osm_switch_get_port_by_lid( * Switch object *********/ -/****f* OpenSM: Switch/osm_switch_get_lid -* NAME -* osm_switch_get_lid -* -* DESCRIPTION -* Gets the switch's LID. -* -* SYNOPSIS -*/ -ib_net16_t -osm_switch_get_lid( - IN const osm_switch_t* const p_sw ); -/* -* PARAMETERS -* p_sw -* [in] Pointer to an osm_switch_t object. -* -* RETURN VALUES -* Returns the switch's LID. A value of zero means no LID has -* been assigned to the switch. -* -* NOTES -* -* SEE ALSO -* Switch object -*********/ - /****f* OpenSM: Switch/osm_switch_get_physp_ptr * NAME * osm_switch_get_physp_ptr @@ -630,25 +586,26 @@ osm_switch_get_physp_ptr( */ static inline osm_physp_t* osm_switch_get_route_by_lid( - IN const osm_switch_t* const p_sw, - IN const ib_net16_t lid ) + IN const osm_switch_t* const p_sw, + IN const ib_net16_t lid ) { - uint8_t port_num; - CL_ASSERT( p_sw ); - CL_ASSERT( lid ); + uint8_t port_num; + + CL_ASSERT( p_sw ); + CL_ASSERT( lid ); - port_num = osm_fwd_tbl_get( &p_sw->fwd_tbl, cl_ntoh16( lid ) ); - /* - In order to avoid holes in the subnet (usually happens when - running UPDN alogrithm ), i.e. cases where port is - unreachable through a switch (we put a OSM_NO_PATH value at - the port entry , we do not assert on unreachable lids entries - at the fwd table but return NULL - */ - if (port_num != OSM_NO_PATH) - return( osm_node_get_physp_ptr( p_sw->p_node, port_num ) ); - else - return NULL; + port_num = osm_fwd_tbl_get( &p_sw->fwd_tbl, cl_ntoh16( lid ) ); + /* + In order to avoid holes in the subnet (usually happens when + running UPDN algorithm), i.e. cases where port is + unreachable through a switch (we put an OSM_NO_PATH value at + the port entry, we do not assert on unreachable lid entries + at the fwd table but return NULL + */ + if (port_num != OSM_NO_PATH) + return( osm_node_get_physp_ptr( p_sw->p_node, port_num ) ); + else + return NULL; } /* * PARAMETERS @@ -700,6 +657,40 @@ osm_switch_get_si_ptr( * Switch object *********/ +/****f* OpenSM: Switch/osm_switch_sp0_is_lmc_capable +* NAME +* osm_switch_sp0_is_lmc_capable +* +* DESCRIPTION +* Returns whether switch port 0 (SP0) can support LMC +* +*/ +static inline unsigned +osm_switch_sp0_is_lmc_capable( + IN const osm_switch_t* const p_sw, + IN osm_subn_t *p_subn) +{ + return (p_subn->opt.lmc_esp0 && + ib_switch_info_is_enhanced_port0(&p_sw->switch_info)) ? 1 : 0; +} +/* +* PARAMETERS +* p_sw +* [in] Pointer to an osm_switch_t object. +* +* p_subn +* [in] Pointer to an osm_subn_t object. +* +* RETURN VALUES +* TRUE if SP0 is enhanced and globally enabled. FALSE otherwise. +* +* NOTES +* This is workaround function, it takes into account user defined +* p_subn->opt.lmc_esp0 parameter. +* +* SEE ALSO +*********/ + /****f* OpenSM: Switch/osm_switch_get_max_block_id * NAME * osm_switch_get_max_block_id @@ -714,7 +705,7 @@ osm_switch_get_max_block_id( IN const osm_switch_t* const p_sw ) { return( (uint32_t)(osm_fwd_tbl_get_size( &p_sw->fwd_tbl ) / - osm_fwd_tbl_get_lids_per_block( &p_sw->fwd_tbl ) ) ); + osm_fwd_tbl_get_lids_per_block( &p_sw->fwd_tbl ) ) ); } /* * PARAMETERS @@ -740,7 +731,7 @@ osm_switch_get_max_block_id( * * SYNOPSIS */ -static inline uint32_t +static inline uint16_t osm_switch_get_max_block_id_in_use( IN const osm_switch_t* const p_sw ) { @@ -782,7 +773,7 @@ osm_switch_get_node_ptr( * [in] Pointer to an osm_switch_t object. * * RETURN VALUES -* Returns a pointer to the LID matrix for this switch. +* Returns a pointer to the Node object for this switch. * * NOTES * @@ -804,6 +795,8 @@ static inline uint16_t osm_switch_get_max_lid_ho( IN const osm_switch_t* const p_sw ) { + if (p_sw->max_lid_ho != 0) + return p_sw->max_lid_ho; return( osm_lid_matrix_get_max_lid_ho( &p_sw->lmx ) ); } /* @@ -884,7 +877,6 @@ osm_switch_get_fwd_tbl_block( * SEE ALSO *********/ - /****f* OpenSM: Switch/osm_switch_supports_mcast * NAME * osm_switch_supports_mcast @@ -948,26 +940,21 @@ osm_switch_set_switch_info( * SEE ALSO *********/ -/****f* OpenSM: Switch/osm_switch_set_path +/****f* OpenSM: Switch/osm_switch_count_path * NAME -* osm_switch_set_path +* osm_switch_count_path * * DESCRIPTION -* Sets the port to route the specified LID. +* Counts this path in port profile. * * SYNOPSIS */ static inline void -osm_switch_set_path( +osm_switch_count_path( IN osm_switch_t* const p_sw, - IN const uint16_t lid_ho, - IN const uint8_t port, - IN const boolean_t ignore_port_prof + IN const uint8_t port ) { - CL_ASSERT( p_sw ); - osm_fwd_tbl_set( &p_sw->fwd_tbl, lid_ho, port ); - if (! ignore_port_prof) osm_port_prof_path_count_inc( &p_sw->p_prof[port] ); } /* @@ -975,11 +962,8 @@ osm_switch_set_path( * p_sw * [in] Pointer to the switch object. * -* lid_ho -* [in] LID value (host order) for which to set the route. -* * port -* [in] Port to route the specified LID value. +* [in] Port to count path. * * RETURN VALUE * None. @@ -1068,16 +1052,138 @@ osm_switch_set_mft_block( * SEE ALSO *********/ +/****f* OpenSM: Switch/osm_switch_get_mft_block +* NAME +* osm_switch_get_mft_block +* +* DESCRIPTION +* Retrieve a block of multicast port masks from the multicast table. +* +* SYNOPSIS +*/ +static inline boolean_t +osm_switch_get_mft_block( + IN osm_switch_t* const p_sw, + IN const uint16_t block_num, + IN const uint8_t position, + OUT ib_net16_t* const p_block ) +{ + CL_ASSERT( p_sw ); + return( osm_mcast_tbl_get_block( &p_sw->mcast_tbl, + block_num, position, p_block ) ); +} +/* +* PARAMETERS +* p_sw +* [in] Pointer to the switch object. +* +* block_num +* [in] Block number (0-511) to set. +* +* position +* [in] Port mask position (0-15) to set. +* +* p_block +* [out] Pointer to the block of port masks stored. +* +* RETURN VALUES +* Returns true if there are more blocks necessary to +* configure all the MLIDs reachable from this switch. +* FALSE otherwise. +* +* NOTES +* +* SEE ALSO +*********/ + +/****f* OpenSM: Switch/osm_switch_get_mft_max_block +* NAME +* osm_switch_get_mft_max_block +* +* DESCRIPTION +* Get the max_block from the associated multicast table. +* +* SYNOPSIS +*/ +static inline uint16_t +osm_switch_get_mft_max_block( + IN osm_switch_t* const p_sw ) +{ + CL_ASSERT( p_sw ); + return( osm_mcast_tbl_get_max_block( &p_sw->mcast_tbl ) ); +} +/* +* PARAMETERS +* p_sw +* [in] Pointer to the switch object. +* +* RETURN VALUE +*/ + +/****f* OpenSM: Switch/osm_switch_get_mft_max_block_in_use +* NAME +* osm_switch_get_mft_max_block_in_use +* +* DESCRIPTION +* Get the max_block_in_use from the associated multicast table. +* +* SYNOPSIS +*/ +static inline int16_t +osm_switch_get_mft_max_block_in_use( + IN osm_switch_t* const p_sw ) +{ + CL_ASSERT( p_sw ); + return( osm_mcast_tbl_get_max_block_in_use( &p_sw->mcast_tbl ) ); +} +/* +* PARAMETERS +* p_sw +* [in] Pointer to the switch object. +* +* RETURN VALUES +* Returns the maximum block ID in use in this switch's mcast table. +* A value of -1 indicates no blocks are in use. +* +* NOTES +* +* SEE ALSO +*/ + +/****f* OpenSM: Switch/osm_switch_get_mft_max_position +* NAME +* osm_switch_get_mft_max_position +* +* DESCRIPTION +* Get the max_position from the associated multicast table. +* +* SYNOPSIS +*/ +static inline uint8_t +osm_switch_get_mft_max_position( + IN osm_switch_t* const p_sw ) +{ + CL_ASSERT( p_sw ); + return( osm_mcast_tbl_get_max_position( &p_sw->mcast_tbl ) ); +} +/* +* PARAMETERS +* p_sw +* [in] Pointer to the switch object. +* +* RETURN VALUE +*/ + /****f* OpenSM: Switch/osm_switch_recommend_path * NAME * osm_switch_recommend_path * * DESCRIPTION * Returns the recommended port on which to route this LID. -* In cases where LMC > 0, the remote side system and node -* used for the routing are tracked in the provided arrays -* (and counts) such that other lid for the same port will -* try and avoid going through the same remote system/node. +* In cases where LMC > 0, the remote side system and node +* used for the routing are tracked in the provided arrays +* (and counts) such that other lid for the same port will +* try and avoid going through the same remote system/node. * * SYNOPSIS */ @@ -1089,9 +1195,7 @@ osm_switch_recommend_path( IN OUT uint64_t *remote_sys_guids, IN OUT uint16_t *p_num_used_sys, IN OUT uint64_t *remote_node_guids, - IN OUT uint16_t *p_num_used_nodes, - IN const uint32_t max_routes_subscribed, - IN boolean_t ui_ucast_fdb_assign_func_defined + IN OUT uint16_t *p_num_used_nodes ); /* * PARAMETERS @@ -1104,35 +1208,24 @@ osm_switch_recommend_path( * ignore_existing * [in] Set to cause the switch to choose the optimal route * regardless of existing paths. -* If false, the switch will choose an existing route if one exists, -* otherwise will choose the optimal route. +* If false, the switch will choose an existing route if one +* exists, otherwise will choose the optimal route. * * remote_sys_guids -* [in out] The array of remote system guids already used to route -* the other lids of the same target port (if LMC > 0). +* [in out] The array of remote system guids already used to +* route the other lids of the same target port (if LMC > 0). * -* p_num_used_sys -* [in out] The number of remote systems used for routing to the port. +* p_num_used_sys +* [in out] The number of remote systems used for routing to +* the port. * * remote_node_guids -* [in out] The array of remote node guids already used to route -* the other lids of the same target port (if LMC > 0). +* [in out] The array of remote node guids already used to route +* the other lids of the same target port (if LMC > 0). * -* p_num_used_nodes -* [in out] The number of remote nodes used for routing to the port. -* -* max_routes_subscribed -* [in] The maximum allowed number of target lids routed through -* a specific port of the switch. If the port already assigned -* (in the lfdb) this number of target lids - it will not be used -* even if it has the smallest hops count to the target lid. -* -* ui_ucast_fdb_assign_func_defined -* [in] If TRUE - this means that there is a ui ucast_fdb_assign table -* function defined (in pfn_ui_ucast_fdb_assign in subnet opts). This -* means that all current entries in the fdbs will be used. -* If FALSE - such function isn't defined. Do the minimum hop checks -* before accepting the current fdbs. +* p_num_used_nodes +* [in out] The number of remote nodes used for routing to +* the port. * * RETURN VALUE * Returns the recommended port on which to route this LID. @@ -1340,6 +1433,7 @@ osm_switch_is_in_mcast_tree( IN const uint16_t mlid_ho ) { const osm_mcast_tbl_t* p_tbl; + p_tbl = &p_sw->mcast_tbl; if( p_tbl ) return( osm_mcast_tbl_is_any_port( &p_sw->mcast_tbl, mlid_ho ) ); @@ -1392,6 +1486,7 @@ osm_switch_discovery_count_get( * SEE ALSO * Node object *********/ + /****f* OpenSM: Node/osm_switch_discovery_count_reset * NAME * osm_switch_discovery_count_reset @@ -1421,6 +1516,7 @@ osm_switch_discovery_count_reset( * SEE ALSO * Node object *********/ + /****f* OpenSM: Node/osm_switch_discovery_count_inc * NAME * osm_switch_discovery_count_inc @@ -1453,3 +1549,4 @@ osm_switch_discovery_count_inc( END_C_DECLS #endif /* _OSM_SWITCH_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_trap_rcv.h b/trunk/ulp/opensm/user/include/opensm/osm_trap_rcv.h index 5a3945f1..5f8e7274 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_trap_rcv.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_trap_rcv.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -44,12 +44,11 @@ * $Revision: 1.3 $ */ - #ifndef _OSM_TRAP_RCV_H_ #define _OSM_TRAP_RCV_H_ #include -#include +#include #include #include #include @@ -86,6 +85,7 @@ BEGIN_C_DECLS * Steve King, Intel * *********/ + /****s* OpenSM: Trap Receiver/osm_trap_rcv_t * NAME * osm_trap_rcv_t @@ -98,15 +98,15 @@ BEGIN_C_DECLS * * SYNOPSIS */ -typedef struct _osm_tap_rcv +typedef struct _osm_trap_rcv { - osm_subn_t *p_subn; - osm_stats_t *p_stats; + osm_subn_t *p_subn; + osm_stats_t *p_stats; osm_log_t *p_log; - osm_resp_t *p_resp; - osm_state_mgr_t *p_state_mgr; - cl_plock_t *p_lock; - cl_event_wheel_t trap_aging_tracker; + osm_resp_t *p_resp; + osm_state_mgr_t *p_state_mgr; + cl_plock_t *p_lock; + cl_event_wheel_t trap_aging_tracker; } osm_trap_rcv_t; /* * FIELDS @@ -128,10 +128,10 @@ typedef struct _osm_tap_rcv * p_lock * Pointer to the serializing lock. * -* trap_aging_tracker -* An event wheel tracking erceived traps and their aging. -* Basically we can start a timer every time we receive a specific -* trap and check to seee if not expired next time it is received. +* trap_aging_tracker +* An event wheel tracking erceived traps and their aging. +* Basically we can start a timer every time we receive a specific +* trap and check to seee if not expired next time it is received. * * SEE ALSO * Trap Receiver object @@ -296,7 +296,7 @@ uint64_t osm_trap_rcv_aging_tracker_callback( IN uint64_t key, IN uint32_t num_regs, - IN void* context ); + IN void* context ); /* * PARAMETERS @@ -306,15 +306,15 @@ osm_trap_rcv_aging_tracker_callback( * num_regs * [in] The number of times the same event (key) was registered. * -* context -* [in] Pointer to the context given in the registering of the event. +* context +* [in] Pointer to the context given in the registering of the event. * * RETURN VALUES * None. * * NOTES -* This function is called by the cl_event_wheel when the aging tracker event -* has ended. +* This function is called by the cl_event_wheel when the aging tracker +* event has ended. * * SEE ALSO * Trap Receiver, Trap Response Controller @@ -323,3 +323,4 @@ osm_trap_rcv_aging_tracker_callback( END_C_DECLS #endif /* _OSM_TRAP_RCV_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_trap_rcv_ctrl.h b/trunk/ulp/opensm/user/include/opensm/osm_trap_rcv_ctrl.h index 483d13f8..c46be6a3 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_trap_rcv_ctrl.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_trap_rcv_ctrl.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -48,8 +48,7 @@ #ifndef _OSM_TRAP_RCV_CTRL_H_ #define _OSM_TRAP_RCV_CTRL_H_ - -#include +#include #include #include #include @@ -82,6 +81,7 @@ BEGIN_C_DECLS * Yael Kalka, Mellanox * *********/ + /****s* OpenSM: Trap Receive Controller/osm_trap_rcv_ctrl_t * NAME * osm_trap_rcv_ctrl_t @@ -229,3 +229,4 @@ osm_trap_rcv_ctrl_init( END_C_DECLS #endif /* OSM_TRAP_RCV_CTRL_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_ts_useraccess.h b/trunk/ulp/opensm/user/include/opensm/osm_ts_useraccess.h index fb2febaf..39df01ba 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_ts_useraccess.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_ts_useraccess.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -31,6 +31,7 @@ * $Id$ */ + #include "ts_ib_useraccess.h" #ifdef __cplusplus @@ -50,3 +51,4 @@ typedef struct ib_gid_entry_ioctl osm_ts_gid_entry_ioctl; END_C_DECLS + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_ucast_mgr.h b/trunk/ulp/opensm/user/include/opensm/osm_ucast_mgr.h index af86f2ae..25d19d55 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_ucast_mgr.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_ucast_mgr.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -44,16 +44,15 @@ * $Revision: 1.4 $ */ - #ifndef _OSM_UCAST_MGR_H_ #define _OSM_UCAST_MGR_H_ - #include #include #include #include #include +#include #include #ifdef __cplusplus @@ -85,6 +84,7 @@ BEGIN_C_DECLS * Steve King, Intel * *********/ + /****s* OpenSM: Unicast Manager/osm_ucast_mgr_t * NAME * osm_ucast_mgr_t @@ -99,12 +99,12 @@ BEGIN_C_DECLS */ typedef struct _osm_ucast_mgr { - osm_subn_t *p_subn; - osm_req_t *p_req; - osm_log_t *p_log; - cl_plock_t *p_lock; - char *p_report_buf; - + osm_subn_t *p_subn; + osm_req_t *p_req; + osm_log_t *p_log; + cl_plock_t *p_lock; + boolean_t any_change; + uint8_t *lft_buf; } osm_ucast_mgr_t; /* * FIELDS @@ -120,6 +120,14 @@ typedef struct _osm_ucast_mgr * p_lock * Pointer to the serializing lock. * +* any_change +* Initialized to FALSE at the beginning of the algorithm, +* set to TRUE by osm_ucast_mgr_set_fwd_table() if any mad +* was sent. +* +* lft_buf +* LFT buffer - used during LFT calculation/setup. +* * SEE ALSO * Unicast Manager object *********/ @@ -203,7 +211,6 @@ osm_ucast_mgr_init( IN osm_ucast_mgr_t* const p_mgr, IN osm_req_t* const p_req, IN osm_subn_t* const p_subn, - IN char* const p_report_buf, IN osm_log_t* const p_log, IN cl_plock_t* const p_lock ); /* @@ -217,9 +224,6 @@ osm_ucast_mgr_init( * p_subn * [in] Pointer to the Subnet object for this subnet. * -* p_report_buf -* [in] Pointer to the large log buffer used for user reporting. -* * p_log * [in] Pointer to the log object. * @@ -238,6 +242,56 @@ osm_ucast_mgr_init( * osm_ucast_mgr_destroy *********/ +/****f* OpenSM: Unicast Manager/osm_ucast_mgr_set_fwd_table +* NAME +* osm_ucast_mgr_set_fwd_table +* +* DESCRIPTION +* Setup forwarding table for the switch (from prepared lft_buf). +* +* SYNOPSIS +*/ +void +osm_ucast_mgr_set_fwd_table( + IN osm_ucast_mgr_t* const p_mgr, + IN osm_switch_t* const p_sw ); +/* +* PARAMETERS +* p_mgr +* [in] Pointer to an osm_ucast_mgr_t object. +* +* p_mgr +* [in] Pointer to an osm_switch_t object. +* +* SEE ALSO +* Unicast Manager +*********/ + +/****f* OpenSM: Unicast Manager/osm_ucast_mgr_build_lid_matrices +* NAME +* osm_ucast_mgr_build_lid_matrices +* +* DESCRIPTION +* Build switches's lid matrices. +* +* SYNOPSIS +*/ +void +osm_ucast_mgr_build_lid_matrices( + IN osm_ucast_mgr_t* const p_mgr ); +/* +* PARAMETERS +* p_mgr +* [in] Pointer to an osm_ucast_mgr_t object. +* +* NOTES +* This function processes the subnet, configuring switches' +* min hops tables (aka lid matrices). +* +* SEE ALSO +* Unicast Manager +*********/ + /****f* OpenSM: Unicast Manager/osm_ucast_mgr_process * NAME * osm_ucast_mgr_process @@ -271,3 +325,4 @@ osm_ucast_mgr_process( END_C_DECLS #endif /* _OSM_UCAST_MGR_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_umadt.h b/trunk/ulp/opensm/user/include/opensm/osm_umadt.h index 3285cebe..80c969e0 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_umadt.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_umadt.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -44,7 +44,6 @@ * $Revision: 1.4 $ */ - #ifndef _OSM_UMADT_h_ #define _OSM_UMADT_h_ @@ -76,6 +75,7 @@ typedef struct _umadt_obj_t{ }umadt_obj_t; /*********/ + /****s* OpenSM: Umadt MAD Wrapper/osm_bind_info * NAME * osm_bind_info @@ -140,3 +140,4 @@ typedef struct _trans_context_t { END_C_DECLS #endif /*_OSM_UMADT_h_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_version.h b/trunk/ulp/opensm/user/include/opensm/osm_version.h index e1c4687f..7be8e07f 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_version.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_version.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -54,9 +54,10 @@ BEGIN_C_DECLS * * SYNOPSIS */ -#define OSM_VERSION "OpenSM Rev:openib-1.2.0" +#define OSM_VERSION "OpenSM Rev:openib-3.0.0" /********/ END_C_DECLS #endif /* _OSM_VERSION_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_vl15intf.h b/trunk/ulp/opensm/user/include/opensm/osm_vl15intf.h index 4257f49c..f56a6ca3 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_vl15intf.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_vl15intf.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -31,6 +31,7 @@ * $Id$ */ + /* * Abstract: * Declaration of osm_vl15_t. @@ -43,7 +44,6 @@ * $Revision: 1.5 $ */ - #ifndef _OSM_VL15INTF_H_ #define _OSM_VL15INTF_H_ @@ -414,3 +414,4 @@ osm_vl15_shutdown( END_C_DECLS #endif /* _OSM_VL15INTF_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_vl_arb_rcv.h b/trunk/ulp/opensm/user/include/opensm/osm_vl_arb_rcv.h index d9573420..9b57aeef 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_vl_arb_rcv.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_vl_arb_rcv.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -35,7 +35,7 @@ /* * Abstract: * Declaration of osm_vla_rcv_t. - * This object represents the Vl Arbitration Receiver object. + * This object represents the VL Arbitration Receiver object. * This object is part of the OpenSM family of objects. * * Environment: @@ -44,11 +44,9 @@ * $Revision: 1.3 $ */ - #ifndef _OSM_VLA_RCV_H_ #define _OSM_VLA_RCV_H_ - #include #include #include @@ -67,15 +65,15 @@ BEGIN_C_DECLS -/****h* OpenSM/Vl Arbitration Receiver +/****h* OpenSM/VL Arbitration Receiver * NAME -* Vl Arbitration Receiver +* VL Arbitration Receiver * * DESCRIPTION -* The Vl Arbitration Receiver object encapsulates the information +* The VL Arbitration Receiver object encapsulates the information * needed to set or get the vl arbitration attribute from a port. * -* The Vl Arbitration Receiver object is thread safe. +* The VL Arbitration Receiver object is thread safe. * * This object should be treated as opaque and should be * manipulated only through the provided functions. @@ -84,12 +82,13 @@ BEGIN_C_DECLS * Eitan Zahavi, Mellanox * *********/ -/****s* OpenSM: Vl Arbitration Receiver/osm_vla_rcv_t + +/****s* OpenSM: VL Arbitration Receiver/osm_vla_rcv_t * NAME * osm_vla_rcv_t * * DESCRIPTION -* Vl Arbitration Receiver structure. +* VL Arbitration Receiver structure. * * This object should be treated as opaque and should * be manipulated only through the provided functions. @@ -119,15 +118,15 @@ typedef struct _osm_vla_rcv * Pointer to the serializing lock. * * SEE ALSO -* Vl Arbitration Receiver object +* VL Arbitration Receiver object *********/ -/****f* OpenSM: Vl Arbitration Receiver/osm_vla_rcv_construct +/****f* OpenSM: VL Arbitration Receiver/osm_vla_rcv_construct * NAME * osm_vla_rcv_construct * * DESCRIPTION -* This function constructs a Vl Arbitration Receiver object. +* This function constructs a VL Arbitration Receiver object. * * SYNOPSIS */ @@ -136,7 +135,7 @@ void osm_vla_rcv_construct( /* * PARAMETERS * p_ctrl -* [in] Pointer to a Vl Arbitration Receiver object to construct. +* [in] Pointer to a VL Arbitration Receiver object to construct. * * RETURN VALUE * This function does not return a value. @@ -148,11 +147,11 @@ void osm_vla_rcv_construct( * method except osm_vla_rcv_init. * * SEE ALSO -* Vl Arbitration Receiver object, osm_vla_rcv_init, +* VL Arbitration Receiver object, osm_vla_rcv_init, * osm_vla_rcv_destroy *********/ -/****f* OpenSM: Vl Arbitration Receiver/osm_vla_rcv_destroy +/****f* OpenSM: VL Arbitration Receiver/osm_vla_rcv_destroy * NAME * osm_vla_rcv_destroy * @@ -174,23 +173,23 @@ void osm_vla_rcv_destroy( * * NOTES * Performs any necessary cleanup of the specified -* Vl Arbitration Receiver object. +* VL Arbitration Receiver object. * Further operations should not be attempted on the destroyed object. * This function should only be called after a call to * osm_vla_rcv_construct or osm_vla_rcv_init. * * SEE ALSO -* Vl Arbitration Receiver object, osm_vla_rcv_construct, +* VL Arbitration Receiver object, osm_vla_rcv_construct, * osm_vla_rcv_init *********/ -/****f* OpenSM: Vl Arbitration Receiver/osm_vla_rcv_init +/****f* OpenSM: VL Arbitration Receiver/osm_vla_rcv_init * NAME * osm_vla_rcv_init * * DESCRIPTION * The osm_vla_rcv_init function initializes a -* Vl Arbitration Receiver object for use. +* VL Arbitration Receiver object for use. * * SYNOPSIS */ @@ -218,18 +217,18 @@ ib_api_status_t osm_vla_rcv_init( * [in] Pointer to the OpenSM serializing lock. * * RETURN VALUES -* CL_SUCCESS if the Vl Arbitration Receiver object was initialized +* CL_SUCCESS if the VL Arbitration Receiver object was initialized * successfully. * * NOTES -* Allows calling other Vl Arbitration Receiver methods. +* Allows calling other VL Arbitration Receiver methods. * * SEE ALSO -* Vl Arbitration Receiver object, osm_vla_rcv_construct, +* VL Arbitration Receiver object, osm_vla_rcv_construct, * osm_vla_rcv_destroy *********/ -/****f* OpenSM: Vl Arbitration Receiver/osm_vla_rcv_process +/****f* OpenSM: VL Arbitration Receiver/osm_vla_rcv_process * NAME * osm_vla_rcv_process * @@ -257,9 +256,10 @@ void osm_vla_rcv_process( * This function processes a SLtoVL attribute. * * SEE ALSO -* Vl Arbitration Receiver, Vl Arbitration Response Controller +* VL Arbitration Receiver, VL Arbitration Response Controller *********/ END_C_DECLS #endif /* _OSM_VLA_RCV_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/osm_vl_arb_rcv_ctrl.h b/trunk/ulp/opensm/user/include/opensm/osm_vl_arb_rcv_ctrl.h index dc913433..bca54d61 100644 --- a/trunk/ulp/opensm/user/include/opensm/osm_vl_arb_rcv_ctrl.h +++ b/trunk/ulp/opensm/user/include/opensm/osm_vl_arb_rcv_ctrl.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -36,7 +36,7 @@ * Abstract: * Declaration of osm_vla_rcv_ctrl_t. * This object represents a controller that set or get resp the - * IBA Vl Arbitration Table attribute from a port. + * IBA VL Arbitration Table attribute from a port. * This object is part of the OpenSM family of objects. * * Environment: @@ -45,12 +45,10 @@ * $Revision: 1.3 $ */ - #ifndef _OSM_VLA_RCV_CTRL_H_ #define _OSM_VLA_RCV_CTRL_H_ - -#include +#include #include #include #include @@ -68,7 +66,7 @@ BEGIN_C_DECLS /****h* OpenSM/VL Arbitration Table Receive Controller * NAME -* Vl Arbitration Receive Controller +* VL Arbitration Receive Controller * * DESCRIPTION * The VL Arbitration Receive Controller object encapsulates @@ -83,6 +81,7 @@ BEGIN_C_DECLS * Eitan Zahavi, Mellanox * *********/ + /****s* OpenSM: VL Arbitration Receive Controller/osm_vla_rcv_ctrl_t * NAME * osm_vla_rcv_ctrl_t @@ -97,8 +96,8 @@ BEGIN_C_DECLS */ typedef struct _osm_vla_rcv_ctrl { - osm_vla_rcv_t *p_rcv; - osm_log_t *p_log; + osm_vla_rcv_t *p_rcv; + osm_log_t *p_log; cl_dispatcher_t *p_disp; cl_disp_reg_handle_t h_disp; @@ -249,7 +248,7 @@ boolean_t osm_vla_rcv_ctrl_is_inited( * * NOTES * The osm_vla_rcv_ctrl_construct or osm_vla_rcv_ctrl_init must be -* called before using this function. +* called before using this function. * * SEE ALSO * VL Arbitration Receive Controller object, osm_vla_rcv_ctrl_construct, @@ -259,3 +258,4 @@ boolean_t osm_vla_rcv_ctrl_is_inited( END_C_DECLS #endif /* _OSM_VLA_RCV_CTRL_H_ */ + diff --git a/trunk/ulp/opensm/user/include/opensm/st.h b/trunk/ulp/opensm/user/include/opensm/st.h index b2cb8c6c..ee0ba918 100644 --- a/trunk/ulp/opensm/user/include/opensm/st.h +++ b/trunk/ulp/opensm/user/include/opensm/st.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -104,3 +104,4 @@ st_table *st_copy(st_table *); END_C_DECLS #endif /* ST_INCLUDED */ + diff --git a/trunk/ulp/opensm/user/include/unistd.h b/trunk/ulp/opensm/user/include/unistd.h new file mode 100644 index 00000000..08fb5372 --- /dev/null +++ b/trunk/ulp/opensm/user/include/unistd.h @@ -0,0 +1,38 @@ +/* + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. + * + * This software is available to you under the OpenIB.org BSD license + * below: + * + * Redistribution and use in source and binary forms, with or + * without modification, are permitted provided that the following + * conditions are met: + * + * - Redistributions of source code must retain the above + * copyright notice, this list of conditions and the following + * disclaimer. + * + * - Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials + * provided with the distribution. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS + * BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN + * ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN + * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + * + * $Id: osm_base.h 1689 2006-09-12 20:55:47Z eitan $ + */ + + + +/* + * Abstract: + * Work around for cmpatibility mode with Linux. + * + */ diff --git a/trunk/ulp/opensm/user/include/vendor/osm_vendor.h b/trunk/ulp/opensm/user/include/vendor/osm_vendor.h index 21baaee6..2df637e7 100644 --- a/trunk/ulp/opensm/user/include/vendor/osm_vendor.h +++ b/trunk/ulp/opensm/user/include/vendor/osm_vendor.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Include file used by OpenSM to pull in the correct vendor file. @@ -74,3 +75,4 @@ #error Choose an interface in osm_vendor_select.h #endif + diff --git a/trunk/ulp/opensm/user/include/vendor/osm_vendor_al.h b/trunk/ulp/opensm/user/include/vendor/osm_vendor_al.h index 44b90863..80293c43 100644 --- a/trunk/ulp/opensm/user/include/vendor/osm_vendor_al.h +++ b/trunk/ulp/opensm/user/include/vendor/osm_vendor_al.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Declaration of osm_mad_wrapper_t. @@ -119,7 +120,7 @@ BEGIN_C_DECLS typedef struct _osm_ca_info { ib_net64_t guid; - uint32_t attr_size; + size_t attr_size; ib_ca_attr_t *p_attr; } osm_ca_info_t; @@ -275,7 +276,7 @@ typedef struct _osm_vendor { ib_al_handle_t h_al; osm_log_t *p_log; - size_t ca_count; + uint32_t ca_count; osm_ca_info_t *p_ca_info; uint32_t timeout; ib_ca_handle_t h_ca; @@ -306,9 +307,7 @@ typedef struct _osm_vendor *********/ -#ifndef OSM_BIND_INVALID_HANDLE -#define OSM_BIND_INVALID_HANDLE NULL -#endif +#define OSM_BIND_INVALID_HANDLE 0 /****s* OpenSM: Vendor AL/osm_bind_handle_t @@ -369,3 +368,4 @@ typedef struct _osm_vend_wrap_t END_C_DECLS #endif /* _OSM_VENDOR_AL_H_ */ + diff --git a/trunk/ulp/opensm/user/include/vendor/osm_vendor_api.h b/trunk/ulp/opensm/user/include/vendor/osm_vendor_api.h index f37b386a..e4c61284 100644 --- a/trunk/ulp/opensm/user/include/vendor/osm_vendor_api.h +++ b/trunk/ulp/opensm/user/include/vendor/osm_vendor_api.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -46,7 +46,6 @@ #ifndef _OSM_VENDOR_API_H_ #define _OSM_VENDOR_API_H_ - #include #include #include @@ -71,7 +70,7 @@ BEGIN_C_DECLS * * SYNOPSIS */ -typedef void (*osm_vend_mad_recv_callback_t)( +typedef void (*osm_vend_mad_recv_callback_t)( IN osm_madw_t *p_madw, IN void* bind_context, IN osm_madw_t *p_req_madw ); @@ -107,7 +106,7 @@ typedef void (*osm_vend_mad_recv_callback_t)( * * SYNOPSIS */ -typedef void (*osm_vend_mad_send_err_callback_t)( +typedef void (*osm_vend_mad_send_err_callback_t)( IN void* bind_context, IN osm_madw_t *p_madw ); /* @@ -125,11 +124,9 @@ typedef void (*osm_vend_mad_send_err_callback_t)( * The vendor layer does not call this function (or any other) * for MADs that were not expecting a response. * -* * SEE ALSO *********/ - /****f* OpenSM Vendor API/osm_vendor_new * NAME * osm_vendor_new @@ -237,8 +234,7 @@ ib_api_status_t osm_vendor_init( IN osm_vendor_t* const p_vend, IN osm_log_t * const p_log, - IN const uint32_t timeout - ); + IN const uint32_t timeout ); /* * PARAMETERS * p_vend @@ -252,16 +248,13 @@ osm_vendor_init( * [in] Transaction timeout value in milliseconds. * A value of 0 disables timeouts. * -* * RETURN VALUE * -* * NOTES * * SEE ALSO *********/ - /****f* OpenSM Vendor API/osm_vendor_bind * NAME * osm_vendor_bind @@ -321,7 +314,7 @@ osm_vendor_bind( */ void osm_vendor_unbind( - IN osm_bind_handle_t h_bind); + IN osm_bind_handle_t h_bind ); /* * PARAMETERS * h_bind @@ -335,7 +328,6 @@ osm_vendor_unbind( * SEE ALSO *********/ - /****f* OpenSM Vendor API/osm_vendor_get * NAME * osm_vendor_get @@ -381,8 +373,8 @@ osm_vendor_get( ib_api_status_t osm_vendor_send( IN osm_bind_handle_t h_bind, - IN osm_madw_t* const p_madw, - IN boolean_t const resp_expected); + IN osm_madw_t* const p_madw, + IN boolean_t const resp_expected); /* * PARAMETERS * h_bind @@ -397,7 +389,6 @@ osm_vendor_send( * RETURN VALUE * IB_SUCCESS on succesful completion. * -* * NOTES * 1. Only mads that expect a response are tracked for transaction competion. * 2. A mad that does not expect a response is being put back immediatly after @@ -406,7 +397,6 @@ osm_vendor_send( * SEE ALSO *********/ - /****f* OpenSM Vendor API/osm_vendor_put * NAME * osm_vendor_put @@ -526,3 +516,4 @@ osm_vendor_set_debug( END_C_DECLS #endif /* _OSM_VENDOR_API_H_ */ + diff --git a/trunk/ulp/opensm/user/include/vendor/osm_vendor_sa_api.h b/trunk/ulp/opensm/user/include/vendor/osm_vendor_sa_api.h index 4b26a189..734d83fb 100644 --- a/trunk/ulp/opensm/user/include/vendor/osm_vendor_sa_api.h +++ b/trunk/ulp/opensm/user/include/vendor/osm_vendor_sa_api.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -67,7 +67,7 @@ BEGIN_C_DECLS * * SYNOPSIS */ -typedef uint32_t osmv_flags_t; +typedef uint32_t osmv_flags_t; #define OSM_SA_FLAGS_SYNC 0x00000001 /* * VALUES @@ -113,6 +113,8 @@ typedef enum _osmv_query_type OSMV_QUERY_UD_MULTICAST_SET, OSMV_QUERY_UD_MULTICAST_DELETE, + OSMV_QUERY_MULTIPATH_REC, + } osmv_query_type_t; /* * VALUES @@ -137,15 +139,15 @@ typedef enum _osmv_query_type * the GUID of the node being requested. * * OSMV_QUERY_PORT_REC_BY_LID -* Query for port information based on the port's base LID. Queries +* Query for port information based on the port's base LID. Queries * of this type should reference an ib_net16_t value that indicates * the base LID of the port being requested. * * OSMV_QUERY_PORT_REC_BY_LID_AND_NUM -* Query for port information based on the port's LID and port num. -* Queries of this type should reference an osmv_user_query_t -* structure as input to the query. The port num and lid should -* be provided by it. +* Query for port information based on the port's LID and port num. +* Queries of this type should reference an osmv_user_query_t +* structure as input to the query. The port num and lid should +* be provided by it. * * OSMV_QUERY_PATH_REC_BY_PORT_GUIDS * Query for path records between the specified pair of port GUIDs. @@ -173,7 +175,6 @@ typedef enum _osmv_query_type * osmv_lid_pair_t osmv_guid_pair_t *****/ - /****s* OpenSM Vendor SA Client/osmv_user_query_t * NAME * osmv_user_query_t @@ -188,9 +189,9 @@ typedef struct _osmv_user_query uint8_t method; ib_net16_t attr_id; ib_net16_t attr_offset; + ib_net32_t attr_mod; ib_net64_t comp_mask; - void *p_attr; - + void *p_attr; } osmv_user_query_t; /* * FIELDS @@ -206,8 +207,12 @@ typedef struct _osmv_user_query * this value by passing in the sizeof( attribute ) into the * ib_get_attr_offset() routine. * +* attr_mod +* Attribute modifier for query request. +* * comp_mask -* Indicates the attribute components that are specified for the query. +* Indicates the attribute components that are specified for the +* query. * * p_attr * References the attribute structure used as input into the query. @@ -234,9 +239,8 @@ typedef struct _osmv_user_query */ typedef struct _osmv_gid_pair { - ib_gid_t src_gid; - ib_gid_t dest_gid; - + ib_gid_t src_gid; + ib_gid_t dest_gid; } osmv_gid_pair_t; /* * FIELDS @@ -253,7 +257,6 @@ typedef struct _osmv_gid_pair * ib_gid_t *****/ - /****s* OpenSM Vendor SA Client/osmv_lid_pair_t * NAME * osmv_lid_pair_t @@ -265,9 +268,8 @@ typedef struct _osmv_gid_pair */ typedef struct _osmv_lid_pair { - ib_net16_t src_lid; - ib_net16_t dest_lid; - + ib_net16_t src_lid; + ib_net16_t dest_lid; } osmv_lid_pair_t; /* * FIELDS @@ -281,7 +283,6 @@ typedef struct _osmv_lid_pair * This structure is used to describe the endpoints of a path. *****/ - /****s* OpenSM Vendor SA Client/osmv_guid_pair_t * NAME * osmv_guid_pair_t @@ -294,9 +295,8 @@ typedef struct _osmv_lid_pair */ typedef struct _osmv_guid_pair { - ib_net64_t src_guid; - ib_net64_t dest_guid; - + ib_net64_t src_guid; + ib_net64_t dest_guid; } osmv_guid_pair_t; /* * FIELDS @@ -314,6 +314,35 @@ typedef struct _osmv_guid_pair * ib_guid_t *****/ +/****s* OpenSM Vendor SA Client/osmv_multipath_req_t +* NAME +* osmv_multipath_req_t +* +* DESCRIPTION +* Fields from which to generate a MultiPathRecord request. +* +* SYNOPSIS +*/ +typedef struct _osmv_multipath_req_t +{ + ib_net64_t comp_mask; + uint16_t pkey; + boolean_t reversible; + uint8_t num_path; + uint8_t sl; + uint8_t independence; + uint8_t sgid_count; + uint8_t dgid_count; + ib_gid_t gids[IB_MULTIPATH_MAX_GIDS]; +} osmv_multipath_req_t; +/* +* FIELDS +* +* NOTES +* This structure is used to describe a multipath request. +* +* SEE ALSO +*****/ /****s* OpenSM Vendor SA Client/osmv_query_res_t * NAME @@ -326,12 +355,11 @@ typedef struct _osmv_guid_pair */ typedef struct _osmv_query_res { - const void *query_context; - ib_api_status_t status; + const void *query_context; + ib_api_status_t status; osmv_query_type_t query_type; - uint32_t result_cnt; + uint32_t result_cnt; osm_madw_t *p_result_madw; - } osmv_query_res_t; /* * FIELDS @@ -343,8 +371,8 @@ typedef struct _osmv_query_res * Indicates the success of the query operation. * * query_type -* Indicates the type of query for which the results are being returned. -* This matches the query_type specified through the +* Indicates the type of query for which the results are being +* returned. This matches the query_type specified through the * osm_vendor_query_sa call. * * result_cnt @@ -374,7 +402,6 @@ typedef struct _osmv_query_res * osmv_get_query_result *****/ - /****f* OpenSM Vendor SA Client/osmv_get_query_result * NAME * osmv_get_query_result @@ -387,8 +414,8 @@ typedef struct _osmv_query_res */ static inline void* osmv_get_query_result( - IN osm_madw_t *p_result_madw, - IN uint32_t result_index ) + IN osm_madw_t *p_result_madw, + IN uint32_t result_index ) { ib_sa_mad_t *p_sa_mad; @@ -420,7 +447,6 @@ osmv_get_query_result( * osmv_query_res_t, osm_madw_t *****/ - /****f* OpenSM Vendor SA Client/osmv_get_query_path_rec * NAME * osmv_get_query_path_rec @@ -433,8 +459,8 @@ osmv_get_query_result( */ static inline ib_path_rec_t* osmv_get_query_path_rec( - IN osm_madw_t *p_result_madw, - IN uint32_t result_index ) + IN osm_madw_t *p_result_madw, + IN uint32_t result_index ) { ib_sa_mad_t *p_sa_mad; @@ -461,7 +487,6 @@ osmv_get_query_path_rec( * osmv_query_res_t, osm_madw_t, osmv_get_query_result, ib_path_rec_t *****/ - /****f* OpenSM Vendor SA Client/osmv_get_query_portinfo_rec * NAME * osmv_get_query_portinfo_rec @@ -474,8 +499,8 @@ osmv_get_query_path_rec( */ static inline ib_portinfo_record_t* osmv_get_query_portinfo_rec( - IN osm_madw_t *p_result_madw, - IN uint32_t result_index ) + IN osm_madw_t *p_result_madw, + IN uint32_t result_index ) { ib_sa_mad_t *p_sa_mad; @@ -503,7 +528,6 @@ osmv_get_query_portinfo_rec( * osmv_query_res_t, osm_madw_t, osmv_get_query_result, ib_portinfo_record_t *****/ - /****f* OpenSM Vendor SA Client/osmv_get_query_node_rec * NAME * osmv_get_query_node_rec @@ -516,8 +540,8 @@ osmv_get_query_portinfo_rec( */ static inline ib_node_record_t* osmv_get_query_node_rec( - IN osm_madw_t *p_result_madw, - IN uint32_t result_index ) + IN osm_madw_t *p_result_madw, + IN uint32_t result_index ) { ib_sa_mad_t *p_sa_mad; @@ -545,7 +569,6 @@ osmv_get_query_node_rec( * osmv_query_res_t, osm_madw_t, osmv_get_query_result, ib_node_record_t *****/ - /****f* OpenSM Vendor SA Client/osmv_get_query_svc_rec * NAME * osmv_get_query_svc_rec @@ -558,8 +581,8 @@ osmv_get_query_node_rec( */ static inline ib_service_record_t* osmv_get_query_svc_rec( - IN osm_madw_t *p_result_madw, - IN uint32_t result_index ) + IN osm_madw_t *p_result_madw, + IN uint32_t result_index ) { ib_sa_mad_t *p_sa_mad; @@ -587,6 +610,87 @@ osmv_get_query_svc_rec( * osmv_query_res_t, osm_madw_t, osmv_get_query_result, ib_service_record_t *****/ +/****f* OpenSM Vendor SA Client/osmv_get_query_mc_rec +* NAME +* osmv_get_query_mc_rec +* +* DESCRIPTION +* Retrieves a multicast record result from a MAD returned by a call to +* osmv_query_sa(). +* +* SYNOPSIS +*/ +static inline ib_member_rec_t* +osmv_get_query_mc_rec( + IN osm_madw_t *p_result_madw, + IN uint32_t result_index ) +{ + ib_sa_mad_t *p_sa_mad; + + CL_ASSERT( p_result_madw ); + p_sa_mad = (ib_sa_mad_t*)osm_madw_get_mad_ptr( p_result_madw ); + CL_ASSERT( p_sa_mad && p_sa_mad->attr_id == IB_MAD_ATTR_MCMEMBER_RECORD ); + + return( (ib_member_rec_t*)osmv_get_query_result( p_result_madw, + result_index ) ); +} +/* +* PARAMETERS +* p_result_madw +* [in] This is a reference to the MAD returned as a result of the +* query. +* +* result_index +* [in] A zero-based index indicating which result to return. +* +* NOTES +* This call returns a pointer to the start of a service record result from +* a call to osmv_query_sa(). +* +* SEE ALSO +* osmv_query_res_t, osm_madw_t, osmv_get_query_result, ib_member_rec_t +*****/ + +/****f* OpenSM Vendor SA Client/osmv_get_query_inform_info_rec +* NAME +* osmv_get_query_inform_info_rec +* +* DESCRIPTION +* Retrieves an InformInfo record result from a MAD returned by +* a call to osmv_query_sa(). +* +* SYNOPSIS +*/ +static inline ib_inform_info_record_t* +osmv_get_query_inform_info_rec( + IN osm_madw_t *p_result_madw, + IN uint32_t result_index ) +{ + ib_sa_mad_t *p_sa_mad; + + CL_ASSERT( p_result_madw ); + p_sa_mad = (ib_sa_mad_t*)osm_madw_get_mad_ptr( p_result_madw ); + CL_ASSERT( p_sa_mad && p_sa_mad->attr_id == IB_MAD_ATTR_INFORM_INFO_RECORD ); + + return( (ib_inform_info_record_t*)osmv_get_query_result( p_result_madw, + result_index ) ); +} +/* +* PARAMETERS +* p_result_madw +* [in] This is a reference to the MAD returned as a result of the +* query. +* +* result_index +* [in] A zero-based index indicating which result to return. +* +* NOTES +* This call returns a pointer to the start of a service record result from +* a call to osmv_query_sa(). +* +* SEE ALSO +* osmv_query_res_t, osm_madw_t, osmv_get_query_result, ib_inform_info_record_t +*****/ /****f* OpenSM Vendor SA Client/osmv_pfn_query_cb_t * NAME @@ -600,7 +704,7 @@ osmv_get_query_svc_rec( */ typedef void (*osmv_pfn_query_cb_t)( - IN osmv_query_res_t *p_query_res ); + IN osmv_query_res_t *p_query_res ); /* * PARAMETERS * p_query_res @@ -620,7 +724,6 @@ typedef void * osmv_query_res_t *****/ - /****s* OpenSM Vendor SA Client/osmv_query_req_t * NAME * osmv_query_req_t @@ -634,21 +737,21 @@ typedef void typedef struct _osmv_query_req { osmv_query_type_t query_type; - const void *p_query_input; - ib_net64_t sm_key; - - uint32_t timeout_ms; - uint32_t retry_cnt; - osmv_flags_t flags; + const void *p_query_input; + ib_net64_t sm_key; - const void *query_context; - osmv_pfn_query_cb_t pfn_query_cb; + uint32_t timeout_ms; + uint32_t retry_cnt; + osmv_flags_t flags; + const void *query_context; + osmv_pfn_query_cb_t pfn_query_cb; } osmv_query_req_t; /* * FIELDS * query_type -* Indicates the type of query that the access layer should perform. +* Indicates the type of query that the access layer should +* perform. * * p_query_input * A pointer to the input for the query. The data referenced by @@ -677,7 +780,8 @@ typedef struct _osmv_query_req * query callback. * * pfn_query_cb -* A user-defined callback that is invoked upon completion of the query. +* A user-defined callback that is invoked upon completion of the +* query. * * NOTES * This structure is used when requesting an osm vendor provided query @@ -736,7 +840,6 @@ osmv_bind_sa( * osmv_query_sa *********/ - /****f* OpenSM Vendor SA Client/osmv_query_sa * NAME * osmv_query_sa @@ -773,3 +876,4 @@ osmv_query_sa( END_C_DECLS #endif /* _OSM_VENDOR_SA_API_H_ */ + diff --git a/trunk/ulp/opensm/user/include/vendor/osm_vendor_select.h b/trunk/ulp/opensm/user/include/vendor/osm_vendor_select.h index 9f534586..b766b67b 100644 --- a/trunk/ulp/opensm/user/include/vendor/osm_vendor_select.h +++ b/trunk/ulp/opensm/user/include/vendor/osm_vendor_select.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Include file that defines which vendor files to compile. @@ -72,3 +73,4 @@ #endif /* OPENIB */ #endif /* _OSM_VENDOR_SELECT_H_ */ + diff --git a/trunk/ulp/opensm/user/libopensm/SOURCES b/trunk/ulp/opensm/user/libopensm/SOURCES index 370e2bcb..7acd92f2 100644 --- a/trunk/ulp/opensm/user/libopensm/SOURCES +++ b/trunk/ulp/opensm/user/libopensm/SOURCES @@ -53,6 +53,7 @@ INCLUDES= \ USER_C_FLAGS=$(USER_C_FLAGS) /MD #Add preproccessor definitions C_DEFINES=$(C_DEFINES) -DWIN32 -D__WIN__ -D__i386__ -Dinline=__inline -DMT_LITTLE_ENDIAN -DOSM_VENDOR_INTF_AL +C_DEFINES=$(C_DEFINES) -I.. -DHAVE_CONFIG_H !if !$(FREEBUILD) #C_DEFINES=$(C_DEFINES) -D_DEBUG -DDEBUG -DDBG C_DEFINES=$(C_DEFINES) diff --git a/trunk/ulp/opensm/user/libopensm/osm_helper.c b/trunk/ulp/opensm/user/libopensm/osm_helper.c index 14718502..55c01c9f 100644 --- a/trunk/ulp/opensm/user/libopensm/osm_helper.c +++ b/trunk/ulp/opensm/user/libopensm/osm_helper.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Implementation of opensm helper functions. @@ -48,7 +49,7 @@ #include #include -#include +#include #include #include #include @@ -154,74 +155,74 @@ const char* const __ib_sm_method_str[] = const char* const __ib_sm_attr_str[] = { - "RESERVED", /* 0 */ + "RESERVED", /* 0 */ "ClassPortInfo", /* 1 */ "Notice", /* 2 */ "InformInfo", /* 3 */ - "RESERVED", /* 4 */ - "RESERVED", /* 5 */ - "RESERVED", /* 6 */ - "RESERVED", /* 7 */ - "RESERVED", /* 8 */ - "RESERVED", /* 9 */ - "RESERVED", /* A */ - "RESERVED", /* B */ - "RESERVED", /* C */ - "RESERVED", /* D */ - "RESERVED", /* E */ - "RESERVED", /* F */ + "RESERVED", /* 4 */ + "RESERVED", /* 5 */ + "RESERVED", /* 6 */ + "RESERVED", /* 7 */ + "RESERVED", /* 8 */ + "RESERVED", /* 9 */ + "RESERVED", /* A */ + "RESERVED", /* B */ + "RESERVED", /* C */ + "RESERVED", /* D */ + "RESERVED", /* E */ + "RESERVED", /* F */ "NodeDescription", /* 10 */ - "NodeInfo", /* 11 */ + "NodeInfo", /* 11 */ "SwitchInfo", /* 12 */ "UNKNOWN", /* 13 */ - "GUIDInfo", /* 14 */ - "PortInfo", /* 15 */ + "GUIDInfo", /* 14 */ + "PortInfo", /* 15 */ "P_KeyTable", /* 16 */ - "SLtoVLMappingTable", /* 17 */ - "VLArbitrationTable", /* 18 */ - "LinearForwardingTable", /* 19 */ - "RandomForwardingTable", /* 1A */ - "MulticastForwardingTable", /* 1B */ + "SLtoVLMappingTable", /* 17 */ + "VLArbitrationTable", /* 18 */ + "LinearForwardingTable", /* 19 */ + "RandomForwardingTable", /* 1A */ + "MulticastForwardingTable", /* 1B */ "UNKNOWN", /* 1C */ "UNKNOWN", /* 1D */ "UNKNOWN", /* 1E */ "UNKNOWN", /* 1F */ "SMInfo", /* 20 */ - "UNKNOWN" /* 21 - always highest value*/ + "UNKNOWN" /* 21 - always highest value */ }; #define OSM_SM_ATTR_STR_UNKNOWN_VAL 0x21 const char* const __ib_sa_attr_str[] = { - "RESERVED", /* 0 */ + "RESERVED", /* 0 */ "ClassPortInfo", /* 1 */ "Notice", /* 2 */ "InformInfo", /* 3 */ - "RESERVED", /* 4 */ - "RESERVED", /* 5 */ - "RESERVED", /* 6 */ - "RESERVED", /* 7 */ - "RESERVED", /* 8 */ - "RESERVED", /* 9 */ - "RESERVED", /* A */ - "RESERVED", /* B */ - "RESERVED", /* C */ - "RESERVED", /* D */ - "RESERVED", /* E */ - "RESERVED", /* F */ - "RESERVED", /* 10 */ + "RESERVED", /* 4 */ + "RESERVED", /* 5 */ + "RESERVED", /* 6 */ + "RESERVED", /* 7 */ + "RESERVED", /* 8 */ + "RESERVED", /* 9 */ + "RESERVED", /* A */ + "RESERVED", /* B */ + "RESERVED", /* C */ + "RESERVED", /* D */ + "RESERVED", /* E */ + "RESERVED", /* F */ + "RESERVED", /* 10 */ "NodeRecord", /* 11 */ - "PortInfoRecord", /* 12 */ - "SLtoVLMappingTableRecord", /* 13 */ - "SwitchInfoRecord", /* 14 */ - "LinearForwardingTableRecord", /* 15 */ - "RandomForwardingTableRecord", /* 16 */ + "PortInfoRecord", /* 12 */ + "SLtoVLMappingTableRecord", /* 13 */ + "SwitchInfoRecord", /* 14 */ + "LinearForwardingTableRecord", /* 15 */ + "RandomForwardingTableRecord", /* 16 */ "MulticastForwardingTableRecord", /* 17 */ - "SMInfoRecord", /* 18 */ - "RESERVED", /* 19 */ - "RandomForwardingTable", /* 1A */ - "MulticastForwardingTable", /* 1B */ + "SMInfoRecord", /* 18 */ + "RESERVED", /* 19 */ + "RandomForwardingTable", /* 1A */ + "MulticastForwardingTable", /* 1B */ "UNKNOWN", /* 1C */ "UNKNOWN", /* 1D */ "UNKNOWN", /* 1E */ @@ -242,22 +243,206 @@ const char* const __ib_sa_attr_str[] = "UNKNOWN", /* 2D */ "UNKNOWN", /* 2E */ "UNKNOWN", /* 2F */ - "GuidInfoRecord", /* 30 */ + "GuidInfoRecord", /* 30 */ "ServiceRecord", /* 31 */ "UNKNOWN", /* 32 */ - "P_KeyTableRecord", /* 33 */ + "P_KeyTableRecord", /* 33 */ "UNKNOWN", /* 34 */ "PathRecord", /* 35 */ - "VLArbitrationTableRecord", /* 36 */ + "VLArbitrationTableRecord", /* 36 */ "UNKNOWN", /* 37 */ - "MCMemberRecord", /* 38 */ - "TraceRecord", /* 39 */ - "MultiPathRecord", /* 3A */ - "ServiceAssociationRecord", /* 3B */ - "UNKNOWN" /* 3C - always highest value*/ + "MCMemberRecord", /* 38 */ + "TraceRecord", /* 39 */ + "MultiPathRecord", /* 3A */ + "ServiceAssociationRecord", /* 3B */ + "UNKNOWN", /* 3C */ + "UNKNOWN", /* 3D */ + "UNKNOWN", /* 3E */ + "UNKNOWN", /* 3F */ + "UNKNOWN", /* 40 */ + "UNKNOWN", /* 41 */ + "UNKNOWN", /* 42 */ + "UNKNOWN", /* 43 */ + "UNKNOWN", /* 44 */ + "UNKNOWN", /* 45 */ + "UNKNOWN", /* 46 */ + "UNKNOWN", /* 47 */ + "UNKNOWN", /* 48 */ + "UNKNOWN", /* 49 */ + "UNKNOWN", /* 4A */ + "UNKNOWN", /* 4B */ + "UNKNOWN", /* 4C */ + "UNKNOWN", /* 4D */ + "UNKNOWN", /* 4E */ + "UNKNOWN", /* 4F */ + "UNKNOWN", /* 50 */ + "UNKNOWN", /* 51 */ + "UNKNOWN", /* 52 */ + "UNKNOWN", /* 53 */ + "UNKNOWN", /* 54 */ + "UNKNOWN", /* 55 */ + "UNKNOWN", /* 56 */ + "UNKNOWN", /* 57 */ + "UNKNOWN", /* 58 */ + "UNKNOWN", /* 59 */ + "UNKNOWN", /* 5A */ + "UNKNOWN", /* 5B */ + "UNKNOWN", /* 5C */ + "UNKNOWN", /* 5D */ + "UNKNOWN", /* 5E */ + "UNKNOWN", /* 5F */ + "UNKNOWN", /* 60 */ + "UNKNOWN", /* 61 */ + "UNKNOWN", /* 62 */ + "UNKNOWN", /* 63 */ + "UNKNOWN", /* 64 */ + "UNKNOWN", /* 65 */ + "UNKNOWN", /* 66 */ + "UNKNOWN", /* 67 */ + "UNKNOWN", /* 68 */ + "UNKNOWN", /* 69 */ + "UNKNOWN", /* 6A */ + "UNKNOWN", /* 6B */ + "UNKNOWN", /* 6C */ + "UNKNOWN", /* 6D */ + "UNKNOWN", /* 6E */ + "UNKNOWN", /* 6F */ + "UNKNOWN", /* 70 */ + "UNKNOWN", /* 71 */ + "UNKNOWN", /* 72 */ + "UNKNOWN", /* 73 */ + "UNKNOWN", /* 74 */ + "UNKNOWN", /* 75 */ + "UNKNOWN", /* 76 */ + "UNKNOWN", /* 77 */ + "UNKNOWN", /* 78 */ + "UNKNOWN", /* 79 */ + "UNKNOWN", /* 7A */ + "UNKNOWN", /* 7B */ + "UNKNOWN", /* 7C */ + "UNKNOWN", /* 7D */ + "UNKNOWN", /* 7E */ + "UNKNOWN", /* 7F */ + "UNKNOWN", /* 80 */ + "UNKNOWN", /* 81 */ + "UNKNOWN", /* 82 */ + "UNKNOWN", /* 83 */ + "UNKNOWN", /* 84 */ + "UNKNOWN", /* 85 */ + "UNKNOWN", /* 86 */ + "UNKNOWN", /* 87 */ + "UNKNOWN", /* 88 */ + "UNKNOWN", /* 89 */ + "UNKNOWN", /* 8A */ + "UNKNOWN", /* 8B */ + "UNKNOWN", /* 8C */ + "UNKNOWN", /* 8D */ + "UNKNOWN", /* 8E */ + "UNKNOWN", /* 8F */ + "UNKNOWN", /* 90 */ + "UNKNOWN", /* 91 */ + "UNKNOWN", /* 92 */ + "UNKNOWN", /* 93 */ + "UNKNOWN", /* 94 */ + "UNKNOWN", /* 95 */ + "UNKNOWN", /* 96 */ + "UNKNOWN", /* 97 */ + "UNKNOWN", /* 98 */ + "UNKNOWN", /* 99 */ + "UNKNOWN", /* 9A */ + "UNKNOWN", /* 9B */ + "UNKNOWN", /* 9C */ + "UNKNOWN", /* 9D */ + "UNKNOWN", /* 9E */ + "UNKNOWN", /* 9F */ + "UNKNOWN", /* A0 */ + "UNKNOWN", /* A1 */ + "UNKNOWN", /* A2 */ + "UNKNOWN", /* A3 */ + "UNKNOWN", /* A4 */ + "UNKNOWN", /* A5 */ + "UNKNOWN", /* A6 */ + "UNKNOWN", /* A7 */ + "UNKNOWN", /* A8 */ + "UNKNOWN", /* A9 */ + "UNKNOWN", /* AA */ + "UNKNOWN", /* AB */ + "UNKNOWN", /* AC */ + "UNKNOWN", /* AD */ + "UNKNOWN", /* AE */ + "UNKNOWN", /* AF */ + "UNKNOWN", /* B0 */ + "UNKNOWN", /* B1 */ + "UNKNOWN", /* B2 */ + "UNKNOWN", /* B3 */ + "UNKNOWN", /* B4 */ + "UNKNOWN", /* B5 */ + "UNKNOWN", /* B6 */ + "UNKNOWN", /* B7 */ + "UNKNOWN", /* B8 */ + "UNKNOWN", /* B9 */ + "UNKNOWN", /* BA */ + "UNKNOWN", /* BB */ + "UNKNOWN", /* BC */ + "UNKNOWN", /* BD */ + "UNKNOWN", /* BE */ + "UNKNOWN", /* BF */ + "UNKNOWN", /* C0 */ + "UNKNOWN", /* C1 */ + "UNKNOWN", /* C2 */ + "UNKNOWN", /* C3 */ + "UNKNOWN", /* C4 */ + "UNKNOWN", /* C5 */ + "UNKNOWN", /* C6 */ + "UNKNOWN", /* C7 */ + "UNKNOWN", /* C8 */ + "UNKNOWN", /* C9 */ + "UNKNOWN", /* CA */ + "UNKNOWN", /* CB */ + "UNKNOWN", /* CC */ + "UNKNOWN", /* CD */ + "UNKNOWN", /* CE */ + "UNKNOWN", /* CF */ + "UNKNOWN", /* D0 */ + "UNKNOWN", /* D1 */ + "UNKNOWN", /* D2 */ + "UNKNOWN", /* D3 */ + "UNKNOWN", /* D4 */ + "UNKNOWN", /* D5 */ + "UNKNOWN", /* D6 */ + "UNKNOWN", /* D7 */ + "UNKNOWN", /* D8 */ + "UNKNOWN", /* D9 */ + "UNKNOWN", /* DA */ + "UNKNOWN", /* DB */ + "UNKNOWN", /* DC */ + "UNKNOWN", /* DD */ + "UNKNOWN", /* DE */ + "UNKNOWN", /* DF */ + "UNKNOWN", /* E0 */ + "UNKNOWN", /* E1 */ + "UNKNOWN", /* E2 */ + "UNKNOWN", /* E3 */ + "UNKNOWN", /* E4 */ + "UNKNOWN", /* E5 */ + "UNKNOWN", /* E6 */ + "UNKNOWN", /* E7 */ + "UNKNOWN", /* E8 */ + "UNKNOWN", /* E9 */ + "UNKNOWN", /* EA */ + "UNKNOWN", /* EB */ + "UNKNOWN", /* EC */ + "UNKNOWN", /* ED */ + "UNKNOWN", /* EE */ + "UNKNOWN", /* EF */ + "UNKNOWN", /* F0 */ + "UNKNOWN", /* F1 */ + "UNKNOWN", /* F2 */ + "InformInfoRecord", /* F3 */ + "UNKNOWN" /* F4 - always highest value */ }; -#define OSM_SA_ATTR_STR_UNKNOWN_VAL 0x3C +#define OSM_SA_ATTR_STR_UNKNOWN_VAL 0xF4 /********************************************************************** @@ -360,7 +545,7 @@ osm_dbg_get_capabilities_str( uint32_t total_len = 0; char *p_local = p_buf; - strcpy( p_local, "Capabilities Mask:\n" ); + strcpy( p_local, "Capability Mask:\n" ); p_local += strlen( p_local ); if( p_pi->capability_mask & IB_PORT_CAP_RESV0 ) @@ -654,8 +839,7 @@ osm_dump_port_info( /* show the capabilities mask */ osm_dbg_get_capabilities_str( buf, BUF_SIZE, "\t\t\t\t", p_pi ); - osm_log( p_log, log_level, - "%s", buf ); + osm_log( p_log, log_level, "%s", buf ); } } @@ -678,7 +862,7 @@ osm_dump_portinfo_record( "\t\t\t\tEndPortLid..............0x%X\n" "\t\t\t\tPortNum.................0x%X\n" "\t\t\t\tReserved................0x%X\n" - "\t\t\t\tPortInfo dump\n" + "\t\t\t\tPortInfo dump:\n" "\t\t\t\tm_key...................0x%016" PRIx64 "\n" "\t\t\t\tsubnet_prefix...........0x%016" PRIx64 "\n" "\t\t\t\tbase_lid................0x%X\n" @@ -752,8 +936,7 @@ osm_dump_portinfo_record( /* show the capabilities mask */ osm_dbg_get_capabilities_str( buf, BUF_SIZE, "\t\t\t\t", p_pi ); - osm_log( p_log, log_level, - "%s", buf ); + osm_log( p_log, log_level, "%s", buf ); } } @@ -775,7 +958,7 @@ osm_dump_guidinfo_record( "\t\t\t\tLid.....................0x%X\n" "\t\t\t\tBlockNum................0x%X\n" "\t\t\t\tReserved................0x%X\n" - "\t\t\t\tGUIDInfo dump\n" + "\t\t\t\tGUIDInfo dump:\n" "\t\t\t\tReserved................0x%X\n" "\t\t\t\tGUID 0..................0x%016" PRIx64 "\n" "\t\t\t\tGUID 1..................0x%016" PRIx64 "\n" @@ -854,12 +1037,17 @@ osm_dump_node_record( if( osm_log_is_active( p_log, log_level ) ) { + char desc[sizeof(p_nr->node_desc.description) + 1]; + + memcpy(desc, p_nr->node_desc.description, + sizeof(p_nr->node_desc.description)); + desc[sizeof(desc) - 1] = '\0'; osm_log( p_log, log_level, - "NodeRecord dump:\n" + "Node Record dump:\n" "\t\t\t\tRID\n" "\t\t\t\tLid.....................0x%X\n" "\t\t\t\tReserved................0x%X\n" - "\t\t\t\tNodeInfoDump\n" + "\t\t\t\tNodeInfo dump:\n" "\t\t\t\tbase_version............0x%X\n" "\t\t\t\tclass_version...........0x%X\n" "\t\t\t\tnode_type...............%s\n" @@ -889,9 +1077,8 @@ osm_dump_node_record( cl_ntoh32( p_ni->revision ), ib_node_info_get_local_port_num( p_ni ), cl_ntoh32( ib_node_info_get_vendor_id( p_ni )), - p_nr->node_desc.description + desc ); - } } @@ -948,6 +1135,79 @@ osm_dump_path_record( } } +/********************************************************************** + **********************************************************************/ +void +osm_dump_multipath_record( + IN osm_log_t* const p_log, + IN const ib_multipath_rec_t* const p_mpr, + IN const osm_log_level_t log_level ) +{ + int i; + char buf_line[1024]; + ib_gid_t const *p_gid; + + if( osm_log_is_active( p_log, log_level ) ) + { + memset(buf_line, 0, sizeof(buf_line)); + p_gid = p_mpr->gids; + if ( p_mpr->sgid_count ) + { + for (i = 0; i < p_mpr->sgid_count; i++) + { + sprintf( buf_line, "%s\t\t\t\tsgid%02d.................." + "0x%016" PRIx64 " : 0x%016" PRIx64 "\n", + buf_line, i + 1, cl_ntoh64( p_gid->unicast.prefix ), + cl_ntoh64( p_gid->unicast.interface_id ) ); + p_gid++; + } + } + if ( p_mpr->dgid_count ) + { + for (i = 0; i < p_mpr->dgid_count; i++) + { + sprintf( buf_line, "%s\t\t\t\tdgid%02d.................." + "0x%016" PRIx64 " : 0x%016" PRIx64 "\n", + buf_line, i + 1, cl_ntoh64( p_gid->unicast.prefix ), + cl_ntoh64( p_gid->unicast.interface_id ) ); + p_gid++; + } + } + osm_log( p_log, log_level, + "MultiPath Record dump:\n" + "\t\t\t\thop_flow_raw............0x%X\n" + "\t\t\t\ttclass..................0x%X\n" + "\t\t\t\tnum_path_revers.........0x%X\n" + "\t\t\t\tpkey....................0x%X\n" + "\t\t\t\tresv0...................0x%X\n" + "\t\t\t\tsl......................0x%X\n" + "\t\t\t\tmtu.....................0x%X\n" + "\t\t\t\trate....................0x%X\n" + "\t\t\t\tpkt_life................0x%X\n" + "\t\t\t\tresv1...................0x%X\n" + "\t\t\t\tindependence............0x%X\n" + "\t\t\t\tsgid_count..............0x%X\n" + "\t\t\t\tdgid_count..............0x%X\n" + "%s\n" + "", + cl_ntoh32( p_mpr->hop_flow_raw ), + p_mpr->tclass, + p_mpr->num_path, + cl_ntoh16( p_mpr->pkey ), + p_mpr->resv0, + cl_ntoh16( p_mpr->sl ), + p_mpr->mtu, + p_mpr->rate, + p_mpr->pkt_life, + p_mpr->resv1, + p_mpr->independence, + p_mpr->sgid_count, + p_mpr->dgid_count, + buf_line + ); + } +} + /********************************************************************** **********************************************************************/ void @@ -966,12 +1226,12 @@ osm_dump_mc_record( "\t\t\t\tPortGid.................0x%016" PRIx64 " : " "0x%016" PRIx64 "\n" "\t\t\t\tqkey....................0x%X\n" - "\t\t\t\tMlid....................0x%X\n" - "\t\t\t\tMtu.....................0x%X\n" + "\t\t\t\tmlid....................0x%X\n" + "\t\t\t\tmtu.....................0x%X\n" "\t\t\t\tTClass..................0x%X\n" "\t\t\t\tpkey....................0x%X\n" - "\t\t\t\tRate....................0x%X\n" - "\t\t\t\tPacketLife..............0x%X\n" + "\t\t\t\trate....................0x%X\n" + "\t\t\t\tpkt_life................0x%X\n" "\t\t\t\tSLFlowLabelHopLimit.....0x%X\n" "\t\t\t\tScopeState..............0x%X\n" "\t\t\t\tProxyJoin...............0x%X\n" @@ -1002,7 +1262,7 @@ osm_dump_service_record( IN const ib_service_record_t* const p_sr, IN const osm_log_level_t log_level ) { - char buf_service_key[33]; + char buf_service_key[35]; char buf_service_name[65]; if( osm_log_is_active( p_log, log_level ) ) @@ -1029,7 +1289,7 @@ osm_dump_service_record( buf_service_name[64] = '\0'; osm_log( p_log, log_level, - "ServiceRecord dump:\n" + "Service Record dump:\n" "\t\t\t\tServiceID...............0x%016" PRIx64 "\n" "\t\t\t\tServiceGID..............0x%016" PRIx64 " : " "0x%016" PRIx64 "\n" @@ -1112,16 +1372,17 @@ osm_dump_inform_info( uint32_t qpn; uint8_t resp_time_val; - ib_inform_info_get_qpn_resp_time(p_ii->g_or_v.generic.qpn_resp_time_val, - &qpn, &resp_time_val); - if( osm_log_is_active( p_log, log_level ) ) { - if (p_ii->is_generic) + + ib_inform_info_get_qpn_resp_time(p_ii->g_or_v.generic.qpn_resp_time_val, + &qpn, &resp_time_val); + + if (p_ii->is_generic) { osm_log( p_log, log_level, "InformInfo dump:\n" - "\t\t\t\tgid.....................0x%016" PRIx64 ",%016" PRIx64 "\n" + "\t\t\t\tgid.....................0x%016" PRIx64 " : 0x%016" PRIx64 "\n" "\t\t\t\tlid_range_begin.........0x%X\n" "\t\t\t\tlid_range_end...........0x%X\n" "\t\t\t\tis_generic..............0x%X\n" @@ -1149,7 +1410,7 @@ osm_dump_inform_info( { osm_log( p_log, log_level, "InformInfo dump:\n" - "\t\t\t\tgid.....................0x%016" PRIx64 ",%016" PRIx64 "\n" + "\t\t\t\tgid.....................0x%016" PRIx64 " : 0x%016" PRIx64 "\n" "\t\t\t\tlid_range_begin.........0x%X\n" "\t\t\t\tlid_range_end...........0x%X\n" "\t\t\t\tis_generic..............0x%X\n" @@ -1176,6 +1437,101 @@ osm_dump_inform_info( } } +/********************************************************************** + **********************************************************************/ +void +osm_dump_inform_info_record( + IN osm_log_t* const p_log, + IN const ib_inform_info_record_t* const p_iir, + IN const osm_log_level_t log_level ) +{ + uint32_t qpn; + uint8_t resp_time_val; + + ib_inform_info_get_qpn_resp_time(p_iir->inform_info.g_or_v.generic.qpn_resp_time_val, + &qpn, &resp_time_val); + + if( osm_log_is_active( p_log, log_level ) ) + { + + ib_inform_info_get_qpn_resp_time(p_iir->inform_info.g_or_v.generic.qpn_resp_time_val, + &qpn, &resp_time_val); + + if (p_iir->inform_info.is_generic) + { + osm_log( p_log, log_level, + "InformInfo Record dump:\n" + "\t\t\t\tRID\n" + "\t\t\t\tSubscriberGID...........0x%016" PRIx64 " : " + "0x%016" PRIx64 "\n" + "\t\t\t\tSubscriberEnum..........0x%X\n" + "\t\t\t\tInformInfo dump:\n" + "\t\t\t\tgid.....................0x%016" PRIx64 " : 0x%016" PRIx64 "\n" + "\t\t\t\tlid_range_begin.........0x%X\n" + "\t\t\t\tlid_range_end...........0x%X\n" + "\t\t\t\tis_generic..............0x%X\n" + "\t\t\t\tsubscribe...............0x%X\n" + "\t\t\t\ttrap_type...............0x%X\n" + "\t\t\t\ttrap_num................%u\n" + "\t\t\t\tqpn.....................0x%06X\n" + "\t\t\t\tresp_time_val...........0x%X\n" + "\t\t\t\tnode_type...............0x%06X\n" + "", + cl_ntoh64( p_iir->subscriber_gid.unicast.prefix ), + cl_ntoh64( p_iir->subscriber_gid.unicast.interface_id ), + cl_ntoh16( p_iir->subscriber_enum ), + cl_ntoh64( p_iir->inform_info.gid.unicast.prefix ), + cl_ntoh64( p_iir->inform_info.gid.unicast.interface_id ), + cl_ntoh16( p_iir->inform_info.lid_range_begin ), + cl_ntoh16( p_iir->inform_info.lid_range_end ), + p_iir->inform_info.is_generic, + p_iir->inform_info.subscribe, + cl_ntoh16( p_iir->inform_info.trap_type ), + cl_ntoh16( p_iir->inform_info.g_or_v.generic.trap_num ), + cl_ntoh32(qpn), + resp_time_val, + cl_ntoh32(ib_inform_info_get_node_type( &p_iir->inform_info )) + ); + } + else + { + osm_log( p_log, log_level, + "InformInfo Record dump:\n" + "\t\t\t\tRID\n" + "\t\t\t\tSubscriberGID...........0x%016" PRIx64 " : " + "0x%016" PRIx64 "\n" + "\t\t\t\tSubscriberEnum..........0x%X\n" + "\t\t\t\tInformInfo dump:\n" + "\t\t\t\tgid.....................0x%016" PRIx64 " : 0x%016" PRIx64 "\n" + "\t\t\t\tlid_range_begin.........0x%X\n" + "\t\t\t\tlid_range_end...........0x%X\n" + "\t\t\t\tis_generic..............0x%X\n" + "\t\t\t\tsubscribe...............0x%X\n" + "\t\t\t\ttrap_type...............0x%X\n" + "\t\t\t\tdev_id..................0x%X\n" + "\t\t\t\tqpn.....................0x%06X\n" + "\t\t\t\tresp_time_val...........0x%X\n" + "\t\t\t\tvendor_id...............0x%06X\n" + "", + cl_ntoh64( p_iir->subscriber_gid.unicast.prefix ), + cl_ntoh64( p_iir->subscriber_gid.unicast.interface_id ), + cl_ntoh16( p_iir->subscriber_enum ), + cl_ntoh64( p_iir->inform_info.gid.unicast.prefix ), + cl_ntoh64( p_iir->inform_info.gid.unicast.interface_id ), + cl_ntoh16( p_iir->inform_info.lid_range_begin ), + cl_ntoh16( p_iir->inform_info.lid_range_end ), + p_iir->inform_info.is_generic, + p_iir->inform_info.subscribe, + cl_ntoh16( p_iir->inform_info.trap_type ), + cl_ntoh16( p_iir->inform_info.g_or_v.vend.dev_id ), + cl_ntoh32(qpn), + resp_time_val, + cl_ntoh32(ib_inform_info_get_node_type( &p_iir->inform_info )) + ); + } + } +} + /********************************************************************** **********************************************************************/ void @@ -1187,7 +1543,7 @@ osm_dump_link_record( if( osm_log_is_active( p_log, log_level ) ) { osm_log( p_log, log_level, - "LinkRecord dump:\n" + "Link Record dump:\n" "\t\t\t\tfrom_lid................0x%X\n" "\t\t\t\tfrom_port_num...........0x%X\n" "\t\t\t\tto_port_num.............0x%X\n" @@ -1240,6 +1596,50 @@ osm_dump_switch_info( } } + +/********************************************************************** + **********************************************************************/ +void +osm_dump_switch_info_record( + IN osm_log_t* const p_log, + IN const ib_switch_info_record_t* const p_sir, + IN const osm_log_level_t log_level ) +{ + if( osm_log_is_active( p_log, log_level ) ) + { + osm_log( p_log, log_level, + "SwitchInfo Record dump:\n" + "\t\t\t\tRID\n" + "\t\t\t\tlid.....................0x%X\n" + "\t\t\t\tSwitchInfo dump:\n" + "\t\t\t\tlin_cap.................0x%X\n" + "\t\t\t\trand_cap................0x%X\n" + "\t\t\t\tmcast_cap...............0x%X\n" + "\t\t\t\tlin_top.................0x%X\n" + "\t\t\t\tdef_port................0x%X\n" + "\t\t\t\tdef_mcast_pri_port......0x%X\n" + "\t\t\t\tdef_mcast_not_port......0x%X\n" + "\t\t\t\tlife_state..............0x%X\n" + "\t\t\t\tlids_per_port...........0x%X\n" + "\t\t\t\tpartition_enf_cap.......0x%X\n" + "\t\t\t\tflags...................0x%X\n" + "", + cl_ntoh16( p_sir->lid ), + cl_ntoh16( p_sir->switch_info.lin_cap ), + cl_ntoh16( p_sir->switch_info.rand_cap ), + cl_ntoh16( p_sir->switch_info.mcast_cap ), + cl_ntoh16( p_sir->switch_info.lin_top ), + p_sir->switch_info.def_port, + p_sir->switch_info.def_mcast_pri_port, + p_sir->switch_info.def_mcast_not_port, + p_sir->switch_info.life_state, + cl_ntoh16( p_sir->switch_info.lids_per_port ), + cl_ntoh16( p_sir->switch_info.enforce_cap ), + p_sir->switch_info.flags + ); + } +} + /********************************************************************** **********************************************************************/ void @@ -1257,7 +1657,7 @@ osm_dump_pkey_block( if( osm_log_is_active( p_log, log_level ) ) { buf_line[0] = '\0'; - for (i = 0; i<32; i++) + for (i = 0; i < 32; i++) sprintf( buf_line,"%s 0x%04x |", buf_line, cl_ntoh16(p_pkey_tbl->pkey_entry[i])); @@ -1293,9 +1693,11 @@ osm_dump_slvl_map_table( { buf_line1[0] = '\0'; buf_line2[0] = '\0'; - for (i = 0; i<16; i++) sprintf( buf_line1,"%s %-2u |", buf_line1, i); - for (i = 0; i<16; i++) sprintf( buf_line2,"%s0x%01X |", - buf_line2, ib_slvl_table_get(p_slvl_tbl, i)); + for (i = 0; i < 16; i++) + sprintf( buf_line1,"%s %-2u |", buf_line1, i); + for (i = 0; i < 16; i++) + sprintf( buf_line2,"%s0x%01X |", + buf_line2, ib_slvl_table_get(p_slvl_tbl, i)); osm_log( p_log, log_level, "SLtoVL dump:\n" "\t\t\tport_guid............0x%016" PRIx64 "\n" @@ -1328,10 +1730,12 @@ osm_dump_vl_arb_table( { buf_line1[0] = '\0'; buf_line2[0] = '\0'; - for (i = 0; i<32; i++) sprintf( buf_line1,"%s 0x%01X |", - buf_line1, p_vla_tbl->vl_entry[i].vl); - for (i = 0; i<32; i++) sprintf( buf_line2,"%s 0x%01X |", - buf_line2, p_vla_tbl->vl_entry[i].weight); + for (i = 0; i < 32; i++) + sprintf( buf_line1,"%s 0x%01X |", + buf_line1, p_vla_tbl->vl_entry[i].vl); + for (i = 0; i < 32; i++) + sprintf( buf_line2,"%s 0x%01X |", + buf_line2, p_vla_tbl->vl_entry[i].weight); osm_log( p_log, log_level, "VlArb dump:\n" "\t\t\tport_guid...........0x%016" PRIx64 "\n" @@ -1372,6 +1776,39 @@ osm_dump_sm_info( } } +/********************************************************************** + **********************************************************************/ +void +osm_dump_sm_info_record( + IN osm_log_t* const p_log, + IN const ib_sminfo_record_t* const p_smir, + IN const osm_log_level_t log_level ) +{ + if( osm_log_is_active( p_log, log_level ) ) + { + osm_log( p_log, OSM_LOG_DEBUG, + "SMInfo Record dump:\n" + "\t\t\t\tRID\n" + "\t\t\t\tLid.....................0x%X\n" + "\t\t\t\tReserved................0x%X\n" + "\t\t\t\tSMInfo dump:\n" + "\t\t\t\tguid....................0x%016" PRIx64 "\n" + "\t\t\t\tsm_key..................0x%016" PRIx64 "\n" + "\t\t\t\tact_count...............%u\n" + "\t\t\t\tpriority................%u\n" + "\t\t\t\tsm_state................%u\n" + "", + cl_ntoh16( p_smir->lid ), + cl_ntoh16( p_smir->resv0 ), + cl_ntoh64( p_smir->sm_info.guid ), + cl_ntoh64( p_smir->sm_info.sm_key ), + cl_ntoh32( p_smir->sm_info.act_count ), + ib_sminfo_get_priority( &p_smir->sm_info ), + ib_sminfo_get_state( &p_smir->sm_info ) + ); + } +} + /********************************************************************** **********************************************************************/ void @@ -1839,6 +2276,11 @@ static const char* const __osm_disp_msg_str[] = "OSM_MSG_MAD_PKEY", "OSM_MSG_MAD_VL_ARB", "OSM_MSG_MAD_SLVL", + "OSM_MSG_MAD_GUIDINFO_RECORD", + "OSM_MSG_MAD_INFORM_INFO_RECORD", +#if defined (VENDOR_RMPP_SUPPORT) && defined (DUAL_SIDED_RMPP) + "OSM_MSG_MAD_MULTIPATH_RECORD", +#endif "UNKNOWN!!" }; @@ -1893,21 +2335,6 @@ osm_get_node_type_str_fixed_width( return( __osm_node_type_str_fixed_width[node_type] ); } -#define OSM_VENDOR_ID_INTEL 0x00D0B7 -#define OSM_VENDOR_ID_MELLANOX 0x0002C9 -#define OSM_VENDOR_ID_REDSWITCH 0x000617 -#define OSM_VENDOR_ID_SILVERSTORM 0x00066A -#define OSM_VENDOR_ID_TOPSPIN 0x0005AD -#define OSM_VENDOR_ID_FUJITSU 0x00E000 -#define OSM_VENDOR_ID_FUJITSU2 0x000B5D -#define OSM_VENDOR_ID_VOLTAIRE 0x0008F1 -#define OSM_VENDOR_ID_YOTTAYOTTA 0x000453 /* Also, Obsidian Research */ -#define OSM_VENDOR_ID_PATHSCALE 0x001175 -#define OSM_VENDOR_ID_IBM 0x000255 -#define OSM_VENDOR_ID_DIVERGENET 0x00084E -#define OSM_VENDOR_ID_FLEXTRONICS 0x000B8C -#define OSM_VENDOR_ID_AGILENT 0x0030D3 - /********************************************************************** **********************************************************************/ const char* @@ -1917,7 +2344,7 @@ osm_get_manufacturer_str( static const char* intel_str = "Intel "; static const char* mellanox_str = "Mellanox "; static const char* redswitch_str = "Redswitch "; - static const char* silverstorm_str = "SilverStorm "; + static const char* silverstorm_str = "SilverStorm"; static const char* topspin_str = "Topspin "; static const char* fujitsu_str = "Fujitsu "; static const char* voltaire_str = "Voltaire "; @@ -1925,8 +2352,15 @@ osm_get_manufacturer_str( static const char* pathscale_str = "PathScale "; static const char* ibm_str = "IBM "; static const char* divergenet_str = "DivergeNet "; - static const char* flextronics_str = "Flextronics "; + static const char* flextronics_str = "Flextronics"; static const char* agilent_str = "Agilent "; + static const char* obsidian_str = "Obsidian "; + static const char* baymicro_str = "BayMicro "; + static const char* lsilogic_str = "LSILogic "; + static const char* ddn_str = "DataDirect "; + static const char* panta_str = "Panta "; + static const char* hp_str = "HP "; + static const char* rioworks_str = "Rioworks "; static const char* unknown_str = "Unknown "; switch( (uint32_t)(guid_ho >> (5 * 8)) ) @@ -1958,6 +2392,20 @@ osm_get_manufacturer_str( return( flextronics_str ); case OSM_VENDOR_ID_AGILENT: return( agilent_str ); + case OSM_VENDOR_ID_OBSIDIAN: + return( obsidian_str ); + case OSM_VENDOR_ID_BAYMICRO: + return( baymicro_str ); + case OSM_VENDOR_ID_LSILOGIC: + return( lsilogic_str ); + case OSM_VENDOR_ID_DDN: + return( ddn_str ); + case OSM_VENDOR_ID_PANTA: + return( panta_str ); + case OSM_VENDOR_ID_HP: + return( hp_str ); + case OSM_VENDOR_ID_RIOWORKS: + return( rioworks_str ); default: return( unknown_str ); } @@ -2083,3 +2531,4 @@ osm_get_sm_mgr_state_str( return( __osm_sm_mgr_state_str[state] ); } + diff --git a/trunk/ulp/opensm/user/libopensm/osm_log.c b/trunk/ulp/opensm/user/libopensm/osm_log.c index 3f6be6a2..e7bc851f 100644 --- a/trunk/ulp/opensm/user/libopensm/osm_log.c +++ b/trunk/ulp/opensm/user/libopensm/osm_log.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Implementaion of osm_log_t. @@ -55,6 +56,9 @@ #include #include #include +#include + +static int log_exit_count = 0; #ifndef WIN32 #include @@ -75,10 +79,53 @@ static char *month_str[] = { "Nov", "Dec" }; -#else -void OsmReportState(IN const char *p_str); +#else +void +OsmReportState( + IN const char *p_str); #endif /* ndef WIN32 */ +#ifndef WIN32 + +static void truncate_log_file(osm_log_t* const p_log) +{ + int fd = fileno(p_log->out_port); + if (ftruncate(fd, 0) < 0) + fprintf(stderr, "truncate_log_file: cannot truncate: %s\n", + strerror(errno)); + if (lseek(fd, 0, SEEK_SET) < 0) + fprintf(stderr, "truncate_log_file: cannot rewind: %s\n", + strerror(errno)); + p_log->count = 0; +} + +#else /* Windows */ + +static void truncate_log_file(osm_log_t* const p_log) +{ + fprintf(stderr, "truncate_log_file: cannot truncate on windows system (yet)\n"); +} +#endif /* ndef WIN32 */ + +int osm_log_printf(osm_log_t *p_log, osm_log_level_t level, + const char *fmt, ...) +{ + va_list args; + int ret; + + if (!(p_log->level&level)) + return 0; + + va_start(args, fmt); + ret = vfprintf(stdout, fmt, args); + va_end(args); + + if (p_log->flush || level&OSM_LOG_ERROR) + fflush( stdout ); + + return ret; +} + void osm_log( IN osm_log_t* const p_log, @@ -106,89 +153,78 @@ osm_log( #endif /* WIN32 */ /* If this is a call to syslog - always print it */ - if ( verbosity & OSM_LOG_SYS ) + if ( verbosity & (OSM_LOG_SYS | p_log->level) ) { - /* this is a call to the syslog */ va_start( args, p_str ); vsprintf( buffer, p_str, args ); va_end(args); - cl_log_event("OpenSM", LOG_INFO, buffer , NULL, 0); - /* SYSLOG should go to stdout too */ - if (p_log->out_port != stdout) + /* this is a call to the syslog */ + if (verbosity & OSM_LOG_SYS) { - printf("%s\n", buffer); - fflush( stdout ); - } + cl_log_event("OpenSM", LOG_INFO, buffer , NULL, 0); - /* send it also to the log file */ + /* SYSLOG should go to stdout too */ + if (p_log->out_port != stdout) + { + printf("%s\n", buffer); + fflush( stdout ); + } #ifdef WIN32 - GetLocalTime(&st); - fprintf( p_log->out_port, "[%02d:%02d:%02d:%03d][%04X] -> %s", - st.wHour, st.wMinute, st.wSecond, st.wMilliseconds, - pid, buffer); - OsmReportState(buffer); + OsmReportState(buffer); +#endif /* WIN32 */ + } -#else - fprintf( p_log->out_port, "%s %02d %02d:%02d:%02d %06d [%04X] -> %s\n", - (result.tm_mon < 12 ? month_str[result.tm_mon] : "???"), - result.tm_mday, result.tm_hour, - result.tm_min, result.tm_sec, - usecs, pid, buffer); - fflush( p_log->out_port ); -#endif - } + /* regular log to default out_port */ + cl_spinlock_acquire( &p_log->lock ); - /* SYS messages go to the log anyways */ - if (p_log->level & verbosity) - { -#ifdef _MEM_DEBUG_MODE_ - /* If we are running in MEM_DEBUG_MODE then - the cl_mem_check will be called on every run */ - if (cl_mem_check() == FALSE) + if (p_log->max_size && p_log->count > p_log->max_size) { - fprintf( p_log->out_port, "*** MEMORY ERROR!!! ***\n" ); - CL_ASSERT(0); + /* truncate here */ + fprintf(stderr, "osm_log: log file exceeds the limit %lu. Truncating.\n", + p_log->max_size); + truncate_log_file(p_log); } -#endif - - va_start( args, p_str ); - vsprintf( buffer, p_str, args ); - va_end(args); - - /* regular log to default out_port */ - cl_spinlock_acquire( &p_log->lock ); + #ifdef WIN32 GetLocalTime(&st); - ret = fprintf( p_log->out_port, "[%02d:%02d:%02d:%03d][%04X] -> %s", - st.wHour, st.wMinute, st.wSecond, st.wMilliseconds, - pid, buffer); - + _retry: + ret = fprintf( p_log->out_port, "[%02d:%02d:%02d:%03d][%04X] -> %s", + st.wHour, st.wMinute, st.wSecond, st.wMilliseconds, + pid, buffer ); #else pid = pthread_self(); - tim = time(NULL); + _retry: ret = fprintf( p_log->out_port, "%s %02d %02d:%02d:%02d %06d [%04X] -> %s", - ((result.tm_mon < 12) && (result.tm_mon >= 0) ? - month_str[result.tm_mon] : "???"), + (result.tm_mon < 12 ? month_str[result.tm_mon] : "???"), result.tm_mday, result.tm_hour, result.tm_min, result.tm_sec, - usecs, pid, buffer); + usecs, pid, buffer ); +#endif + + /* flush log */ + if (ret > 0 && (p_log->flush || (verbosity & OSM_LOG_ERROR)) && + fflush( p_log->out_port ) < 0) + ret = -1; -#endif /* WIN32 */ - - /* - Flush log on errors too. - */ - if( p_log->flush || (verbosity & OSM_LOG_ERROR) ) - fflush( p_log->out_port ); - - cl_spinlock_release( &p_log->lock ); - - if (ret < 0) + if (ret >= 0) + { + log_exit_count = 0; + p_log->count += ret; + } + else if (log_exit_count < 3) { - fprintf(stderr, "OSM LOG FAILURE! Probably quota exceeded\n"); - exit(1); + log_exit_count++; + if (errno == ENOSPC && p_log->max_size) { + fprintf(stderr, "osm_log: write failed: %s. Truncating log file.\n", + strerror(errno)); + truncate_log_file(p_log); + goto _retry; + } + fprintf(stderr, "osm_log: write failed: %s\n", strerror(errno)); } + + cl_spinlock_release( &p_log->lock ); } } @@ -221,3 +257,71 @@ osm_is_debug(void) return FALSE; #endif /* defined( _DEBUG_ ) */ } + +ib_api_status_t +osm_log_init_v2( + IN osm_log_t* const p_log, + IN const boolean_t flush, + IN const uint8_t log_flags, + IN const char *log_file, + IN const unsigned long max_size, + IN const boolean_t accum_log_file ) +{ + struct stat st; + + p_log->level = log_flags; + p_log->flush = flush; + p_log->count = 0; + p_log->max_size = 0; + + if (log_file == NULL || !strcmp(log_file, "-") || + !strcmp(log_file, "stdout")) + { + p_log->out_port = stdout; + } + else if (!strcmp(log_file, "stderr")) + { + p_log->out_port = stderr; + } + else + { + if (accum_log_file) + p_log->out_port = fopen(log_file, "a+"); + else + p_log->out_port = fopen(log_file, "w+"); + + if (!p_log->out_port) + { + if (accum_log_file) + printf("Cannot open %s for appending. Permission denied\n", log_file); + else + printf("Cannot open %s for writing. Permission denied\n", log_file); + + return(IB_UNKNOWN_ERROR); + } + + if (fstat(fileno(p_log->out_port), &st) == 0) + p_log->count = st.st_size; + + p_log->max_size = max_size; + } + + openlog("OpenSM", LOG_CONS | LOG_PID, LOG_USER); + + if (cl_spinlock_init( &p_log->lock ) == CL_SUCCESS) + return IB_SUCCESS; + else + return IB_ERROR; +} + +ib_api_status_t +osm_log_init( + IN osm_log_t* const p_log, + IN const boolean_t flush, + IN const uint8_t log_flags, + IN const char *log_file, + IN const boolean_t accum_log_file ) +{ + return osm_log_init_v2( p_log, flush, log_flags, log_file, 0, accum_log_file ); +} + diff --git a/trunk/ulp/opensm/user/libopensm/osm_mad_pool.c b/trunk/ulp/opensm/user/libopensm/osm_mad_pool.c index e8eb792e..03ccd341 100644 --- a/trunk/ulp/opensm/user/libopensm/osm_mad_pool.c +++ b/trunk/ulp/opensm/user/libopensm/osm_mad_pool.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Implementation of osm_mad_pool_t. @@ -49,6 +50,7 @@ #endif /* HAVE_CONFIG_H */ #include +#include #include #include #include @@ -83,7 +85,7 @@ osm_mad_pool_construct( { CL_ASSERT( p_pool ); - cl_memclr( p_pool, sizeof(*p_pool) ); + memset( p_pool, 0, sizeof(*p_pool) ); cl_qlock_pool_construct( &p_pool->madw_pool ); } @@ -153,7 +155,7 @@ osm_mad_pool_get( CL_ASSERT( total_size ); /* - Frist, acquire a mad wrapper from the mad wrapper pool. + First, acquire a mad wrapper from the mad wrapper pool. */ p_madw = (osm_madw_t*)cl_qlock_pool_get( &p_pool->madw_pool ); if( p_madw == NULL ) @@ -170,7 +172,6 @@ osm_mad_pool_get( Next, acquire a wire mad of the specified size. */ p_mad = osm_vendor_get( h_bind, total_size, &p_madw->vend_wrap ); - if( p_mad == NULL ) { osm_log( p_pool->p_log, OSM_LOG_ERROR, @@ -217,7 +218,7 @@ osm_mad_pool_get_wrapper( CL_ASSERT( p_mad ); /* - Frist, acquire a mad wrapper from the mad wrapper pool. + First, acquire a mad wrapper from the mad wrapper pool. */ p_madw = (osm_madw_t*)cl_qlock_pool_get( &p_pool->madw_pool ); if( p_madw == NULL ) @@ -298,3 +299,4 @@ osm_mad_pool_put( OSM_LOG_EXIT( p_pool->p_log ); } + diff --git a/trunk/ulp/opensm/user/libvendor/SOURCES b/trunk/ulp/opensm/user/libvendor/SOURCES index d128cdfd..929dc1ae 100644 --- a/trunk/ulp/opensm/user/libvendor/SOURCES +++ b/trunk/ulp/opensm/user/libvendor/SOURCES @@ -51,6 +51,7 @@ INCLUDES= \ USER_C_FLAGS=$(USER_C_FLAGS) /Ze #Add preproccessor definitions C_DEFINES=$(C_DEFINES) -DWIN32 -D__WIN__ -D__i386__ -Dinline=__inline -DMT_LITTLE_ENDIAN -DOSM_VENDOR_INTF_AL +C_DEFINES=$(C_DEFINES) -I.. -DHAVE_CONFIG_H !if !$(FREEBUILD) #C_DEFINES=$(C_DEFINES) -D_DEBUG -DDEBUG -DDBG C_DEFINES=$(C_DEFINES) diff --git a/trunk/ulp/opensm/user/libvendor/osm_vendor_al.c b/trunk/ulp/opensm/user/libvendor/osm_vendor_al.c index 04715b8b..a450e4f0 100644 --- a/trunk/ulp/opensm/user/libvendor/osm_vendor_al.c +++ b/trunk/ulp/opensm/user/libvendor/osm_vendor_al.c @@ -533,7 +533,7 @@ __osm_ca_info_init( } /* attr size by verbs definition is required to be (uint32_t *) under opensm is only being set as 1 */ status = ib_query_ca_by_guid( p_vend->h_al, ca_guid, NULL, - &p_ca_info->attr_size ); + (uint32_t*)&p_ca_info->attr_size ); if( (status != IB_INSUFFICIENT_MEMORY ) && (status != IB_SUCCESS ) ) { osm_log( p_vend->p_log, OSM_LOG_ERROR, @@ -799,8 +799,10 @@ osm_vendor_get_all_port_attr( for( port_num = 0; port_num < num_ports; port_num++ ) { - p_attr_array[port_count] = *__osm_ca_info_get_port_attr_ptr( - p_ca_info, port_num ); + p_attr_array[port_count] = + *__osm_ca_info_get_port_attr_ptr( p_ca_info, port_num ); + /* convert lid to host order */ + p_attr_array[port_count].lid = cl_ntoh16(p_attr_array[port_count].lid); port_count++; } } diff --git a/trunk/ulp/opensm/user/libvendor/osm_vendor_mlx_sa.c b/trunk/ulp/opensm/user/libvendor/osm_vendor_mlx_sa.c index f17583d7..ed123c67 100644 --- a/trunk/ulp/opensm/user/libvendor/osm_vendor_mlx_sa.c +++ b/trunk/ulp/opensm/user/libvendor/osm_vendor_mlx_sa.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -33,10 +33,13 @@ + #if HAVE_CONFIG_H # include #endif /* HAVE_CONFIG_H */ +#include +#include #include #include #include @@ -136,7 +139,7 @@ __osmv_sa_mad_rcv_cb( { /* if we are in not in a method response of an rmpp nature we must get only 1 */ - /* HACK: in the future we might need to be smarter for other mathods... */ + /* HACK: in the future we might need to be smarter for other methods... */ if (p_sa_mad->method != IB_MAD_METHOD_GETTABLE_RESP) { query_res.result_cnt = 1; @@ -176,7 +179,7 @@ __osmv_sa_mad_rcv_cb( Exit: /* free the copied query request if found */ - if (p_query_req_copy) cl_free(p_query_req_copy); + if (p_query_req_copy) free(p_query_req_copy); /* put back the request madw */ if (p_req_madw) @@ -214,7 +217,8 @@ __osmv_sa_mad_err_cb( query_res.status = IB_TIMEOUT; query_res.result_cnt = 0; - + query_res.p_result_madw->status = IB_TIMEOUT; + p_madw->status = IB_TIMEOUT; query_res.query_type = p_query_req_copy->query_type; p_query_req_copy->pfn_query_cb( &query_res ); @@ -222,7 +226,7 @@ __osmv_sa_mad_err_cb( if ((p_query_req_copy->flags & OSM_SA_FLAGS_SYNC) == OSM_SA_FLAGS_SYNC) cl_event_signal( &p_bind->sync_event ); - if (p_query_req_copy) cl_free(p_query_req_copy); + if (p_query_req_copy) free(p_query_req_copy); OSM_LOG_EXIT( p_bind->p_log ); } @@ -284,7 +288,7 @@ __osmv_get_lid_and_sm_lid_by_port_guid( /* allocate the attributes */ p_attr_array = - (ib_port_attr_t *)cl_malloc(sizeof(ib_port_attr_t)*num_ports); + (ib_port_attr_t *)malloc(sizeof(ib_port_attr_t)*num_ports); /* obtain the attributes */ status = osm_vendor_get_all_port_attr(p_vend, p_attr_array, &num_ports); @@ -295,7 +299,7 @@ __osmv_get_lid_and_sm_lid_by_port_guid( "Fail to get port attributes (error: %s)\n", ib_get_err_str(status) ); - cl_free(p_attr_array); + free(p_attr_array); goto Exit; } @@ -316,7 +320,7 @@ __osmv_get_lid_and_sm_lid_by_port_guid( } } - cl_free(p_attr_array); + free(p_attr_array); Exit: OSM_LOG_EXIT( p_vend->p_log ); @@ -348,15 +352,15 @@ osmv_bind_sa( bind_info.port_guid = port_guid; bind_info.mad_class = IB_MCLASS_SUBN_ADM; bind_info.class_version = 2; - bind_info.is_responder = FALSE; + bind_info.is_responder = TRUE; bind_info.is_trap_processor = FALSE; - bind_info.is_report_processor = FALSE; + bind_info.is_report_processor = TRUE; bind_info.send_q_size = 256; bind_info.recv_q_size = 256; /* allocate the new sa bind info */ p_sa_bind_info = - (osmv_sa_bind_info_t *)cl_malloc(sizeof(osmv_sa_bind_info_t)); + (osmv_sa_bind_info_t *)malloc(sizeof(osmv_sa_bind_info_t)); if (! p_sa_bind_info) { osm_log( p_log, OSM_LOG_ERROR, @@ -384,7 +388,7 @@ osmv_bind_sa( if (p_sa_bind_info->h_bind == OSM_BIND_INVALID_HANDLE) { - cl_free(p_sa_bind_info); + free(p_sa_bind_info); p_sa_bind_info = OSM_BIND_INVALID_HANDLE; osm_log( p_log, OSM_LOG_ERROR, "osmv_bind_sa: ERR 0506: " @@ -401,7 +405,7 @@ osmv_bind_sa( &p_sa_bind_info->sm_lid); if (status != IB_SUCCESS) { - cl_free(p_sa_bind_info); + free(p_sa_bind_info); p_sa_bind_info = OSM_BIND_INVALID_HANDLE; osm_log( p_log, OSM_LOG_ERROR, "osmv_bind_sa: ERR 0507: " @@ -419,7 +423,7 @@ osmv_bind_sa( "cl_init_event failed: %s\n", ib_get_err_str(cl_status) ); - cl_free(p_sa_bind_info); + free(p_sa_bind_info); p_sa_bind_info = OSM_BIND_INVALID_HANDLE; } @@ -447,6 +451,7 @@ typedef struct _osmv_sa_mad_data uint8_t method; ib_net16_t attr_id; ib_net16_t attr_offset; + ib_net32_t attr_mod; ib_net64_t comp_mask; void *p_attr; } osmv_sa_mad_data_t; @@ -458,7 +463,10 @@ typedef struct _osmv_sa_mad_data * Attribute ID * * attr_offset - * Offset as defiend by RMPP + * Offset as defined by RMPP + * + * attr_mod + * Attribute modifier * * comp_mask * The component mask of the query @@ -533,7 +541,7 @@ __osmv_send_sa_req( cl_atomic_inc( &trans_id ); /* Cleanup the MAD from any residue */ - cl_memclr(p_sa_mad, MAD_BLOCK_SIZE); + memset(p_sa_mad, 0, MAD_BLOCK_SIZE); /* Initialize the standard MAD header. */ ib_mad_init_new( @@ -543,7 +551,7 @@ __osmv_send_sa_req( p_sa_mad_data->method, /* method */ cl_hton64( ( uint64_t ) trans_id ),/* tid */ p_sa_mad_data->attr_id, /* attr id */ - 0 /* attr mod */ + p_sa_mad_data->attr_mod /* attr mod */ ); /* Set the query information. */ @@ -552,8 +560,8 @@ __osmv_send_sa_req( p_sa_mad->comp_mask = p_sa_mad_data->comp_mask; if( p_sa_mad->comp_mask ) { - cl_memcpy( p_sa_mad->data, p_sa_mad_data->p_attr, - ib_get_attr_size(p_sa_mad_data->attr_offset)); + memcpy( p_sa_mad->data, p_sa_mad_data->p_attr, + ib_get_attr_size(p_sa_mad_data->attr_offset)); } /* @@ -581,7 +589,7 @@ __osmv_send_sa_req( To store on the MADW we cast it into what opensm has: p_madw->context.arb_context.context1 */ - p_query_req_copy = cl_malloc(sizeof(*p_query_req_copy)); + p_query_req_copy = malloc(sizeof(*p_query_req_copy)); *p_query_req_copy = *p_query_req; p_madw->context.arb_context.context1 = p_query_req_copy; @@ -602,6 +610,7 @@ __osmv_send_sa_req( "Waiting for async event.\n" ); cl_event_wait_on( &p_bind->sync_event, EVENT_NO_TIMEOUT, FALSE ); cl_event_reset(&p_bind->sync_event); + status = p_madw->status; } Exit: @@ -635,6 +644,7 @@ osmv_query_sa( /* Set the request information. */ sa_mad_data.method = IB_MAD_METHOD_GETTABLE; + sa_mad_data.attr_mod = 0; /* Set the MAD attributes and component mask correctly. */ switch ( p_query_req->query_type ) @@ -647,9 +657,22 @@ osmv_query_sa( if (p_user_query->method) sa_mad_data.method = p_user_query->method; sa_mad_data.attr_offset = p_user_query->attr_offset; sa_mad_data.attr_id = p_user_query->attr_id; + sa_mad_data.attr_mod = p_user_query->attr_mod; sa_mad_data.comp_mask = p_user_query->comp_mask; sa_mad_data.p_attr = p_user_query->p_attr; - break; +#if (0) +#ifdef OSM_VENDOR_INTF_AL + /* HACK for OFED OSM: convert lid order from network to + host for IB_MAD_ATTR_PORTINFO_RECORD */ + if ( (sa_mad_data.attr_id == IB_MAD_ATTR_PORTINFO_RECORD) && + (sa_mad_data.comp_mask & IB_PIR_COMPMASK_LID)) + { + ib_portinfo_record_t * p_pir = (ib_portinfo_record_t *)sa_mad_data.p_attr; + p_pir->lid = cl_ntoh16(p_pir->lid); + } +#endif +#endif + break; case OSMV_QUERY_ALL_SVC_RECS: osm_log( p_log, OSM_LOG_DEBUG, @@ -671,8 +694,8 @@ osmv_query_sa( sa_mad_data.attr_offset = ib_get_attr_offset( sizeof( ib_service_record_t ) ); sa_mad_data.p_attr = &svc_rec; - cl_memcpy( svc_rec.service_name, p_query_req->p_query_input, - sizeof( ib_svc_name_t ) ); + memcpy( svc_rec.service_name, p_query_req->p_query_input, + sizeof( ib_svc_name_t ) ); break; case OSMV_QUERY_SVC_REC_BY_ID: @@ -762,7 +785,7 @@ osmv_query_sa( case OSMV_QUERY_PATH_REC_BY_PORT_GUIDS: osm_log( p_log, OSM_LOG_DEBUG, "osmv_query_sa DBG:001 %s","PATH_REC_BY_PORT_GUIDS\n" ); - cl_memclr(&path_rec, sizeof(ib_path_rec_t )); + memset(&path_rec, 0, sizeof(ib_path_rec_t )); sa_mad_data.attr_id = IB_MAD_ATTR_PATH_RECORD; sa_mad_data.attr_offset = ib_get_attr_offset( sizeof( ib_path_rec_t ) ); @@ -781,24 +804,24 @@ osmv_query_sa( case OSMV_QUERY_PATH_REC_BY_GIDS: osm_log( p_log, OSM_LOG_DEBUG, "osmv_query_sa DBG:001 %s","PATH_REC_BY_GIDS\n" ); - cl_memclr(&path_rec, sizeof(ib_path_rec_t )); + memset(&path_rec, 0, sizeof(ib_path_rec_t )); sa_mad_data.attr_id = IB_MAD_ATTR_PATH_RECORD; sa_mad_data.attr_offset = ib_get_attr_offset( sizeof( ib_path_rec_t ) ); sa_mad_data.comp_mask = ( IB_PR_COMPMASK_DGID | IB_PR_COMPMASK_SGID ); sa_mad_data.p_attr = &path_rec; - cl_memcpy( &path_rec.dgid, - &( ( osmv_gid_pair_t * ) ( p_query_req->p_query_input ) )-> - dest_gid, sizeof( ib_gid_t ) ); - cl_memcpy( &path_rec.sgid, - &( ( osmv_gid_pair_t * ) ( p_query_req->p_query_input ) )-> - src_gid, sizeof( ib_gid_t ) ); + memcpy( &path_rec.dgid, + &( ( osmv_gid_pair_t * ) ( p_query_req->p_query_input ) )-> + dest_gid, sizeof( ib_gid_t ) ); + memcpy( &path_rec.sgid, + &( ( osmv_gid_pair_t * ) ( p_query_req->p_query_input ) )-> + src_gid, sizeof( ib_gid_t ) ); break; case OSMV_QUERY_PATH_REC_BY_LIDS: osm_log( p_log, OSM_LOG_DEBUG, "osmv_query_sa DBG:001 %s","PATH_REC_BY_LIDS\n" ); - cl_memclr(&path_rec, sizeof(ib_path_rec_t )); + memset(&path_rec, 0, sizeof(ib_path_rec_t )); sa_mad_data.method = IB_MAD_METHOD_GET; sa_mad_data.attr_id = IB_MAD_ATTR_PATH_RECORD; sa_mad_data.attr_offset = @@ -853,3 +876,4 @@ osmv_query_sa( *****************************************************************************/ + diff --git a/trunk/ulp/opensm/user/opensm/SOURCES b/trunk/ulp/opensm/user/opensm/SOURCES index d363eebc..f1bd9326 100644 --- a/trunk/ulp/opensm/user/opensm/SOURCES +++ b/trunk/ulp/opensm/user/opensm/SOURCES @@ -47,8 +47,11 @@ SOURCES=\ osm_opensm.c \ osm_pkey.c \ osm_pkey_mgr.c \ + osm_prtn.c \ + osm_prtn_config.c \ osm_pkey_rcv.c \ osm_pkey_rcv_ctrl.c \ + osm_qos.c \ osm_port.c \ osm_port_info_rcv.c \ osm_port_info_rcv_ctrl.c \ @@ -57,6 +60,7 @@ SOURCES=\ osm_req_ctrl.c \ osm_resp.c \ osm_sa.c \ + osm_router.c \ osm_sa_class_port_info.c \ osm_sa_class_port_info_ctrl.c \ osm_sa_guidinfo_record.c \ @@ -70,6 +74,8 @@ SOURCES=\ osm_sa_mad_ctrl.c \ osm_sa_mcmember_record.c \ osm_sa_mcmember_record_ctrl.c \ + osm_sa_mft_record.c \ + osm_sa_mft_record_ctrl.c \ osm_sa_node_record.c \ osm_sa_node_record_ctrl.c \ osm_sa_path_record.c \ @@ -85,6 +91,8 @@ SOURCES=\ osm_sa_slvl_record_ctrl.c \ osm_sa_sminfo_record.c \ osm_sa_sminfo_record_ctrl.c \ + osm_sa_sw_info_record.c \ + osm_sa_sw_info_record_ctrl.c \ osm_sa_vlarb_record.c \ osm_sa_vlarb_record_ctrl.c \ osm_service.c \ @@ -106,6 +114,8 @@ SOURCES=\ osm_trap_rcv_ctrl.c \ osm_ucast_mgr.c \ osm_ucast_updn.c \ + osm_ucast_file.c \ + osm_ucast_ftree.c \ osm_vl15intf.c \ osm_vl_arb_rcv.c \ osm_vl_arb_rcv_ctrl.c \ @@ -143,6 +153,7 @@ INCLUDES= \ USER_C_FLAGS=$(USER_C_FLAGS) /MD #Add preproccessor definitions C_DEFINES=$(C_DEFINES) -DWIN32 -D__WIN__ -D__i386__ -Dinline=__inline -DMT_LITTLE_ENDIAN -DOSM_VENDOR_INTF_AL +C_DEFINES=$(C_DEFINES) -I.. -DHAVE_CONFIG_H !if !$(FREEBUILD) #C_DEFINES=$(C_DEFINES) -D_DEBUG -DDEBUG -DDBG C_DEFINES=$(C_DEFINES) diff --git a/trunk/ulp/opensm/user/opensm/cl_dispatcher.c b/trunk/ulp/opensm/user/opensm/cl_dispatcher.c index 2e3242d1..dd2f78f6 100644 --- a/trunk/ulp/opensm/user/opensm/cl_dispatcher.c +++ b/trunk/ulp/opensm/user/opensm/cl_dispatcher.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,7 +32,6 @@ */ - /* * Abstract: * Implementation of Dispatcher abstraction. @@ -43,25 +42,22 @@ * $Revision: 1.5 $ */ - #if HAVE_CONFIG_H # include #endif /* HAVE_CONFIG_H */ -#include -#include +#include +#include #include /* give some guidance when we build our cl_pool of messages */ -#define CL_DISP_INITIAL_MSG_COUNT 256 +#define CL_DISP_INITIAL_MSG_COUNT 256 #define CL_DISP_MSG_GROW_SIZE 64 - /* give some guidance when we build our cl_pool of registration elements */ -#define CL_DISP_INITIAL_REG_COUNT 16 +#define CL_DISP_INITIAL_REG_COUNT 16 #define CL_DISP_REG_GROW_SIZE 16 - /******************************************************************** __cl_disp_worker @@ -125,7 +121,6 @@ __cl_disp_worker( cl_spinlock_release( &p_disp->lock ); } - /******************************************************************** ********************************************************************/ void @@ -158,7 +153,7 @@ cl_disp_shutdown( /* Free all registration info. */ while( !cl_is_qlist_empty( &p_disp->reg_list ) ) - cl_free( cl_qlist_remove_head( &p_disp->reg_list ) ); + free( cl_qlist_remove_head( &p_disp->reg_list ) ); } /******************************************************************** @@ -176,7 +171,6 @@ cl_disp_destroy( cl_ptr_vector_destroy( &p_disp->reg_vec ); } - /******************************************************************** ********************************************************************/ cl_status_t @@ -224,7 +218,6 @@ cl_disp_init( return( status ); } - /******************************************************************** ********************************************************************/ cl_disp_reg_handle_t @@ -250,12 +243,16 @@ cl_disp_register( } /* Get a registration info from the pool. */ - p_reg = (cl_disp_reg_info_t*)cl_zalloc( sizeof(cl_disp_reg_info_t) ); + p_reg = (cl_disp_reg_info_t*)malloc( sizeof(cl_disp_reg_info_t) ); if( !p_reg ) { cl_spinlock_release( &p_disp->lock ); return( NULL ); } + else + { + memset( p_reg, 0, sizeof(cl_disp_reg_info_t) ); + } p_reg->p_disp = p_disp; p_reg->ref_cnt = 0; @@ -273,7 +270,7 @@ cl_disp_register( status = cl_ptr_vector_set( &p_disp->reg_vec, msg_id, p_reg ); if( status != CL_SUCCESS ) { - cl_free( p_reg ); + free( p_reg ); cl_spinlock_release( &p_disp->lock ); return( NULL ); } @@ -284,7 +281,6 @@ cl_disp_register( return( p_reg ); } - /******************************************************************** ********************************************************************/ void @@ -320,12 +316,11 @@ cl_disp_unregister( /* Remove the registrant from the list. */ cl_qlist_remove_item( &p_disp->reg_list, (cl_list_item_t*)p_reg ); /* Return the registration info to the pool */ - cl_free( p_reg ); + free( p_reg ); cl_spinlock_release( &p_disp->lock ); } - /******************************************************************** ********************************************************************/ cl_status_t @@ -407,3 +402,4 @@ cl_disp_get_queue_status( cl_spinlock_release( &p_disp->lock ); } + diff --git a/trunk/ulp/opensm/user/opensm/cl_event_wheel.c b/trunk/ulp/opensm/user/opensm/cl_event_wheel.c index d657cdf3..a4ec7aa5 100644 --- a/trunk/ulp/opensm/user/opensm/cl_event_wheel.c +++ b/trunk/ulp/opensm/user/opensm/cl_event_wheel.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -37,7 +37,8 @@ #endif /* HAVE_CONFIG_H */ #include -#include +#include +#include #include cl_status_t @@ -126,7 +127,7 @@ __cl_event_wheel_callback( IN void* context ) cl_qlist_remove_head(&p_event_wheel->events_wheel); /* delete the event info object - allocated by cl_event_wheel_reg */ - cl_free(p_event); + free(p_event); } else { @@ -202,7 +203,6 @@ __cl_event_wheel_callback( IN void* context ) /* * Construct and Initialize */ - void cl_event_wheel_construct( IN cl_event_wheel_t* const p_event_wheel ) @@ -326,7 +326,7 @@ cl_event_wheel_destroy( /* remove it from the map */ p_map_item = &(p_event->map_item); cl_qmap_remove_item(&p_event_wheel->events_map, p_map_item); - cl_free(p_event); /* allocated by cl_event_wheel_reg */ + free(p_event); /* allocated by cl_event_wheel_reg */ p_list_item = cl_qlist_remove_head(&p_event_wheel->events_wheel); } @@ -383,7 +383,7 @@ cl_event_wheel_reg( { /* make a new one */ p_event = (cl_event_wheel_reg_info_t *) - cl_malloc( sizeof (cl_event_wheel_reg_info_t) ); + malloc( sizeof (cl_event_wheel_reg_info_t) ); p_event->num_regs = 0; } @@ -500,7 +500,7 @@ cl_event_wheel_unreg( "Removed key:0x%"PRIx64"\n", key ); /* free the item */ - cl_free(p_event); + free(p_event); } else { @@ -606,7 +606,7 @@ main () cl_event_wheel_construct( &event_wheel ); /* init */ - osm_log_init( &log, TRUE, 0xff, NULL, FALSE); + osm_log_init_v2( &log, TRUE, 0xff, NULL, 0, FALSE); cl_event_wheel_init( &event_wheel, &log ); /* Start Playing */ @@ -660,3 +660,4 @@ main () } #endif /* __CL_EVENT_WHEEL_TEST__ */ + diff --git a/trunk/ulp/opensm/user/opensm/main.c b/trunk/ulp/opensm/user/opensm/main.c index 57f986ea..77552a63 100644 --- a/trunk/ulp/opensm/user/opensm/main.c +++ b/trunk/ulp/opensm/user/opensm/main.c @@ -54,7 +54,7 @@ #include #include #include -#include +#include /******************************************************************** D E F I N E G L O B A L V A R I A B L E S @@ -91,28 +91,30 @@ enum service_state g_service_state = SERVICE_STATE_STARTING; void OsmReportState(IN const char *p_str) { - if (!strcmp(p_str, "SUBNET UP\n") || - (!strcmp(p_str, "SM port is down\n")) || - (!strcmp(p_str, "Errors during initialization\n")) || - (!strcmp(p_str, "Entering STANDBY state\n"))) + if ( !strcmp(p_str, "SUBNET UP\n") || + !strcmp(p_str, "SM port is down\n") || + !strcmp(p_str, "Errors during initialization\n") || + !strcmp(p_str, "Entering STANDBY state\n") ) { InterlockedCompareExchange((LONG *)&g_service_state , SERVICE_STATE_STARTED_OK, SERVICE_STATE_STARTING); return; } - if (!strcmp(p_str, "Found remote SM with non-matching sm_key. Exiting\n") || - (!strcmp(p_str, "Errors on subnet. Duplicate GUID found ""by link from a port to itself. ""See osm log for more details\n")) || - (!strcmp(p_str, "Errors on subnet. SM found duplicated guids or 12x ""link with lane reversal badly configured. ""See osm log for more details\n")) || - (!strcmp(p_str, "Fatal: Error restoring Guid-to-Lid persistent database\n"))) + if ( !strcmp(p_str, "Found remote SM with non-matching sm_key. Exiting\n") || + !strcmp(p_str, "Errors on subnet. Duplicate GUID found ""by link from a port to itself. ""See osm log for more details\n") || + !strcmp(p_str, "Errors on subnet. SM found duplicated guids or 12x ""link with lane reversal badly configured. ""See osm log for more details\n") || + !strcmp(p_str, "Fatal: Error restoring Guid-to-Lid persistent database\n") ) { InterlockedCompareExchange((LONG *)&g_service_state , SERVICE_STATE_START_FAILED, SERVICE_STATE_STARTING); return; } - if(!strcmp(p_str, "OpenSM Rev:openib-1.2.0\n") || - (!strcmp(p_str, "Entering MASTER state\n"))|| - (!strcmp(p_str, "Exiting SM\n"))) + if( !strcmp(p_str, "OpenSM Rev:openib-1.2.0\n") || + !strcmp(p_str, "OpenSM Rev:openib-2.0.3\n") || + !strcmp(p_str, "OpenSM Rev:openib-3.0.0\n") || + !strcmp(p_str, "Entering MASTER state\n") || + !strcmp(p_str, "Exiting SM\n") ) { // This are messages that it is safe to ignore return; @@ -144,7 +146,7 @@ show_usage(void) " bound to 1 port at a time.\n" " If GUID given is 0, OpenSM displays a list\n" " of possible port GUIDs and waits for user input.\n" - " Without -g, OpenSM trys to use the default port.\n\n"); + " Without -g, OpenSM tries to use the default port.\n\n"); printf( "-l \n" "--lmc \n" " This option specifies the subnet's LMC value.\n" @@ -160,10 +162,10 @@ show_usage(void) "--priority \n" " This option specifies the SM's PRIORITY.\n" " This will effect the handover cases, where master\n" - " is chosen by priority and GUID.\n" ); + " is chosen by priority and GUID.\n\n" ); printf( "-smkey \n" " This option specifies the SM's SM_Key (64 bits).\n" - " This will effect SM authentication.\n" ); + " This will effect SM authentication.\n\n" ); printf( "-r\n" "--reassign_lids\n" " This option causes OpenSM to reassign LIDs to all\n" @@ -171,14 +173,18 @@ show_usage(void) " may disrupt subnet traffic.\n" " Without -r, OpenSM attempts to preserve existing\n" " LID assignments resolving multiple use of same LID.\n\n"); - printf( "-u\n" - "--updn\n" - " This option activate UPDN algorithm instead of Min Hop\n" - " algorithm (default).\n"); + printf( "-R\n" + "--routing_engine \n" + " This option chooses routing engine instead of Min Hop\n" + " algorithm (default). Supported engines: updn, file\n\n"); + printf( "-U\n" + "--ucast_file \n" + " This option specifies name of the unicast dump file\n" + " from where switch forwarding tables will be loaded.\n\n"); printf ("-a\n" "--add_guid_file \n" " Set the root nodes for the Up/Down routing algorithm\n" - " to the guids provided in the given file (one at a line)\n" + " to the guids provided in the given file (one to a line)\n" "\n"); printf( "-o\n" "--once\n" @@ -203,28 +209,37 @@ show_usage(void) " Specifying -maxsmps 0 allows unlimited outstanding\n" " SMPs.\n" " Without -maxsmps, OpenSM defaults to a maximum of\n" - " one outstanding SMP.\n\n" ); + " 4 outstanding SMPs.\n\n" ); printf( "-i \n" "-ignore-guids \n" " This option provides the means to define a set of ports\n" - " (by guids) that will be ignored by the link load \n" + " (by guid) that will be ignored by the link load\n" " equalization algorithm.\n\n" ); printf( "-x\n" "--honor_guid2lid\n" " This option forces OpenSM to honor the guid2lid file,\n" " when it comes out of Standby state, if such file exists\n" - " under OSM_CACHE_DIR, and is valid.\n" - " By default this is FALSE.\n" ); + " under OSM_CACHE_DIR, and is valid. By default, this is FALSE.\n\n" ); printf( "-f\n" "--log_file\n" " This option defines the log to be the given file.\n" - " By default the log goes to /var/log/osm.log.\n" + " By default, the log goes to %temp%/log/osm.log.\n" " For the log to go to standard output use -f stdout.\n\n"); printf( "-e\n" "--erase_log_file\n" - " This option will cause deletion of the log file \n" - " (if it previously exists). By default, the log file \n" + " This option will cause deletion of the log file\n" + " (if it previously exists). By default, the log file\n" " is accumulative.\n\n"); + printf( "-P\n" + "--Pconfig\n" + " This option defines the optional partition configuration file.\n" + " The default name is '%s'.\n\n", OSM_DEFAULT_PARTITION_CONFIG_FILE); + printf( "-Q\n" + "--no_qos\n" + " This option disables QoS setup.\n\n"); + printf( "-N\n" + "--no_part_enforce\n" + " This option disables partition enforcement on switch external ports.\n\n"); printf( "-y\n" "--stay_on_fatal\n" " This option will cause SM not to exit on fatal initialization\n" @@ -236,13 +251,13 @@ show_usage(void) " This option increases the log verbosity level.\n" " The -v option may be specified multiple times\n" " to further increase the verbosity level.\n" - " See the -vf option for more information about.\n" + " See the -D option for more information about\n" " log verbosity.\n\n" ); printf( "-V\n" " This option sets the maximum verbosity level and\n" " forces log flushing.\n" - " The -V is equivalent to '-vf 0xFF -d 2'.\n" - " See the -vf option for more information about.\n" + " The -V is equivalent to '-D 0xFF -d 2'.\n" + " See the -D option for more information about\n" " log verbosity.\n\n" ); printf( "-D \n" " This option sets the log verbosity level.\n" @@ -276,7 +291,6 @@ show_usage(void) " -d1 - Force single threaded dispatching\n" " -d2 - Force log flushing after each log message\n" " -d3 - Disable multicast support\n" - " -d4 - Put OpenSM in memory tracking mode\n" " -d10 - Put OpenSM in testability mode\n" " Without -d, no debug options are enabled\n\n" ); printf( "-h\n" @@ -334,7 +348,7 @@ get_port_guid( /* If num_ports is 1, then there is only one possible port to use. Use it. */ if ( num_ports == 1 ) { - printf("Using default guid 0x%" PRIx64 "\n", cl_hton64(attr_array[0].port_guid)); + printf("Using default GUID 0x%" PRIx64 "\n", cl_hton64(attr_array[0].port_guid)); return( attr_array[0].port_guid ); } @@ -342,7 +356,7 @@ get_port_guid( /* If port_guid is 0, and this is gen2 - use the default port whose info is in attr_array[0] */ if ( port_guid == 0 ) { - printf("Using default guid 0x%" PRIx64 "\n", cl_hton64(attr_array[0].port_guid)); + printf("Using default GUID 0x%" PRIx64 "\n", cl_hton64(attr_array[0].port_guid)); return( attr_array[0].port_guid ); } #endif /* OSM_VENDOR_INTF_OPENIB */ @@ -543,7 +557,7 @@ opensm_main( boolean_t cache_options = FALSE; char *ignore_guids_file_name = NULL; uint32_t val; - const char * const short_option = "i:f:ed:g:l:s:t:a:uvVhorcyx"; + const char * const short_option = "i:f:ed:g:l:L:s:t:a:R:U:P:NQvVhorcyx"; /* @@ -565,15 +579,21 @@ opensm_main( { "verbose", 0, NULL, 'v'}, { "D", 1, NULL, 'D'}, { "log_file", 1, NULL, 'f'}, + { "log_limit", 1, NULL, 'L'}, { "erase_log_file",0, NULL, 'e'}, + { "Pconfig", 1, NULL, 'P'}, + { "no_part_enforce",0,NULL, 'N'}, + { "no_qos", 0, NULL, 'Q'}, { "maxsmps", 1, NULL, 'n'}, + { "console", 0, NULL, 'q'}, { "V", 0, NULL, 'V'}, { "help", 0, NULL, 'h'}, { "once", 0, NULL, 'o'}, { "reassign_lids", 0, NULL, 'r'}, { "priority", 1, NULL, 'p'}, { "smkey", 1, NULL, 'k'}, - { "updn", 0, NULL, 'u'}, + { "routing_engine",1, NULL, 'R'}, + { "ucast_file" ,1, NULL, 'U'}, { "add_guid_file", 1, NULL, 'a'}, { "cache-options", 0, NULL, 'c'}, { "stay_on_fatal", 0, NULL, 'y'}, @@ -661,6 +681,14 @@ opensm_main( printf(" Max wire smp's = %d\n", opt.max_wire_smps); break; + case 'q': + /* + * OpenSM interactive console + */ + opt.console = TRUE; + printf(" Enabling OpenSM interactive console\n"); + break; + case 'd': dbg_lvl = strtol(optarg, NULL, 0); printf(" d level = 0x%x\n", dbg_lvl); @@ -684,13 +712,13 @@ opensm_main( printf(" Debug mode: Disable multicast support\n"); opt.disable_multicast = TRUE; } - else if(dbg_lvl == 4) - { - mem_track = TRUE; - } + /* + * NOTE: Debug level 4 used to be used for memory tracking + * but this is now deprecated + */ else if(dbg_lvl >= 10) { - /* Please look at subnet.h for list of testability modes. */ + /* Please look at osm_subnet.h for list of testability modes. */ opt.testability_mode = dbg_lvl - 9; } else @@ -722,11 +750,28 @@ opensm_main( opt.log_file = optarg; break; + case 'L': + opt.log_max_size = strtoul(optarg, NULL, 0) * (1024*1024); + printf(" Log file max size is %lu bytes\n", opt.log_max_size); + break; + case 'e': opt.accum_log_file = FALSE; printf(" Creating new log file\n"); break; + case 'P': + opt.partition_config_file = optarg; + break; + + case 'N': + opt.no_partition_enforcement = TRUE; + break; + + case 'Q': + opt.no_qos = TRUE; + break; + case 'y': opt.exit_on_fatal = FALSE; printf(" Staying on fatal initialization errors\n"); @@ -759,9 +804,14 @@ opensm_main( opt.sm_key = sm_key; break; - case 'u': - opt.updn_activate = TRUE; - printf(" Activate UPDN algorithm\n"); + case 'R': + opt.routing_engine_name = optarg; + printf(" Activate \'%s\' routing engine\n", optarg); + break; + + case 'U': + opt.ucast_dump_file = optarg; + printf(" Ucast dump file is \'%s\'\n", optarg); break; case 'a': @@ -802,9 +852,6 @@ opensm_main( /* Done with options description */ printf("-------------------------------------------------\n"); - if (mem_track) - __cl_mem_track(TRUE); - opt.log_flags = (uint8_t)log_flags; status = osm_opensm_init( &osm, &opt ); @@ -864,13 +911,6 @@ opensm_main( } osm_opensm_sweep( &osm ); - /* since osm_opensm_init get opt as RO we'll set the opt value with UI pfn here */ - /* Now do the registration */ - if (opt.updn_activate) - if (osm_updn_reg_calc_min_hop_table(osm.p_updn_ucast_routing, &(osm.subn.opt))) { - status = IB_ERROR; - goto Exit; - } status = osm_opensm_wait_for_subnet_up( &osm, EVENT_NO_TIMEOUT, TRUE ); @@ -914,8 +954,6 @@ opensm_main( g_service_state = SERVICE_STATE_START_FAILED; osm_opensm_destroy( &osm ); - if (mem_track) cl_mem_display(); - exit( 0 ); } diff --git a/trunk/ulp/opensm/user/opensm/osm.h b/trunk/ulp/opensm/user/opensm/osm.h new file mode 100644 index 00000000..2caab674 --- /dev/null +++ b/trunk/ulp/opensm/user/opensm/osm.h @@ -0,0 +1,68 @@ +/*++ +============================================================================= +Copyright (c) 2005 Mellanox Technologies + +Module Name: + + osm.mc + +Abstract: + + OpenSM event log messages + +Authors: + + Leonid Keller + +Environment: + + Kernel Mode . + +============================================================================= +--*/ + +// +// Values are 32 bit values layed out as follows: +// +// 3 3 2 2 2 2 2 2 2 2 2 2 1 1 1 1 1 1 1 1 1 1 +// 1 0 9 8 7 6 5 4 3 2 1 0 9 8 7 6 5 4 3 2 1 0 9 8 7 6 5 4 3 2 1 0 +// +---+-+-+-----------------------+-------------------------------+ +// |Sev|C|R| Facility | Code | +// +---+-+-+-----------------------+-------------------------------+ +// +// where +// +// Sev - is the severity code +// +// 00 - Success +// 01 - Informational +// 10 - Warning +// 11 - Error +// +// C - is the Customer code flag +// +// R - is a reserved bit +// +// Facility - is the facility code +// +// Code - is the facility's status code +// +// +// Define the facility codes +// + + +// +// Define the severity codes +// + + +// +// MessageId: EVENT_OSM_ANY_INFO +// +// MessageText: +// +// %1 +// +#define EVENT_OSM_ANY_INFO 0x00000000L + diff --git a/trunk/ulp/opensm/user/opensm/osm.rc b/trunk/ulp/opensm/user/opensm/osm.rc new file mode 100644 index 00000000..116522b7 --- /dev/null +++ b/trunk/ulp/opensm/user/opensm/osm.rc @@ -0,0 +1,2 @@ +LANGUAGE 0x9,0x1 +1 11 MSG00001.bin diff --git a/trunk/ulp/opensm/user/opensm/osm_console.c b/trunk/ulp/opensm/user/opensm/osm_console.c index a0f36f04..9eadd40d 100644 --- a/trunk/ulp/opensm/user/opensm/osm_console.c +++ b/trunk/ulp/opensm/user/opensm/osm_console.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -31,6 +31,7 @@ * $Id$ */ + #if HAVE_CONFIG_H # include #endif /* HAVE_CONFIG_H */ @@ -222,3 +223,4 @@ void osm_console(osm_opensm_t *p_osm) } } + diff --git a/trunk/ulp/opensm/user/opensm/osm_db_files.c b/trunk/ulp/opensm/user/opensm/osm_db_files.c index 0ac9234e..43a90d10 100644 --- a/trunk/ulp/opensm/user/opensm/osm_db_files.c +++ b/trunk/ulp/opensm/user/opensm/osm_db_files.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Implemntation of the osm_db interface using simple text files @@ -43,11 +44,12 @@ # include #endif /* HAVE_CONFIG_H */ -#include -#include #include #include #include +#include +#include +#include /****d* Database/OSM_DB_MAX_LINE_LEN * NAME @@ -123,7 +125,7 @@ void osm_db_construct( IN osm_db_t* const p_db ) { - cl_memclr(p_db, sizeof(osm_db_t)); + memset(p_db, 0, sizeof(osm_db_t)); cl_list_construct( &p_db->domains ); } @@ -141,8 +143,8 @@ osm_db_domain_destroy( cl_spinlock_destroy( &p_domain_imp->lock ); st_free_table( p_domain_imp->p_hash ); - cl_free( p_domain_imp->file_name ); - cl_free( p_domain_imp ); + free( p_domain_imp->file_name ); + free( p_domain_imp ); } /*************************************************************************** @@ -156,10 +158,10 @@ osm_db_destroy( while ((p_domain = cl_list_remove_head( &p_db->domains )) != NULL ) { osm_db_domain_destroy( p_domain ); - cl_free( p_domain ); + free( p_domain ); } cl_list_destroy( &p_db->domains ); - cl_free( p_db->p_db_imp ); + free( p_db->p_db_imp ); } /*************************************************************************** @@ -174,11 +176,11 @@ osm_db_init( OSM_LOG_ENTER( p_log, osm_db_init ); - p_db_imp = (osm_db_imp_t *)cl_malloc(sizeof(osm_db_imp_t)); + p_db_imp = (osm_db_imp_t *)malloc(sizeof(osm_db_imp_t)); CL_ASSERT( p_db_imp != NULL); p_db_imp->db_dir_name = getenv("OSM_CACHE_DIR"); - if ( p_db_imp->db_dir_name == NULL ) + if (!p_db_imp->db_dir_name || !(*p_db_imp->db_dir_name)) p_db_imp->db_dir_name = OSM_DEFAULT_CACHE_DIR; /* Create the directory if it doesn't exist */ @@ -190,7 +192,7 @@ osm_db_init( /* make sure the directory exists */ if (lstat(p_db_imp->db_dir_name, &dstat)) { - if (mkdir(p_db_imp->db_dir_name, 777)) + if (mkdir(p_db_imp->db_dir_name, 0755)) { osm_log( p_log, OSM_LOG_ERROR, "osm_db_init: ERR 6101: " @@ -228,18 +230,18 @@ osm_db_domain_init( OSM_LOG_ENTER( p_log, osm_db_domain_init ); /* allocate a new domain object */ - p_domain = (osm_db_domain_t *)cl_malloc(sizeof(osm_db_domain_t)); + p_domain = (osm_db_domain_t *)malloc(sizeof(osm_db_domain_t)); CL_ASSERT( p_domain != NULL ); p_domain_imp = - (osm_db_domain_imp_t *)cl_malloc(sizeof(osm_db_domain_imp_t)); + (osm_db_domain_imp_t *)malloc(sizeof(osm_db_domain_imp_t)); CL_ASSERT( p_domain_imp != NULL ); dir_name_len = strlen(((osm_db_imp_t*)p_db->p_db_imp)->db_dir_name); /* set the domain file name */ p_domain_imp->file_name = - (char *)cl_malloc(sizeof(char)*(dir_name_len) + strlen(domain_name) + 2); + (char *)malloc(sizeof(char)*(dir_name_len) + strlen(domain_name) + 2); CL_ASSERT(p_domain_imp->file_name != NULL); strcpy(p_domain_imp->file_name,((osm_db_imp_t*)p_db->p_db_imp)->db_dir_name); strcat(p_domain_imp->file_name,domain_name); @@ -252,8 +254,8 @@ osm_db_domain_init( "osm_db_domain_init: ERR 6102: " " Failed to open the db file:%s\n", p_domain_imp->file_name); - cl_free(p_domain_imp); - cl_free(p_domain); + free(p_domain_imp); + free(p_domain); p_domain = NULL; goto Exit; } @@ -359,19 +361,19 @@ osm_db_restore( goto EndParsing; } - p_key = (char *)cl_malloc(sizeof(char)*(strlen(p_first_word) + 1)); + p_key = (char *)malloc(sizeof(char)*(strlen(p_first_word) + 1)); strcpy(p_key, p_first_word); p_rest_of_line = strtok_r(NULL, "\n", &p_last); if (p_rest_of_line != NULL) { p_accum_val = - (char*)cl_malloc(sizeof(char)*(strlen(p_rest_of_line) + 1)); + (char*)malloc(sizeof(char)*(strlen(p_rest_of_line) + 1)); strcpy(p_accum_val, p_rest_of_line); } else { - p_accum_val = (char*)cl_malloc(2); + p_accum_val = (char*)malloc(2); strcpy(p_accum_val, "\0"); } } @@ -424,9 +426,9 @@ osm_db_restore( /* accumulate into the value */ p_prev_val = p_accum_val; p_accum_val = - (char *)cl_malloc(strlen(p_prev_val) + strlen(sLine) + 1); + (char *)malloc(strlen(p_prev_val) + strlen(sLine) + 1); strcpy(p_accum_val, p_prev_val); - cl_free(p_prev_val); + free(p_prev_val); strcat(p_accum_val, sLine); } } /* in key */ @@ -468,7 +470,7 @@ osm_db_store( p_domain_imp = (osm_db_domain_imp_t *)p_domain->p_domain_imp; p_tmp_file_name = - (char *)cl_malloc(sizeof(char)*(strlen(p_domain_imp->file_name)+8)); + (char *)malloc(sizeof(char)*(strlen(p_domain_imp->file_name)+8)); strcpy(p_tmp_file_name, p_domain_imp->file_name); strcat(p_tmp_file_name,".tmp"); @@ -509,7 +511,7 @@ osm_db_store( } Exit: cl_spinlock_release( &p_domain_imp->lock ); - cl_free(p_tmp_file_name); + free(p_tmp_file_name); OSM_LOG_EXIT( p_log ); return status; } @@ -521,8 +523,8 @@ osm_db_store( int __osm_clear_tbl_entry(st_data_t key, st_data_t val, st_data_t arg) { - cl_free((char*)key); - cl_free((char*)val); + free((char*)key); + free((char*)val); return ST_DELETE; } @@ -620,17 +622,18 @@ osm_db_update( else { /* need to allocate the key */ - p_new_key = cl_malloc(sizeof(char)*(strlen(p_key) + 1)); + p_new_key = malloc(sizeof(char)*(strlen(p_key) + 1)); strcpy(p_new_key, p_key); } /* need to arange a new copy of the value */ - p_new_val = cl_malloc(sizeof(char)*(strlen(p_val) + 1)); + p_new_val = malloc(sizeof(char)*(strlen(p_val) + 1)); strcpy(p_new_val, p_val); st_insert(p_domain_imp->p_hash, (st_data_t)p_new_key, (st_data_t)p_new_val); - if (p_prev_val) cl_free(p_prev_val); + if (p_prev_val) + free(p_prev_val); cl_spinlock_release( &p_domain_imp->lock ); @@ -669,8 +672,8 @@ osm_db_delete( } else { - cl_free(p_key); - cl_free(p_prev_val); + free(p_key); + free(p_prev_val); res = 0; } } @@ -707,7 +710,7 @@ main(int argc, char **argv) cl_list_construct( &keys ); cl_list_init( &keys, 10 ); - osm_log_init( &log, TRUE, 0xff, "/tmp/test_osm_db.log", FALSE); + osm_log_init_v2( &log, TRUE, 0xff, "/var/log/osm_db_test.log", 0, FALSE); osm_db_construct(&db); if (osm_db_init(&db, &log)) @@ -790,3 +793,4 @@ main(int argc, char **argv) cl_list_destroy( &keys ); } #endif + diff --git a/trunk/ulp/opensm/user/opensm/osm_db_pack.c b/trunk/ulp/opensm/user/opensm/osm_db_pack.c index bf45d77f..14b923e8 100644 --- a/trunk/ulp/opensm/user/opensm/osm_db_pack.c +++ b/trunk/ulp/opensm/user/opensm/osm_db_pack.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + #if HAVE_CONFIG_H # include #endif /* HAVE_CONFIG_H */ @@ -39,6 +40,7 @@ #include #include #include + static inline void __osm_pack_guid(uint64_t guid, char *p_guid_str) { @@ -106,7 +108,7 @@ osm_db_guid2lid_guids( while ( (p_key = cl_list_remove_head( &keys )) != NULL ) { - p_guid_elem = (osm_db_guid_elem_t*)cl_malloc(sizeof(osm_db_guid_elem_t)); + p_guid_elem = (osm_db_guid_elem_t*)malloc(sizeof(osm_db_guid_elem_t)); CL_ASSERT( p_guid_elem != NULL ); p_guid_elem->guid = __osm_unpack_guid(p_key); @@ -167,3 +169,4 @@ osm_db_guid2lid_delete( return( osm_db_delete( p_g2l, guid_str) ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_drop_mgr.c b/trunk/ulp/opensm/user/opensm/osm_drop_mgr.c index ed8933b4..eb8bbd4b 100644 --- a/trunk/ulp/opensm/user/opensm/osm_drop_mgr.c +++ b/trunk/ulp/opensm/user/opensm/osm_drop_mgr.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Implementation of osm_drop_mgr_t. @@ -48,12 +49,15 @@ # include #endif /* HAVE_CONFIG_H */ +#include +#include #include #include #include #include #include #include +#include #include #include #include @@ -69,7 +73,7 @@ osm_drop_mgr_construct( IN osm_drop_mgr_t* const p_mgr ) { CL_ASSERT( p_mgr ); - cl_memclr( p_mgr, sizeof(*p_mgr) ); + memset( p_mgr, 0, sizeof(*p_mgr) ); } /********************************************************************** @@ -112,7 +116,29 @@ osm_drop_mgr_init( /********************************************************************** **********************************************************************/ -void +static void +__osm_drop_mgr_remove_router( + IN const osm_drop_mgr_t* const p_mgr, + IN const ib_net64_t portguid ) +{ + osm_router_t *p_rtr; + cl_qmap_t* p_rtr_guid_tbl; + + p_rtr_guid_tbl = &p_mgr->p_subn->rtr_guid_tbl; + p_rtr = (osm_router_t*)cl_qmap_remove( p_rtr_guid_tbl, portguid ); + if( p_rtr != (osm_router_t*)cl_qmap_end( p_rtr_guid_tbl ) ) + { + osm_log( p_mgr->p_log, OSM_LOG_VERBOSE, + "__osm_drop_mgr_remove_router: " + "Cleaned router for port guid 0x%016" PRIx64 "\n", + cl_ntoh64( portguid ) ); + osm_router_delete( &p_rtr ); + } +} + +/********************************************************************** + **********************************************************************/ +static void __osm_drop_mgr_remove_port( IN const osm_drop_mgr_t* const p_mgr, IN osm_port_t* p_port ) @@ -140,7 +166,6 @@ __osm_drop_mgr_remove_port( ib_gid_t port_gid; ib_mad_notice_attr_t notice; ib_api_status_t status; - char* p_node_desc; OSM_LOG_ENTER( p_mgr->p_log, __osm_drop_mgr_remove_port ); @@ -170,9 +195,6 @@ __osm_drop_mgr_remove_port( } p_port_guid_tbl = &p_mgr->p_subn->port_guid_tbl; - p_port_lid_tbl = &p_mgr->p_subn->port_lid_tbl; - p_sm_guid_tbl = &p_mgr->p_subn->sm_guid_tbl; - p_port_check = (osm_port_t*)cl_qmap_remove( p_port_guid_tbl, port_guid ); if( p_port_check != p_port ) { @@ -182,18 +204,21 @@ __osm_drop_mgr_remove_port( cl_ntoh64( port_guid ) ); goto Exit; } - - p_sm = (osm_remote_sm_t*)cl_qmap_remove(p_sm_guid_tbl, port_guid ); + + p_sm_guid_tbl = &p_mgr->p_subn->sm_guid_tbl; + p_sm = (osm_remote_sm_t*)cl_qmap_remove( p_sm_guid_tbl, port_guid ); if( p_sm != (osm_remote_sm_t*)cl_qmap_end( p_sm_guid_tbl ) ) { /* need to remove this item */ osm_log( p_mgr->p_log, OSM_LOG_VERBOSE, "__osm_drop_mgr_remove_port: " - "Cleaned sm for port guid\n" ); + "Cleaned SM for port guid\n" ); - cl_free(p_sm); + free(p_sm); } + __osm_drop_mgr_remove_router( p_mgr, port_guid ); + osm_port_get_lid_range_ho( p_port, &min_lid_ho, &max_lid_ho ); osm_log( p_mgr->p_log, OSM_LOG_VERBOSE, @@ -201,6 +226,7 @@ __osm_drop_mgr_remove_port( "Clearing abandoned LID range [0x%X,0x%X]\n", min_lid_ho, max_lid_ho ); + p_port_lid_tbl = &p_mgr->p_subn->port_lid_tbl; for( lid_ho = min_lid_ho; lid_ho <= max_lid_ho; lid_ho++ ) cl_ptr_vector_set( p_port_lid_tbl, lid_ho, NULL ); @@ -232,8 +258,8 @@ __osm_drop_mgr_remove_port( /* Let's check if this is a case of link that is lost (both ports weren't recognized), or a "hiccup" in the subnet - in which case the remote port was recognized, and its state is ACTIVE. - If this is just a "hiccup" - force a heavy sweep in the next sweep. We don't - want to loose that part of the subnet. */ + If this is just a "hiccup" - force a heavy sweep in the next sweep. + We don't want to lose that part of the subnet. */ if (osm_port_discovery_count_get( p_remote_port ) && osm_physp_get_port_state( p_remote_physp ) == IB_LINK_ACTIVE ) { @@ -261,18 +287,18 @@ __osm_drop_mgr_remove_port( osm_node_unlink( p_node, (uint8_t)port_num, p_remote_node, (uint8_t)remote_port_num ); - /* If ther remote node is a ca - need to remove the remote port, since - it is no longer reachable. This can be done if we reset the discovery - count of the remote port. */ - if ( osm_node_get_type( p_remote_node ) == IB_NODE_TYPE_CA ) + /* If the remote node is ca or router - need to remove the remote port, + since it is no longer reachable. This can be done if we reset the + discovery count of the remote port. */ + if ( osm_node_get_type( p_remote_node ) != IB_NODE_TYPE_SWITCH ) { if ( p_remote_port != (osm_port_t*)cl_qmap_end( p_port_guid_tbl ) ) { osm_port_discovery_count_reset( p_remote_port ); osm_log( p_mgr->p_log, OSM_LOG_DEBUG, "__osm_drop_mgr_remove_port: " - "resetting discovery count of node: " - "0x%016" PRIx64 " port num:%u\n", + "Resetting discovery count of node: " + "0x%016" PRIx64 " port num:0x%X\n", cl_ntoh64( osm_node_get_node_guid( p_remote_node ) ), remote_port_num ); } @@ -281,7 +307,7 @@ __osm_drop_mgr_remove_port( osm_log( p_mgr->p_log, OSM_LOG_DEBUG, "__osm_drop_mgr_remove_port: " - "Clearing physical port number %u\n", + "Clearing physical port number 0x%X\n", port_num ); osm_physp_destroy( p_physp ); @@ -301,16 +327,16 @@ __osm_drop_mgr_remove_port( p_mcm = (osm_mcm_info_t*)cl_qlist_remove_head( &p_port->mcm_list ); } - /* initialize the p_node_desc */ - p_node_desc = p_port->p_node ? (char*)(p_port->p_node->node_desc.description) : "UNKNOWN"; - osm_port_delete( &p_port ); + /* initialize the p_node - may need to get node_desc later */ + p_node = p_port->p_node; + osm_port_delete( &p_port ); /* issue a notice - trap 65 */ /* details of the notice */ notice.generic_type = 0x83; /* is generic subn mgt type */ - ib_notice_set_prod_type(¬ice, CL_HTON32(4)); /* A class manager generator */ + ib_notice_set_prod_type_ho(¬ice, 4); /* A class manager generator */ /* endport ceases to be reachable */ notice.g_or_v.generic.trap_num = CL_HTON16(65); /* The sm_base_lid is saved in network order already. */ @@ -319,9 +345,9 @@ __osm_drop_mgr_remove_port( /* we need to provide the GID */ port_gid.unicast.prefix = p_mgr->p_subn->opt.subnet_prefix; port_gid.unicast.interface_id = port_guid; - cl_memcpy(&(notice.data_details.ntc_64_67.gid), - &(port_gid), - sizeof(ib_gid_t)); + memcpy(&(notice.data_details.ntc_64_67.gid), + &(port_gid), + sizeof(ib_gid_t)); /* According to page 653 - the issuer gid in this case of trap is the SM gid, since the SM is the initiator of this trap. */ @@ -337,19 +363,31 @@ __osm_drop_mgr_remove_port( ib_get_err_str( status ) ); goto Exit; } - osm_log( p_mgr->p_log, OSM_LOG_INFO, - "Removed port with GUID:0x%016" PRIx64 - " LID range [0x%X,0x%X] of node:%s\n", - cl_ntoh64( port_gid.unicast.interface_id ), - min_lid_ho, max_lid_ho, p_node_desc ); - + + if (osm_log_is_active( p_mgr->p_log, OSM_LOG_INFO )) + { + char desc[IB_NODE_DESCRIPTION_SIZE + 1]; + + if (p_node) + { + memcpy(desc, p_node->node_desc.description, IB_NODE_DESCRIPTION_SIZE); + desc[IB_NODE_DESCRIPTION_SIZE] = '\0'; + } + osm_log( p_mgr->p_log, OSM_LOG_INFO, + "__osm_drop_mgr_remove_port: " + "Removed port with GUID:0x%016" PRIx64 + " LID range [0x%X,0x%X] of node:%s\n", + cl_ntoh64( port_gid.unicast.interface_id ), + min_lid_ho, max_lid_ho, p_node ? desc : "UNKNOWN" ); + } + Exit: OSM_LOG_EXIT( p_mgr->p_log ); } /********************************************************************** **********************************************************************/ -void +static void __osm_drop_mgr_remove_switch( IN const osm_drop_mgr_t* const p_mgr, IN osm_node_t* p_node ) @@ -373,6 +411,7 @@ __osm_drop_mgr_remove_switch( } else { + p_node->sw = NULL; osm_switch_delete( &p_sw ); } @@ -381,26 +420,7 @@ __osm_drop_mgr_remove_switch( /********************************************************************** **********************************************************************/ -void -__osm_drop_mgr_remove_router( - IN const osm_drop_mgr_t* const p_mgr, - IN osm_node_t* p_node ) -{ - OSM_LOG_ENTER( p_mgr->p_log, __osm_drop_mgr_remove_router ); - - UNUSED_PARAM( p_mgr ); - UNUSED_PARAM( p_node ); - - osm_log( p_mgr->p_log, OSM_LOG_ERROR, - "__osm_drop_mgr_remove_router: ERR 0106: " - "Routers are not supported\n" ); - - OSM_LOG_EXIT( p_mgr->p_log ); -} - -/********************************************************************** - **********************************************************************/ -boolean_t +static boolean_t __osm_drop_mgr_process_node( IN const osm_drop_mgr_t* const p_mgr, IN osm_node_t* p_node ) @@ -426,7 +446,6 @@ __osm_drop_mgr_process_node( Delete all the logical and physical port objects associated with this node. */ - p_node_guid_tbl = &p_mgr->p_subn->node_guid_tbl; p_port_guid_tbl = &p_mgr->p_subn->port_guid_tbl; max_ports = osm_node_get_num_physp( p_node ); @@ -437,8 +456,7 @@ __osm_drop_mgr_process_node( { port_guid = osm_physp_get_port_guid( p_physp ); - p_port = (osm_port_t*)cl_qmap_get( - p_port_guid_tbl, port_guid ); + p_port = (osm_port_t*)cl_qmap_get( p_port_guid_tbl, port_guid ); if( p_port != (osm_port_t*)cl_qmap_end( p_port_guid_tbl ) ) __osm_drop_mgr_remove_port( p_mgr, p_port ); @@ -447,28 +465,10 @@ __osm_drop_mgr_process_node( return_val = TRUE; - switch( osm_node_get_type( p_node ) ) - { - case IB_NODE_TYPE_CA: - break; - - case IB_NODE_TYPE_SWITCH: + if (p_node->sw) __osm_drop_mgr_remove_switch( p_mgr, p_node ); - break; - - case IB_NODE_TYPE_ROUTER: - __osm_drop_mgr_remove_router( p_mgr, p_node ); - break; - - default: - osm_log( p_mgr->p_log, OSM_LOG_ERROR, - "__osm_drop_mgr_process_node: ERR 0104: " - "Node 0x%016" PRIx64 " unknown node type: %u\n", - cl_ntoh64( osm_node_get_node_guid( p_node ) ), - osm_node_get_type( p_node ) ); - break; - } + p_node_guid_tbl = &p_mgr->p_subn->node_guid_tbl; p_node_check = (osm_node_t*)cl_qmap_remove( p_node_guid_tbl, osm_node_get_node_guid( p_node ) ); if( p_node_check != p_node ) @@ -488,13 +488,11 @@ __osm_drop_mgr_process_node( /********************************************************************** **********************************************************************/ -void +static void __osm_drop_mgr_check_node( IN const osm_drop_mgr_t* const p_mgr, IN osm_node_t* p_node ) { - osm_switch_t *p_sw; - cl_qmap_t* p_sw_guid_tbl; ib_net64_t node_guid; osm_physp_t *p_physp; osm_port_t *p_port; @@ -507,18 +505,15 @@ __osm_drop_mgr_check_node( if ( osm_node_get_type( p_node ) != IB_NODE_TYPE_SWITCH ) { - osm_log( p_mgr->p_log, OSM_LOG_VERBOSE, + osm_log( p_mgr->p_log, OSM_LOG_ERROR, "__osm_drop_mgr_check_node: ERR 0107: " "Node 0x%016" PRIx64 " is not a switch node\n", cl_ntoh64( node_guid ) ); goto Exit; } - p_sw_guid_tbl = &p_mgr->p_subn->sw_guid_tbl; - /* Make sure we have a switch object for this node */ - p_sw = (osm_switch_t*)cl_qmap_get( p_sw_guid_tbl, node_guid ); - if (p_sw == (osm_switch_t*)cl_qmap_end( p_sw_guid_tbl ) ) + if (!p_node->sw) { /* We do not have switch info for this node */ osm_log( p_mgr->p_log, OSM_LOG_VERBOSE, @@ -553,7 +548,7 @@ __osm_drop_mgr_check_node( { osm_log( p_mgr->p_log, OSM_LOG_VERBOSE, "__osm_drop_mgr_check_node: " - "Node 0x%016" PRIx64 " no port object\n", + "Node 0x%016" PRIx64 " has no port object\n", cl_ntoh64( node_guid ) ); __osm_drop_mgr_process_node( p_mgr, p_node ); @@ -723,3 +718,4 @@ osm_drop_mgr_process( CL_PLOCK_RELEASE( p_mgr->p_lock ); OSM_LOG_EXIT( p_mgr->p_log ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_fwd_tbl.c b/trunk/ulp/opensm/user/opensm/osm_fwd_tbl.c index 89d735be..1365f385 100644 --- a/trunk/ulp/opensm/user/opensm/osm_fwd_tbl.c +++ b/trunk/ulp/opensm/user/opensm/osm_fwd_tbl.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Implementation of osm_fwd_tbl_t. @@ -48,7 +49,6 @@ # include #endif /* HAVE_CONFIG_H */ -#include #include #include #include @@ -112,3 +112,4 @@ osm_fwd_tbl_destroy( osm_rand_tbl_delete( &p_tbl->p_rnd_tbl ); } } + diff --git a/trunk/ulp/opensm/user/opensm/osm_inform.c b/trunk/ulp/opensm/user/opensm/osm_inform.c index 7a7c89c4..2bd875c1 100644 --- a/trunk/ulp/opensm/user/opensm/osm_inform.c +++ b/trunk/ulp/opensm/user/opensm/osm_inform.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -46,8 +46,9 @@ # include #endif /* HAVE_CONFIG_H */ +#include +#include #include -#include #include #include #include @@ -58,28 +59,26 @@ typedef struct _osm_infr_match_ctxt { - cl_list_t *p_remove_infr_list; + cl_list_t *p_remove_infr_list; ib_mad_notice_attr_t *p_ntc; - } osm_infr_match_ctxt_t; /********************************************************************** **********************************************************************/ - void osm_infr_construct( IN osm_infr_t* const p_infr ) { - cl_memclr( p_infr, sizeof(osm_infr_t) ); + memset( p_infr, 0, sizeof(osm_infr_t) ); } + /********************************************************************** **********************************************************************/ - void osm_infr_destroy( IN osm_infr_t* const p_infr ) { - cl_free(p_infr); + free( p_infr ); } /********************************************************************** @@ -94,10 +93,9 @@ osm_infr_init( /* what else do we need in the inform_record ??? */ /* copy the contents of the provided informinfo */ - cl_memcpy(p_infr,p_infr_rec, sizeof(osm_infr_t)); + memcpy( p_infr, p_infr_rec, sizeof(osm_infr_t) ); } - /********************************************************************** **********************************************************************/ osm_infr_t* @@ -108,66 +106,15 @@ osm_infr_new( CL_ASSERT(p_infr_rec); - p_infr = (osm_infr_t*)cl_malloc( sizeof(osm_infr_t) ); + p_infr = (osm_infr_t*)malloc( sizeof(osm_infr_t) ); if( p_infr ) { - osm_infr_construct( p_infr ); osm_infr_init( p_infr, p_infr_rec ); } return( p_infr ); } -/********************************************************************** - * Match an infr by the RID of the stored inform_info_record - **********************************************************************/ -static -cl_status_t -__match_rid_of_inf_rec( - IN const cl_list_item_t* const p_list_item, - IN void* context ) -{ - ib_inform_info_record_t* p_infr_rec = (ib_inform_info_record_t *)context; - osm_infr_t* p_infr = (osm_infr_t*)p_list_item; - int32_t count; - - count = cl_memcmp( - &p_infr->inform_record, - p_infr_rec, - sizeof(p_infr_rec->subscriber_gid) + - sizeof(p_infr_rec->subscriber_enum) ); - - if(count == 0) - return CL_SUCCESS; - else - return CL_NOT_FOUND; - -} - -/********************************************************************** - **********************************************************************/ -osm_infr_t* -osm_infr_get_by_rid( - IN osm_subn_t const *p_subn, - IN osm_log_t *p_log, - IN ib_inform_info_record_t* const p_infr_rec ) -{ - cl_list_item_t* p_list_item; - - OSM_LOG_ENTER( p_log, osm_infr_get_by_rid ); - - p_list_item = cl_qlist_find_from_head( - &p_subn->sa_infr_list, - __match_rid_of_inf_rec, - p_infr_rec); - - if( p_list_item == cl_qlist_end( &p_subn->sa_infr_list ) ) - p_list_item = NULL; - - OSM_LOG_EXIT( p_log ); - return (osm_infr_t*)p_list_item; -} - /********************************************************************** **********************************************************************/ void @@ -179,22 +126,26 @@ __dump_all_informs( OSM_LOG_ENTER( p_log, __dump_all_informs ); + if( !osm_log_is_active( p_log, OSM_LOG_DEBUG ) ) + goto Exit; + p_list_item = cl_qlist_head( &p_subn->sa_infr_list ); while (p_list_item != cl_qlist_end( &p_subn->sa_infr_list )) { - osm_dump_inform_info(p_log, - &((osm_infr_t*)p_list_item)->inform_record.inform_info, - OSM_LOG_DEBUG); - p_list_item = cl_qlist_next( p_list_item ); + osm_dump_inform_info( p_log, + &((osm_infr_t*)p_list_item)->inform_record.inform_info, + OSM_LOG_DEBUG ); + p_list_item = cl_qlist_next( p_list_item ); } + + Exit: OSM_LOG_EXIT( p_log ); } /********************************************************************** * Match an infr by the InformInfo and Address vector **********************************************************************/ -static -cl_status_t +static cl_status_t __match_inf_rec( IN const cl_list_item_t* const p_list_item, IN void* context ) @@ -202,32 +153,124 @@ __match_inf_rec( osm_infr_t* p_infr_rec = (osm_infr_t *)context; osm_infr_t* p_infr = (osm_infr_t*)p_list_item; osm_log_t *p_log = p_infr_rec->p_infr_rcv->p_log; - cl_status_t status; - int32_t count1, count2; + cl_status_t status = CL_NOT_FOUND; + ib_gid_t all_zero_gid; OSM_LOG_ENTER( p_log, __match_inf_rec); - count1 = cl_memcmp(&p_infr->report_addr, &p_infr_rec->report_addr, - sizeof(p_infr_rec->report_addr)); - if (count1) - osm_log(p_log, OSM_LOG_DEBUG, - "__match_inf_rec : " - "Differ by Address\n"); - count2 = cl_memcmp( - &p_infr->inform_record.inform_info, - &p_infr_rec->inform_record.inform_info, - sizeof(p_infr->inform_record.inform_info)); - if (count2) - osm_log(p_log, OSM_LOG_DEBUG, - "__match_inf_rec : " - "Differ by InformInfo\n" ); - if ((count1 == 0) && (count2 == 0)) - status = CL_SUCCESS; + + if ( memcmp( &p_infr->report_addr, + &p_infr_rec->report_addr, + sizeof(p_infr_rec->report_addr)) ) + { + osm_log( p_log, OSM_LOG_DEBUG, + "__match_inf_rec: " + "Differ by Address\n" ); + goto Exit; + } + + memset( &all_zero_gid, 0, sizeof(ib_gid_t) ); + + /* if inform_info.gid is not zero, ignore lid range */ + if ( !memcmp( &p_infr_rec->inform_record.inform_info.gid, + &all_zero_gid, + sizeof(p_infr_rec->inform_record.inform_info.gid)) ) + { + if ( memcmp( &p_infr->inform_record.inform_info.gid, + &p_infr_rec->inform_record.inform_info.gid, + sizeof(p_infr->inform_record.inform_info.gid)) ) + { + osm_log( p_log, OSM_LOG_DEBUG, + "__match_inf_rec: " + "Differ by InformInfo.gid\n" ); + goto Exit; + } + } else - status = CL_NOT_FOUND; + { + if ( (p_infr->inform_record.inform_info.lid_range_begin != + p_infr_rec->inform_record.inform_info.lid_range_begin) || + (p_infr->inform_record.inform_info.lid_range_end != + p_infr_rec->inform_record.inform_info.lid_range_end) ) + { + osm_log( p_log, OSM_LOG_DEBUG, + "__match_inf_rec: " + "Differ by InformInfo.LIDRange\n" ); + goto Exit; + } + } + + if ( p_infr->inform_record.inform_info.trap_type != + p_infr_rec->inform_record.inform_info.trap_type ) + { + osm_log( p_log, OSM_LOG_DEBUG, + "__match_inf_rec: " + "Differ by InformInfo.TrapType\n" ); + goto Exit; + } + + if ( p_infr->inform_record.inform_info.is_generic != + p_infr_rec->inform_record.inform_info.is_generic ) + { + osm_log( p_log, OSM_LOG_DEBUG, + "__match_inf_rec: " + "Differ by InformInfo.IsGeneric\n" ); + goto Exit; + } + + if (p_infr->inform_record.inform_info.is_generic) + { + if ( p_infr->inform_record.inform_info.g_or_v.generic.trap_num != + p_infr_rec->inform_record.inform_info.g_or_v.generic.trap_num ) + osm_log( p_log, OSM_LOG_DEBUG, + "__match_inf_rec: " + "Differ by InformInfo.Generic.TrapNumber\n" ); + else if ( p_infr->inform_record.inform_info.g_or_v.generic.qpn_resp_time_val != + p_infr_rec->inform_record.inform_info.g_or_v.generic.qpn_resp_time_val ) + osm_log( p_log, OSM_LOG_DEBUG, + "__match_inf_rec: " + "Differ by InformInfo.Generic.QPNRespTimeVal\n" ); + else if ( p_infr->inform_record.inform_info.g_or_v.generic.node_type_msb != + p_infr_rec->inform_record.inform_info.g_or_v.generic.node_type_msb ) + osm_log( p_log, OSM_LOG_DEBUG, + "__match_inf_rec: " + "Differ by InformInfo.Generic.NodeTypeMSB\n" ); + else if ( p_infr->inform_record.inform_info.g_or_v.generic.node_type_lsb != + p_infr_rec->inform_record.inform_info.g_or_v.generic.node_type_lsb ) + osm_log( p_log, OSM_LOG_DEBUG, + "__match_inf_rec: " + "Differ by InformInfo.Generic.NodeTypeLSB\n" ); + else + status = CL_SUCCESS; + } + else + { + if ( p_infr->inform_record.inform_info.g_or_v.vend.dev_id != + p_infr_rec->inform_record.inform_info.g_or_v.vend.dev_id ) + osm_log( p_log, OSM_LOG_DEBUG, + "__match_inf_rec: " + "Differ by InformInfo.Vendor.DeviceID\n" ); + else if ( p_infr->inform_record.inform_info.g_or_v.vend.qpn_resp_time_val != + p_infr_rec->inform_record.inform_info.g_or_v.vend.qpn_resp_time_val ) + osm_log( p_log, OSM_LOG_DEBUG, + "__match_inf_rec: " + "Differ by InformInfo.Vendor.QPNRespTimeVal\n" ); + else if ( p_infr->inform_record.inform_info.g_or_v.vend.vendor_id_msb != + p_infr_rec->inform_record.inform_info.g_or_v.vend.vendor_id_msb ) + osm_log( p_log, OSM_LOG_DEBUG, + "__match_inf_rec: " + "Differ by InformInfo.Vendor.VendorIdMSB\n" ); + else if ( p_infr->inform_record.inform_info.g_or_v.vend.vendor_id_lsb != + p_infr_rec->inform_record.inform_info.g_or_v.vend.vendor_id_lsb ) + osm_log( p_log, OSM_LOG_DEBUG, + "__match_inf_rec: " + "Differ by InformInfo.Vendor.VendorIdLSB\n" ); + else + status = CL_SUCCESS; + } + Exit: OSM_LOG_EXIT( p_log ); return status; - } /********************************************************************** @@ -242,24 +285,26 @@ osm_infr_get_by_rec( OSM_LOG_ENTER( p_log, osm_infr_get_by_rec ); - __dump_all_informs(p_subn, p_log); + __dump_all_informs( p_subn, p_log ); osm_log( p_log, OSM_LOG_DEBUG, "osm_infr_get_by_rec: " - "Looking for Inform Record:\n"); - osm_dump_inform_info(p_log, &(p_infr_rec->inform_record.inform_info), - OSM_LOG_DEBUG); + "Looking for Inform Record\n" ); + osm_dump_inform_info( p_log, &(p_infr_rec->inform_record.inform_info), + OSM_LOG_DEBUG ); osm_log( p_log, OSM_LOG_DEBUG, "osm_infr_get_by_rec: " - "InformInfo list size is : %d\n", + "InformInfo list size %d\n", cl_qlist_count(&p_subn->sa_infr_list) ); + p_list_item = cl_qlist_find_from_head( &p_subn->sa_infr_list, __match_inf_rec, - p_infr_rec); + p_infr_rec ); if( p_list_item == cl_qlist_end( &p_subn->sa_infr_list ) ) p_list_item = NULL; + OSM_LOG_EXIT( p_log ); return (osm_infr_t*)p_list_item; } @@ -269,54 +314,59 @@ osm_infr_get_by_rec( void osm_infr_insert_to_db( IN osm_subn_t *p_subn, - IN osm_log_t *p_log, + IN osm_log_t *p_log, IN osm_infr_t *p_infr) { OSM_LOG_ENTER( p_log, osm_infr_insert_to_db ); osm_log( p_log, OSM_LOG_DEBUG, "osm_infr_insert_to_db: " - "Inserting a new InformInfo Record into Database\n"); + "Inserting new InformInfo Record into Database\n" ); osm_log( p_log, OSM_LOG_DEBUG, "osm_infr_insert_to_db: " - "Dump before insertion (size : %d) : \n", + "Dump before insertion (size %d)\n", cl_qlist_count(&p_subn->sa_infr_list) ); - __dump_all_informs(p_subn, p_log); + __dump_all_informs( p_subn, p_log ); - /* osm_dump_inform_info(p_log, - &(p_infr->inform_record.inform_info), OSM_LOG_DEBUG); */ +#if 0 + osm_dump_inform_info( p_log, + &(p_infr->inform_record.inform_info), OSM_LOG_DEBUG ); +#endif - cl_qlist_insert_head(&p_subn->sa_infr_list, - &p_infr->list_item); + cl_qlist_insert_head( &p_subn->sa_infr_list, + &p_infr->list_item ); osm_log( p_log, OSM_LOG_DEBUG, "osm_infr_insert_to_db: " - "Dump after insertion (size : %d) : \n", + "Dump after insertion (size %d)\n", cl_qlist_count(&p_subn->sa_infr_list) ); - __dump_all_informs(p_subn, p_log); + __dump_all_informs( p_subn, p_log ); OSM_LOG_EXIT( p_log ); } +/********************************************************************** + **********************************************************************/ void osm_infr_remove_from_db( IN osm_subn_t *p_subn, - IN osm_log_t *p_log, + IN osm_log_t *p_log, IN osm_infr_t *p_infr) { OSM_LOG_ENTER( p_log, osm_infr_remove_from_db ); osm_log( p_log, OSM_LOG_DEBUG, "osm_infr_remove_from_db: " - "Removing InformInfo Subscribing GID:0x%016" PRIx64 ",0x%016" PRIx64 + "Removing InformInfo Subscribing GID:0x%016" PRIx64 " : 0x%016" PRIx64 " Enum:0x%X from Database\n", cl_ntoh64(p_infr->inform_record.subscriber_gid.unicast.prefix), cl_ntoh64(p_infr->inform_record.subscriber_gid.unicast.interface_id), p_infr->inform_record.subscriber_enum ); - osm_dump_inform_info(p_log, &(p_infr->inform_record.inform_info), OSM_LOG_DEBUG); - cl_qlist_remove_item(&p_subn->sa_infr_list, - &p_infr->list_item); + osm_dump_inform_info( p_log, &(p_infr->inform_record.inform_info), OSM_LOG_DEBUG ); + + cl_qlist_remove_item( &p_subn->sa_infr_list, + &p_infr->list_item ); osm_infr_destroy( p_infr ); @@ -325,33 +375,30 @@ osm_infr_remove_from_db( /********************************************************************** * Send a report: - * * Given a target address to send to and the notice. - * We need to send: SubnAdmReport - of SubnAdmClass - * + * We need to send SubnAdmReport **********************************************************************/ -static -ib_api_status_t -osm_send_report( - IN osm_infr_t* p_infr_rec, /* the informinfo */ - IN ib_mad_notice_attr_t* p_ntc /* notice to send */ - ) { - - osm_madw_t* p_report_madw; - ib_mad_notice_attr_t* p_report_ntc; - ib_mad_t* p_mad; - ib_sa_mad_t* p_sa_mad; - static atomic32_t trap_fwd_trans_id = 0x02DAB000; - ib_api_status_t status; - osm_log_t *p_log = p_infr_rec->p_infr_rcv->p_log; +static ib_api_status_t +__osm_send_report( + IN osm_infr_t* p_infr_rec, /* the informinfo */ + IN ib_mad_notice_attr_t* p_ntc /* notice to send */ + ) +{ + osm_madw_t* p_report_madw; + ib_mad_notice_attr_t* p_report_ntc; + ib_mad_t* p_mad; + ib_sa_mad_t* p_sa_mad; + static atomic32_t trap_fwd_trans_id = 0x02DAB000; + ib_api_status_t status; + osm_log_t * p_log = p_infr_rec->p_infr_rcv->p_log; - OSM_LOG_ENTER( p_log, osm_send_report ); + OSM_LOG_ENTER( p_log, __osm_send_report ); - /* HACK: who switches or uses the src and dest GIDs in the grh_info ?? */ + /* HACK: who switches or uses the src and dest GIDs in the grh_info ?? */ - /* it is better to use LIDs since the GIDs might not be there for SMI traps */ + /* it is better to use LIDs since the GIDs might not be there for SMI traps */ osm_log( p_log, OSM_LOG_DEBUG, - "osm_send_report: " + "__osm_send_report: " "Forwarding Notice Event from LID:0x%X" " to InformInfo LID: 0x%X TID:0x%X\n", cl_ntoh16(p_ntc->issuer_lid), @@ -369,40 +416,38 @@ osm_send_report( if( !p_report_madw ) { - osm_log(p_log, OSM_LOG_ERROR, - "osm_send_report: ERR 0203: " - "osm_mad_pool_get failed\n" ); + osm_log( p_log, OSM_LOG_ERROR, + "__osm_send_report: ERR 0203: " + "osm_mad_pool_get failed\n" ); status = IB_ERROR; goto Exit; } /* advance trap trans id (cant simply ++ on some systems inside ntoh) */ p_mad = osm_madw_get_mad_ptr( p_report_madw ); - ib_mad_init_new(p_mad, - IB_MCLASS_SUBN_ADM, - 2, - IB_MAD_METHOD_REPORT, - cl_hton64( (uint64_t)cl_atomic_inc( &trap_fwd_trans_id ) ), - IB_MAD_ATTR_NOTICE, - 0); + ib_mad_init_new( p_mad, + IB_MCLASS_SUBN_ADM, + 2, + IB_MAD_METHOD_REPORT, + cl_hton64( (uint64_t)cl_atomic_inc( &trap_fwd_trans_id ) ), + IB_MAD_ATTR_NOTICE, + 0 ); p_sa_mad = osm_madw_get_sa_mad_ptr( p_report_madw ); - /* HACK: I'm not sure if we can simply use the SA MAD format for - notices. However, this is what is implied by the spec */ p_report_ntc = (ib_mad_notice_attr_t*)&(p_sa_mad->data); /* copy the notice */ *p_report_ntc = *p_ntc; /* The TRUE is for: response is expected */ - status = osm_vendor_send(p_report_madw->h_bind, p_report_madw, TRUE ); - if (status != IB_SUCCESS) + status = osm_vendor_send( p_report_madw->h_bind, p_report_madw, TRUE ); + if ( status != IB_SUCCESS ) { - osm_log(p_log, OSM_LOG_ERROR, - "osm_send_report: ERR 0204: " - "osm_vendor_send. status = %s\n", - ib_get_err_str(status)); + osm_log( p_log, OSM_LOG_ERROR, + "__osm_send_report: ERR 0204: " + "osm_vendor_send status = %s\n", + ib_get_err_str(status) ); goto Exit; } @@ -412,16 +457,14 @@ osm_send_report( } /********************************************************************** - * This route comapre a given Notice and a ListItem of InformInfo type. - * - * PRE REQUISITES: + * This routine compares a given Notice and a ListItem of InformInfo type. + * PREREQUISITE: * The Notice.GID should be pre-filled with the trap generator GID **********************************************************************/ -static -void +static void __match_notice_to_inf_rec( IN cl_list_item_t* const p_list_item, - IN void* context ) + IN void* context ) { osm_infr_match_ctxt_t* p_infr_match = (osm_infr_match_ctxt_t *)context; ib_mad_notice_attr_t* p_ntc = p_infr_match->p_ntc; @@ -451,14 +494,14 @@ __match_notice_to_inf_rec( */ /* GID IssuerGID if non zero must match the trap */ - if (p_ii->gid.unicast.prefix != 0 || p_ii->gid.unicast.interface_id != 0 ) + if ( p_ii->gid.unicast.prefix != 0 || p_ii->gid.unicast.interface_id != 0 ) { - /* macth by GID */ - if (cl_memcmp(&(p_ii->gid), &(p_ntc->issuer_gid), sizeof(ib_gid_t))) + /* match by GID */ + if ( memcmp(&(p_ii->gid), &(p_ntc->issuer_gid), sizeof(ib_gid_t)) ) { - osm_log(p_log, OSM_LOG_DEBUG, - "__match_notice_to_inf_rec: " - "Mismatch by GID\n"); + osm_log( p_log, OSM_LOG_DEBUG, + "__match_notice_to_inf_rec: " + "Mismatch by GID\n" ); goto Exit; } } @@ -466,100 +509,103 @@ __match_notice_to_inf_rec( { /* LIDRange IssuerLID apply only if GID=0 */ /* If lid_range_begin of the informInfo is 0xFFFF - then it should be ignored. */ - if (p_ii->lid_range_begin != 0xFFFF) + if ( p_ii->lid_range_begin != 0xFFFF ) { - /* a real lid range is given - check it. */ + /* a real lid range is given - check it */ if ( (cl_hton16(p_ii->lid_range_begin) > cl_hton16(p_ntc->issuer_lid)) || (cl_hton16(p_ntc->issuer_lid) > cl_hton16(p_ii->lid_range_end)) ) { - osm_log(p_log, OSM_LOG_DEBUG, - "__match_notice_to_inf_rec: " - "Mismatch by LID Range. Needed: 0x%X <= 0x%X <= 0x%X\n", - cl_hton16(p_ii->lid_range_begin), - cl_hton16(p_ntc->issuer_lid), - cl_hton16(p_ii->lid_range_end) - ); + osm_log( p_log, OSM_LOG_DEBUG, + "__match_notice_to_inf_rec: " + "Mismatch by LID Range. Needed: 0x%X <= 0x%X <= 0x%X\n", + cl_hton16(p_ii->lid_range_begin), + cl_hton16(p_ntc->issuer_lid), + cl_hton16(p_ii->lid_range_end) + ); goto Exit; } } } /* IsGeneric IsGeneric is compulsory and must match the trap */ - if ((p_ii->is_generic && ! ib_notice_is_generic(p_ntc)) || - (!p_ii->is_generic && ib_notice_is_generic(p_ntc))) + if ( (p_ii->is_generic && ! ib_notice_is_generic(p_ntc)) || + (!p_ii->is_generic && ib_notice_is_generic(p_ntc)) ) { - osm_log(p_log, OSM_LOG_DEBUG, - "__match_notice_to_inf_rec: " - "Mismatch by Generic/Vendor\n"); + osm_log( p_log, OSM_LOG_DEBUG, + "__match_notice_to_inf_rec: " + "Mismatch by Generic/Vendor\n" ); goto Exit; } /* Type Type if not 0xFFFF must match */ - if ((p_ii->trap_type != 0xFFFF) && - (cl_ntoh16(p_ii->trap_type) != ib_notice_get_type(p_ntc))) { - osm_log(p_log, OSM_LOG_DEBUG, - "__match_notice_to_inf_rec: " - "Mismatch by Type\n"); + if ( (p_ii->trap_type != 0xFFFF) && + (cl_ntoh16(p_ii->trap_type) != ib_notice_get_type(p_ntc)) ) + { + osm_log( p_log, OSM_LOG_DEBUG, + "__match_notice_to_inf_rec: " + "Mismatch by Type\n" ); goto Exit; } /* based on generic type */ - if (p_ii->is_generic) + if ( p_ii->is_generic ) { /* TrapNumber TrapNumber if not 0xFFFF must match */ - if ((p_ii->g_or_v.generic.trap_num != 0xFFFF) && - (p_ii->g_or_v.generic.trap_num != p_ntc->g_or_v.generic.trap_num)) { - - osm_log(p_log, OSM_LOG_DEBUG, - "__match_notice_to_inf_rec: " - "Mismatch by Trap Num\n"); + if ( (p_ii->g_or_v.generic.trap_num != 0xFFFF) && + (p_ii->g_or_v.generic.trap_num != p_ntc->g_or_v.generic.trap_num) ) + { + osm_log( p_log, OSM_LOG_DEBUG, + "__match_notice_to_inf_rec: " + "Mismatch by Trap Num\n" ); goto Exit; } /* ProducerType ProducerType match or 0xFFFFFF */ - if ((cl_ntoh32(ib_inform_info_get_node_type(p_ii)) != 0xFFFFFF) && - (ib_inform_info_get_node_type(p_ii) != ib_notice_get_prod_type(p_ntc))) { - osm_log(p_log, OSM_LOG_DEBUG, - "__match_notice_to_inf_rec: " - "Mismatch by Node Type: II=0x%06X Trap=0x%06X\n", - cl_ntoh32(ib_inform_info_get_node_type(p_ii)), - cl_ntoh32(ib_notice_get_prod_type(p_ntc)) - ); + if ( (cl_ntoh32(ib_inform_info_get_node_type(p_ii)) != 0xFFFFFF) && + (ib_inform_info_get_node_type(p_ii) != ib_notice_get_prod_type(p_ntc)) ) + { + osm_log( p_log, OSM_LOG_DEBUG, + "__match_notice_to_inf_rec: " + "Mismatch by Node Type: II=0x%06X Trap=0x%06X\n", + cl_ntoh32(ib_inform_info_get_node_type(p_ii)), + cl_ntoh32(ib_notice_get_prod_type(p_ntc)) + ); goto Exit; } } else { /* DeviceId DeviceID if not 0xFFFF must match */ - if ((p_ii->g_or_v.vend.dev_id != 0xFFFF) && - (p_ii->g_or_v.vend.dev_id != p_ntc->g_or_v.vend.dev_id)) { - osm_log(p_log, OSM_LOG_DEBUG, - "__match_notice_to_inf_rec: " - "Mismatch by Dev Id\n"); + if ( (p_ii->g_or_v.vend.dev_id != 0xFFFF) && + (p_ii->g_or_v.vend.dev_id != p_ntc->g_or_v.vend.dev_id) ) + { + osm_log( p_log, OSM_LOG_DEBUG, + "__match_notice_to_inf_rec: " + "Mismatch by Dev Id\n" ); goto Exit; } /* VendorID VendorID match or 0xFFFFFF */ - if ((ib_inform_info_get_vend_id(p_ii) != CL_HTON32(0xFFFFFF)) && - (ib_inform_info_get_vend_id(p_ii) != ib_notice_get_vend_id(p_ntc))) { - osm_log(p_log, OSM_LOG_DEBUG, - "__match_notice_to_inf_rec: " - "Mismatch by Vendor ID\n"); - + if ( (ib_inform_info_get_vend_id(p_ii) != CL_HTON32(0xFFFFFF)) && + (ib_inform_info_get_vend_id(p_ii) != ib_notice_get_vend_id(p_ntc)) ) + { + osm_log( p_log, OSM_LOG_DEBUG, + "__match_notice_to_inf_rec: " + "Mismatch by Vendor ID\n" ); goto Exit; } } - /* Check if there is a pkey match. o13-17.1.1*/ + /* Check if there is a pkey match. o13-17.1.1 */ /* Check if the issuer of the trap is the SM. If it is, then the gid comparison should be done on the trap source (saved as the gid in the data details field). If the issuer gid is not the SM - then it is the guid of the trap - source. */ + source */ if ( (cl_ntoh64(p_ntc->issuer_gid.unicast.prefix) == p_subn->opt.subnet_prefix) && (cl_ntoh64(p_ntc->issuer_gid.unicast.interface_id) == p_subn->sm_port_guid) ) { /* The issuer is the SM then this is trap 64-67 - compare the gid - with the gid saved on the data details. */ + with the gid saved on the data details */ source_gid = p_ntc->data_details.ntc_64_67.gid; } else @@ -571,10 +617,10 @@ __match_notice_to_inf_rec( if( p_src_port == (osm_port_t*)cl_qmap_end( &(p_subn->port_guid_tbl)) ) { - osm_log(p_log, OSM_LOG_INFO, - "__match_notice_to_inf_rec: " - "Cannot find source port with GUID:0x%016" PRIx64 "\n", - cl_ntoh64(source_gid.unicast.interface_id) ); + osm_log( p_log, OSM_LOG_INFO, + "__match_notice_to_inf_rec: " + "Cannot find source port with GUID:0x%016" PRIx64 "\n", + cl_ntoh64(source_gid.unicast.interface_id) ); goto Exit; } @@ -583,59 +629,58 @@ __match_notice_to_inf_rec( cl_ntoh16(p_infr_rec->report_addr.dest_lid) ); if( !p_dest_port ) { - osm_log(p_log, OSM_LOG_INFO, - "__match_notice_to_inf_rec: " - "Cannot find destination port with LID:0x%04x\n", - cl_ntoh16(p_infr_rec->report_addr.dest_lid) ); + osm_log( p_log, OSM_LOG_INFO, + "__match_notice_to_inf_rec: " + "Cannot find destination port with LID:0x%04x\n", + cl_ntoh16(p_infr_rec->report_addr.dest_lid) ); goto Exit; } if (osm_port_share_pkey( p_log, p_src_port, p_dest_port ) == FALSE ) { - osm_log(p_log, OSM_LOG_DEBUG, - "__match_notice_to_inf_rec: " - "Mismatch by Pkey\n"); + osm_log( p_log, OSM_LOG_DEBUG, + "__match_notice_to_inf_rec: " + "Mismatch by Pkey\n" ); /* According to o13-17.1.2 - If this informInfo does not have lid_range_begin of 0xFFFF, then this informInfo request - should be removed from database. */ - if (p_ii->lid_range_begin != 0xFFFF) + should be removed from database */ + if ( p_ii->lid_range_begin != 0xFFFF ) { - osm_log(p_log, OSM_LOG_VERBOSE, - "__match_notice_to_inf_rec: " - "Pkey mismatch on lid_range_begin != 0xFFFF. " - "Need to remove this informInfo from db.\n"); - /* add the informInfo record to the remove_infr list. */ - cl_list_insert_tail( p_infr_to_remove_list, - p_infr_rec ); + osm_log( p_log, OSM_LOG_VERBOSE, + "__match_notice_to_inf_rec: " + "Pkey mismatch on lid_range_begin != 0xFFFF. " + "Need to remove this informInfo from db\n" ); + /* add the informInfo record to the remove_infr list */ + cl_list_insert_tail( p_infr_to_remove_list, p_infr_rec ); } goto Exit; } /* send the report to the address provided in the inform record */ - osm_log(p_log, OSM_LOG_DEBUG, - "__match_notice_to_inf_rec: " - "MATCH! Sending Report...\n"); - osm_send_report(p_infr_rec, p_ntc); + osm_log( p_log, OSM_LOG_DEBUG, + "__match_notice_to_inf_rec: " + "MATCH! Sending Report...\n" ); + __osm_send_report( p_infr_rec, p_ntc ); status = CL_SUCCESS; + Exit: OSM_LOG_EXIT( p_log ); } /********************************************************************** - * Once a Trap was received by the osm_trap_rcv, or a Trap sourced in - * the SM was sent (Traps 64-67) this routine is called with a copy of + * Once a Trap was received by osm_trap_rcv, or a Trap sourced by + * the SM was sent (Traps 64-67), this routine is called with a copy of * the notice data. * Given a notice attribute - compare and see if it matches the InformInfo - * Element and if it does - call the Report(Notice) for the + * element and if it does - call the Report(Notice) for the * target QP registered by the address stored in the InformInfo element **********************************************************************/ ib_api_status_t osm_report_notice( IN osm_log_t* const p_log, IN osm_subn_t* p_subn, - IN ib_mad_notice_attr_t *p_ntc - ) { - + IN ib_mad_notice_attr_t *p_ntc ) +{ osm_infr_match_ctxt_t context; cl_list_t infr_to_remove_list; osm_infr_t* p_infr_rec; @@ -644,20 +689,20 @@ osm_report_notice( OSM_LOG_ENTER( p_log, osm_report_notice ); /* - * we must make sure we are ready for this ... + * we must make sure we are ready for this... * note that the trap receivers might be initialized before * the osm_infr_init call is performed. */ - if (p_subn->sa_infr_list.state != CL_INITIALIZED) + if ( p_subn->sa_infr_list.state != CL_INITIALIZED ) { osm_log( p_log, OSM_LOG_DEBUG, "osm_report_notice: " - "Ignoring Notice Reports since Inform List is not initialized yet!\n"); + "Ignoring Notice Reports since Inform List is not initialized yet!\n" ); return IB_ERROR; } /* an official Event information log */ - if (ib_notice_is_generic(p_ntc)) + if ( ib_notice_is_generic(p_ntc) ) { osm_log( p_log, OSM_LOG_INFO, "osm_report_notice: " @@ -701,7 +746,7 @@ osm_report_notice( &context ); /* If we inserted items into the infr_to_remove_list - we need to - remove them. */ + remove them */ p_infr_rec = (osm_infr_t*)cl_list_remove_head(&infr_to_remove_list); while ( p_infr_rec != NULL ) { @@ -715,3 +760,4 @@ osm_report_notice( return(IB_SUCCESS); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_lid_mgr.c b/trunk/ulp/opensm/user/opensm/osm_lid_mgr.c index 86322511..9217ea00 100644 --- a/trunk/ulp/opensm/user/opensm/osm_lid_mgr.c +++ b/trunk/ulp/opensm/user/opensm/osm_lid_mgr.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -31,6 +31,7 @@ * $Id$ */ + /* * Abstract: * Implementation of osm_lid_mgr_t. @@ -39,7 +40,7 @@ * * DATA STRUCTURES: * p_subn->port_lid_tbl : a vector pointing from lid to its port. - * osm db guid2lid domain : a hash from guid to lid (min lid) + * osm db guid2lid domain : a hash from guid to lid (min lid). * p_subn->port_guid_tbl : a map from guid to discovered port obj. * * ALGORITHM: @@ -50,7 +51,7 @@ * 0.2 if the port info has a lid and that range is empty in * port_lid_tbl, return 0 and update the port_lid_tbl and * guid2lid - * 0.3 else find an empty space in port_lid_tbl, update the + * 0.3 else find an empty space in port_lid_tbl, update the * port_lid_tbl and guid2lid, return 1 to flag a change required. * * 1. During initialization: @@ -66,7 +67,7 @@ * 2.4 set the port info * * 3. During all other ports lid assignment: - * 3.1 go through all ports in the subnet. + * 3.1 go through all ports in the subnet * 3.1.1 call __osm_lid_mgr_get_port_min_lid * 3.1.2 if a change required send the port info * 3.2 if any change send the signal PENDING... @@ -79,21 +80,19 @@ * $Revision: 1.15 $ */ -/* - Next available error code: 0x403 -*/ - #if HAVE_CONFIG_H # include #endif /* HAVE_CONFIG_H */ +#include +#include #include -#include #include #include #include #include #include +#include #include #include #include @@ -115,7 +114,7 @@ void osm_lid_mgr_construct( IN osm_lid_mgr_t* const p_mgr ) { - cl_memclr( p_mgr, sizeof(*p_mgr) ); + memset( p_mgr, 0, sizeof(*p_mgr) ); cl_ptr_vector_construct( &p_mgr->used_lids ); } @@ -133,7 +132,7 @@ osm_lid_mgr_destroy( p_item = cl_qlist_remove_head( &p_mgr->free_ranges ); while ( p_item != cl_qlist_end( &p_mgr->free_ranges ) ) { - cl_free((osm_lid_mgr_range_t *)p_item); + free((osm_lid_mgr_range_t *)p_item); p_item = cl_qlist_remove_head( &p_mgr->free_ranges ); } OSM_LOG_EXIT( p_mgr->p_log ); @@ -144,7 +143,7 @@ Validate the guid to lid data by making sure that under the current LMC we did not get duplicates. If we do flag them as errors and remove the entry. **********************************************************************/ -void +static void __osm_lid_mgr_validate_db( IN osm_lid_mgr_t* p_mgr) { @@ -160,7 +159,6 @@ __osm_lid_mgr_validate_db( if (p_mgr->p_subn->opt.lmc) lmc_mask = ~((1 << p_mgr->p_subn->opt.lmc) - 1); - else lmc_mask = 0xffff; @@ -214,7 +212,7 @@ __osm_lid_mgr_validate_db( } else { - /* check if the lids were not previously assigend */ + /* check if the lids were not previously assigned */ for (lid = min_lid; lid <= max_lid; lid++) { if (( cl_ptr_vector_get_size( &p_mgr->used_lids ) > lid ) && @@ -296,7 +294,7 @@ osm_lid_mgr_init( cl_ptr_vector_init( &p_mgr->used_lids, 100, 40 ); cl_qlist_init( &p_mgr->free_ranges ); - /* we use the stored guid to lid table if not forced to re-assign */ + /* we use the stored guid to lid table if not forced to reassign */ if (!p_mgr->p_subn->opt.reassign_lids) { if (osm_db_restore(p_mgr->p_g2l)) @@ -304,15 +302,15 @@ osm_lid_mgr_init( if (p_subn->opt.exit_on_fatal) { osm_log( p_mgr->p_log, OSM_LOG_SYS, - "Fatal: Error restoring Guid-to-Lid persistent database\n" ); + "FATAL: Error restoring Guid-to-Lid persistent database\n" ); status = IB_ERROR; goto Exit; } else { - osm_log( p_mgr->p_log, OSM_LOG_ERROR, - "osm_lid_mgr_init: ERR 0317: " - "Error restoring Guid-to-Lid persistent database\n"); + osm_log( p_mgr->p_log, OSM_LOG_ERROR, + "osm_lid_mgr_init: ERR 0317: " + "Error restoring Guid-to-Lid persistent database\n"); } } @@ -326,13 +324,23 @@ Exit: return( status ); } +static uint16_t +__osm_trim_lid( + IN uint16_t lid ) +{ + if ((lid > IB_LID_UCAST_END_HO) || + (lid < IB_LID_UCAST_START_HO)) + return 0; + return lid; +} + /********************************************************************** initialize the manager for a new sweep: scans the known persistent assignment and port_lid_tbl re-calculate all empty ranges. cleanup invalid port_lid_tbl entries **********************************************************************/ -int +static int __osm_lid_mgr_init_sweep( IN osm_lid_mgr_t* const p_mgr ) { @@ -387,7 +395,7 @@ __osm_lid_mgr_init_sweep( if (osm_db_restore(p_mgr->p_g2l)) osm_log( p_mgr->p_log, OSM_LOG_ERROR, "osm_lid_mgr_init_sweep: ERR 0306: " - "Error restoring Guid-to-Lid persistant database. Ignoring it\n"); + "Error restoring Guid-to-Lid persistent database. Ignoring it\n"); } } @@ -395,7 +403,7 @@ __osm_lid_mgr_init_sweep( p_item = cl_qlist_remove_head( &p_mgr->free_ranges ); while ( p_item != cl_qlist_end( &p_mgr->free_ranges ) ) { - cl_free( (osm_lid_mgr_range_t *)p_item ); + free( (osm_lid_mgr_range_t *)p_item ); p_item = cl_qlist_remove_head( &p_mgr->free_ranges ); } @@ -403,7 +411,7 @@ __osm_lid_mgr_init_sweep( for (lid = 0; lid < cl_ptr_vector_get_size(p_discovered_vec); lid++) cl_ptr_vector_set(p_discovered_vec, lid, NULL); - /* we if are in the first sweep and in re-assign lids mode + /* we if are in the first sweep and in reassign lids mode we should ignore all the available info and simply define one huge empty range */ if ((p_mgr->p_subn->first_time_master_sweep == TRUE) && @@ -413,7 +421,7 @@ __osm_lid_mgr_init_sweep( "__osm_lid_mgr_init_sweep: " "Skipping all lids as we are reassigning them\n"); p_range = - (osm_lid_mgr_range_t *)cl_malloc(sizeof(osm_lid_mgr_range_t)); + (osm_lid_mgr_range_t *)malloc(sizeof(osm_lid_mgr_range_t)); p_range->min_lid = 1; goto AfterScanningLids; } @@ -426,6 +434,8 @@ __osm_lid_mgr_init_sweep( p_port = (osm_port_t*)cl_qmap_next( &p_port->map_item ) ) { osm_port_get_lid_range_ho(p_port, &disc_min_lid, &disc_max_lid); + disc_min_lid = __osm_trim_lid(disc_min_lid); + disc_max_lid = __osm_trim_lid(disc_max_lid); for (lid = disc_min_lid; lid <= disc_max_lid; lid++) cl_ptr_vector_set(p_discovered_vec, lid, p_port ); /* make sure the guid2lid entry is valid. If not, clean it. */ @@ -433,8 +443,8 @@ __osm_lid_mgr_init_sweep( cl_ntoh64(osm_port_get_guid(p_port)), &db_min_lid, &db_max_lid)) { - if ( osm_node_get_type( osm_port_get_parent_node( p_port ) ) != - IB_NODE_TYPE_SWITCH) + if ( !p_port->p_node->sw || + osm_switch_sp0_is_lmc_capable(p_port->p_node->sw, p_mgr->p_subn)) num_lids = lmc_num_lids; else num_lids = 1; @@ -532,53 +542,53 @@ __osm_lid_mgr_init_sweep( /* get the lid range of that port, and the required number of lids we are about to assign to it */ osm_port_get_lid_range_ho(p_port, &disc_min_lid, &disc_max_lid); - if ( osm_node_get_type( osm_port_get_parent_node( p_port ) ) != - IB_NODE_TYPE_SWITCH) + if ( !p_port->p_node->sw || + osm_switch_sp0_is_lmc_capable(p_port->p_node->sw, p_mgr->p_subn)) { disc_max_lid = disc_min_lid + lmc_num_lids - 1; num_lids = lmc_num_lids; - } - else - { - num_lids = 1; } + else + num_lids = 1; + /* Make sure the lid is aligned */ if ((num_lids != 1) && ((disc_min_lid & lmc_mask) != disc_min_lid)) { /* The lid cannot be used */ - osm_log( p_mgr->p_log, OSM_LOG_DEBUG, - "__osm_lid_mgr_init_sweep: " + osm_log( p_mgr->p_log, OSM_LOG_DEBUG, + "__osm_lid_mgr_init_sweep: " "0x%04x is free as it was discovered " "but not aligned\n", lid ); - } - else - { + } + else + { /* check that all needed lids are not persistently mapped */ is_free = FALSE; for ( req_lid = disc_min_lid + 1 ; req_lid <= disc_max_lid ; req_lid++ ) { - if ((req_lid <= max_persistent_lid) && cl_ptr_vector_get(p_persistent_vec, req_lid)) - { - osm_log( p_mgr->p_log, OSM_LOG_DEBUG, - "__osm_lid_mgr_init_sweep: " - "0x%04x is free as it was discovered " - "but mapped\n", - lid); - is_free = TRUE; - break; - } - } - if (is_free == FALSE) - { + if ((req_lid <= max_persistent_lid) && cl_ptr_vector_get(p_persistent_vec, req_lid)) + { + osm_log( p_mgr->p_log, OSM_LOG_DEBUG, + "__osm_lid_mgr_init_sweep: " + "0x%04x is free as it was discovered " + "but mapped\n", + lid ); + is_free = TRUE; + break; + } + } + + if (is_free == FALSE) + { /* This port will use its local lid, and consume the entire required lid range. Thus we can skip that range. */ /* If the disc_max_lid is greater then lid, we can skip right to it, since we've done all neccessary checks on the lids in between. */ if (disc_max_lid > lid) lid = disc_max_lid; - } - } + } + } } } } @@ -592,7 +602,7 @@ __osm_lid_mgr_init_sweep( else { p_range = - (osm_lid_mgr_range_t *)cl_malloc(sizeof(osm_lid_mgr_range_t)); + (osm_lid_mgr_range_t *)malloc(sizeof(osm_lid_mgr_range_t)); p_range->min_lid = lid; p_range->max_lid = lid; } @@ -618,12 +628,12 @@ __osm_lid_mgr_init_sweep( if (!p_range) { p_range = - (osm_lid_mgr_range_t *)cl_malloc(sizeof(osm_lid_mgr_range_t)); + (osm_lid_mgr_range_t *)malloc(sizeof(osm_lid_mgr_range_t)); /* The p_range can be NULL in one of 2 cases: 1. If max_defined_lid == 0. In this case, we want the entire range. - 2. If all lids discovered in the loop where mapped. In this case - no free range exists, and we want to define it after the last + 2. If all lids discovered in the loop where mapped. In this case, + no free range exists and we want to define it after the last mapped lid. */ p_range->min_lid = lid; @@ -633,7 +643,7 @@ __osm_lid_mgr_init_sweep( osm_log( p_mgr->p_log, OSM_LOG_DEBUG, "__osm_lid_mgr_init_sweep: " "final free lid range [0x%x:0x%x]\n", - p_range->min_lid, p_range->max_lid); + p_range->min_lid, p_range->max_lid ); OSM_LOG_EXIT( p_mgr->p_log ); return status; @@ -753,22 +763,24 @@ __osm_lid_mgr_find_free_lid_range( /* if we run out of lids, give an error and abort! */ osm_log( p_mgr->p_log, OSM_LOG_ERROR, "__osm_lid_mgr_find_free_lid_range: ERR 0307: " - "OPENSM RAN OUT OF LIDS!!!\n"); + "OPENSM RAN OUT OF LIDS!!!\n" ); CL_ASSERT( 0 ); } /********************************************************************** **********************************************************************/ -void - __osm_lid_mgr_cleanup_discovered_port_lid_range( - IN osm_lid_mgr_t* p_mgr, - IN osm_port_t *p_port ) +static void +__osm_lid_mgr_cleanup_discovered_port_lid_range( + IN osm_lid_mgr_t* p_mgr, + IN osm_port_t *p_port ) { cl_ptr_vector_t *p_discovered_vec = &p_mgr->p_subn->port_lid_tbl; uint16_t lid, min_lid, max_lid; uint16_t max_tbl_lid = (uint16_t)(cl_ptr_vector_get_size( p_discovered_vec )); osm_port_get_lid_range_ho(p_port, &min_lid, &max_lid); + min_lid = __osm_trim_lid(min_lid); + max_lid = __osm_trim_lid(max_lid); for (lid = min_lid; lid <= max_lid; lid++) { if ((lid < max_tbl_lid ) && @@ -785,7 +797,7 @@ void 0.3 else find an empty space in port_lid_tbl, update the port_lid_tbl and guid2lid, return 1 to flag a change required. **********************************************************************/ -int +static int __osm_lid_mgr_get_port_lid( IN osm_lid_mgr_t* const p_mgr, IN osm_port_t * const p_port, @@ -808,9 +820,9 @@ __osm_lid_mgr_get_port_lid( /* get the lid from the guid2lid */ guid = cl_ntoh64( osm_port_get_guid( p_port ) ); - /* if the port is a switch then we only need one lid */ - if( osm_node_get_type( osm_port_get_parent_node( p_port ) ) == - IB_NODE_TYPE_SWITCH ) + /* if the port is a base switch port 0 then we only need one lid */ + if( p_port->p_node->sw && + !osm_switch_sp0_is_lmc_capable(p_port->p_node->sw, p_mgr->p_subn)) num_lids = 1; /* if the port matches the guid2lid */ @@ -823,7 +835,7 @@ __osm_lid_mgr_get_port_lid( osm_log( p_mgr->p_log, OSM_LOG_DEBUG, "__osm_lid_mgr_get_port_lid: " "0x%016" PRIx64" matches its known lid:0x%04x\n", - guid, min_lid); + guid, min_lid ); goto Exit; } else @@ -844,7 +856,7 @@ __osm_lid_mgr_get_port_lid( osm_log( p_mgr->p_log, OSM_LOG_DEBUG, "__osm_lid_mgr_get_port_lid: " "0x%016" PRIx64" has no persistent lid assigned\n", - guid); + guid ); } /* if the port info carries a lid it must be lmc aligned and not mapped @@ -852,7 +864,7 @@ __osm_lid_mgr_get_port_lid( min_lid = cl_ntoh16(osm_port_get_base_lid(p_port)); /* we want to ignore the discovered lid if we are also on first sweep of - re-assign lids flow */ + reassign lids flow */ if (min_lid && ! ((p_mgr->p_subn->first_time_master_sweep == TRUE) && (p_mgr->p_subn->opt.reassign_lids == TRUE ))) @@ -868,7 +880,7 @@ __osm_lid_mgr_get_port_lid( osm_log( p_mgr->p_log, OSM_LOG_DEBUG, "__osm_lid_mgr_get_port_lid: " "0x%016" PRIx64" lid range:[0x%x-0x%x] is free\n", - guid, *p_min_lid, *p_max_lid); + guid, *p_min_lid, *p_max_lid ); goto NewLidSet; } else @@ -877,7 +889,7 @@ __osm_lid_mgr_get_port_lid( "__osm_lid_mgr_get_port_lid: " "0x%016" PRIx64 " existing lid range:[0x%x:0x%x] is not free\n", - guid, min_lid, min_lid + num_lids - 1); + guid, min_lid, min_lid + num_lids - 1 ); } } else @@ -886,7 +898,7 @@ __osm_lid_mgr_get_port_lid( "__osm_lid_mgr_get_port_lid: " "0x%016" PRIx64 " existing lid range:[0x%x:0x%x] is not lmc aligned\n", - guid, min_lid, min_lid + num_lids - 1); + guid, min_lid, min_lid + num_lids - 1 ); } } @@ -898,7 +910,7 @@ __osm_lid_mgr_get_port_lid( osm_log( p_mgr->p_log, OSM_LOG_DEBUG, "__osm_lid_mgr_get_port_lid: " "0x%016" PRIx64" assigned a new lid range:[0x%x-0x%x]\n", - guid, *p_min_lid, *p_max_lid); + guid, *p_min_lid, *p_max_lid ); lid_changed = 1; NewLidSet: @@ -943,10 +955,10 @@ __osm_lid_mgr_set_remote_pi_state_to_init( **********************************************************************/ static boolean_t __osm_lid_mgr_set_physp_pi( - IN osm_lid_mgr_t * const p_mgr, - IN osm_port_t* const p_port, - IN osm_physp_t* const p_physp, - IN ib_net16_t const lid ) + IN osm_lid_mgr_t * const p_mgr, + IN osm_port_t* const p_port, + IN osm_physp_t* const p_physp, + IN ib_net16_t const lid ) { uint8_t payload[IB_SMP_DATA_SIZE]; ib_port_info_t* p_pi = (ib_port_info_t*)payload; @@ -975,18 +987,19 @@ __osm_lid_mgr_set_physp_pi( port_num = osm_physp_get_port_num( p_physp ); p_node = osm_physp_get_node_ptr( p_physp ); - if( (osm_node_get_type( p_node ) == IB_NODE_TYPE_SWITCH) && + if( (osm_node_get_type( p_node ) == IB_NODE_TYPE_SWITCH ) && (port_num != 0) ) { /* Switch ports that are not numbered 0 should not be set with the - following attributes set later (during NO_CHANGE state in link mgr). + following attributes as they are set later (during NO_CHANGE state + in link mgr). */ if( osm_log_is_active( p_mgr->p_log, OSM_LOG_DEBUG ) ) { osm_log( p_mgr->p_log, OSM_LOG_DEBUG, "__osm_lid_mgr_set_physp_pi: " - "Skipping switch port %u, GUID = 0x%016" PRIx64 "\n", + "Skipping switch port %u, GUID 0x%016" PRIx64 "\n", port_num, cl_ntoh64( osm_physp_get_port_guid( p_physp ) ) ); } @@ -1006,12 +1019,12 @@ __osm_lid_mgr_set_physp_pi( Third, send the SMP to this physical port. */ - cl_memclr( payload, IB_SMP_DATA_SIZE ); + memset( payload, 0, IB_SMP_DATA_SIZE ); /* Correction by FUJITSU */ if( port_num != 0 ) { - cl_memcpy( payload, p_old_pi, sizeof(ib_port_info_t) ); + memcpy( payload, p_old_pi, sizeof(ib_port_info_t) ); } /* @@ -1045,36 +1058,36 @@ __osm_lid_mgr_set_physp_pi( p_pi->m_key = p_mgr->p_subn->opt.m_key; /* Check to see if the value we are setting is different than the value in the port_info. If it is, turn on send_set flag */ - if (cl_memcmp( &p_pi->m_key, &p_old_pi->m_key, sizeof(p_pi->m_key) )) + if (memcmp( &p_pi->m_key, &p_old_pi->m_key, sizeof(p_pi->m_key) )) send_set = TRUE; p_pi->subnet_prefix = p_mgr->p_subn->opt.subnet_prefix; /* Check to see if the value we are setting is different than the value in the port_info. If it is, turn on send_set flag */ - if (cl_memcmp( &p_pi->subnet_prefix, &p_old_pi->subnet_prefix, - sizeof(p_pi->subnet_prefix) )) + if (memcmp( &p_pi->subnet_prefix, &p_old_pi->subnet_prefix, + sizeof(p_pi->subnet_prefix) )) send_set = TRUE; p_pi->base_lid = lid; /* Check to see if the value we are setting is different than the value in the port_info. If it is, turn on send_set flag */ - if (cl_memcmp( &p_pi->base_lid, &p_old_pi->base_lid, - sizeof(p_pi->base_lid) )) + if (memcmp( &p_pi->base_lid, &p_old_pi->base_lid, + sizeof(p_pi->base_lid) )) send_set = TRUE; /* we are updating the ports with our local sm_base_lid */ p_pi->master_sm_base_lid = p_mgr->p_subn->sm_base_lid; /* Check to see if the value we are setting is different than the value in the port_info. If it is, turn on send_set flag */ - if (cl_memcmp( &p_pi->master_sm_base_lid, &p_old_pi->master_sm_base_lid, - sizeof(p_pi->master_sm_base_lid) )) + if (memcmp( &p_pi->master_sm_base_lid, &p_old_pi->master_sm_base_lid, + sizeof(p_pi->master_sm_base_lid) )) send_set = TRUE; p_pi->m_key_lease_period = p_mgr->p_subn->opt.m_key_lease_period; /* Check to see if the value we are setting is different than the value in the port_info. If it is, turn on send_set flag */ - if (cl_memcmp( &p_pi->m_key_lease_period, &p_old_pi->m_key_lease_period, - sizeof(p_pi->m_key_lease_period) )) + if (memcmp( &p_pi->m_key_lease_period, &p_old_pi->m_key_lease_period, + sizeof(p_pi->m_key_lease_period) )) send_set = TRUE; /* @@ -1097,21 +1110,31 @@ __osm_lid_mgr_set_physp_pi( p_pi->link_width_enabled = p_old_pi->link_width_supported; /* Check to see if the value we are setting is different than the value in the port_info. If it is, turn on send_set flag */ - if (cl_memcmp( &p_pi->link_width_enabled, &p_old_pi->link_width_enabled, - sizeof(p_pi->link_width_enabled) )) + if (memcmp( &p_pi->link_width_enabled, &p_old_pi->link_width_enabled, + sizeof(p_pi->link_width_enabled) )) + send_set = TRUE; + + if ( p_mgr->p_subn->opt.force_link_speed ) + ib_port_info_set_link_speed_enabled( p_pi, IB_LINK_SPEED_ACTIVE_2_5 ); + else if (ib_port_info_get_link_speed_enabled( p_old_pi ) != ib_port_info_get_link_speed_sup( p_pi )) + ib_port_info_set_link_speed_enabled( p_pi, IB_PORT_LINK_SPEED_ENABLED_MASK ); + else + ib_port_info_set_link_speed_enabled( p_pi, ib_port_info_get_link_speed_enabled( p_old_pi )); + if (memcmp( &p_pi->link_speed, &p_old_pi->link_speed, + sizeof(p_pi->link_speed) )) send_set = TRUE; /* M_KeyProtectBits are always zero */ p_pi->mkey_lmc = p_mgr->p_subn->opt.lmc; /* Check to see if the value we are setting is different than the value in the port_info. If it is, turn on send_set flag */ - if (cl_memcmp( &p_pi->mkey_lmc, &p_old_pi->mkey_lmc, sizeof(p_pi->mkey_lmc) )) + if (memcmp( &p_pi->mkey_lmc, &p_old_pi->mkey_lmc, sizeof(p_pi->mkey_lmc) )) send_set = TRUE; /* calc new op_vls and mtu */ op_vls = osm_physp_calc_link_op_vls( p_mgr->p_log, p_mgr->p_subn, p_physp ); - mtu = osm_physp_calc_link_mtu(p_mgr->p_log, p_physp ); + mtu = osm_physp_calc_link_mtu( p_mgr->p_log, p_physp ); ib_port_info_set_neighbor_mtu( p_pi, mtu ); @@ -1132,15 +1155,15 @@ __osm_lid_mgr_set_physp_pi( p_mgr->p_subn->opt.local_phy_errors_threshold, p_mgr->p_subn->opt.overrun_errors_threshold); - if (cl_memcmp( &p_pi->error_threshold, &p_old_pi->error_threshold, - sizeof(p_pi->error_threshold) )) + if (memcmp( &p_pi->error_threshold, &p_old_pi->error_threshold, + sizeof(p_pi->error_threshold) )) send_set = TRUE; /* To reset the port state machine we can send PortInfo.State = DOWN. - (see: 7.2.7 p161 lines:10-19.) + (see: 7.2.7 p171 lines:10-19) */ - if ( (mtu != ib_port_info_get_neighbor_mtu( p_old_pi )) || + if ( (mtu != ib_port_info_get_neighbor_mtu(p_old_pi)) || (op_vls != ib_port_info_get_op_vls(p_old_pi))) { if( osm_log_is_active( p_mgr->p_log, OSM_LOG_DEBUG ) ) @@ -1148,7 +1171,7 @@ __osm_lid_mgr_set_physp_pi( osm_log( p_mgr->p_log, OSM_LOG_DEBUG, "__osm_lid_mgr_set_physp_pi: " "Sending Link Down due to op_vls or mtu change. MTU:%u,%u VL_CAP:%u,%u\n", - mtu, ib_port_info_get_mtu_cap( p_old_pi ), + mtu, ib_port_info_get_neighbor_mtu(p_old_pi), op_vls, ib_port_info_get_op_vls(p_old_pi) ); } @@ -1169,7 +1192,7 @@ __osm_lid_mgr_set_physp_pi( { /* For Port 0, NeighborMTU is relevant only for Enh. SP0. - In this case we'll set the MTU according to the mtu_cap + In this case, we'll set the MTU according to the mtu_cap */ ib_port_info_set_neighbor_mtu( p_pi, ib_port_info_get_mtu_cap( p_old_pi ) ); if ( ib_port_info_get_neighbor_mtu(p_pi) != @@ -1178,8 +1201,19 @@ __osm_lid_mgr_set_physp_pi( osm_log( p_mgr->p_log, OSM_LOG_DEBUG, "__osm_lid_mgr_set_physp_pi: " - "Updating neighbor_mtu on sw. port 0 to:%u\n", + "Updating neighbor_mtu on switch port 0 to:%u\n", ib_port_info_get_neighbor_mtu( p_pi ) ); + + /* Determine if enhanced switch port 0 and if so set LMC */ + if (osm_switch_sp0_is_lmc_capable(p_node->sw, p_mgr->p_subn)) + { + /* M_KeyProtectBits are always zero */ + p_pi->mkey_lmc = p_mgr->p_subn->opt.lmc; + /* Check to see if the value we are setting is different than + the value in the port_info. If it is, turn on send_set flag */ + if (memcmp( &p_pi->mkey_lmc, &p_old_pi->mkey_lmc, sizeof(p_pi->mkey_lmc) )) + send_set = TRUE; + } } context.pi_context.node_guid = osm_node_get_node_guid( p_node ); @@ -1188,6 +1222,7 @@ __osm_lid_mgr_set_physp_pi( context.pi_context.update_master_sm_base_lid = FALSE; context.pi_context.ignore_errors = FALSE; context.pi_context.light_sweep = FALSE; + context.pi_context.active_transition = FALSE; /* We need to set the cli_rereg bit when we are in first_time_master_sweep for @@ -1204,6 +1239,7 @@ __osm_lid_mgr_set_physp_pi( if ( ( p_mgr->p_subn->first_time_master_sweep == TRUE || new_port == TRUE ) && + !p_mgr->p_subn->opt.no_clients_rereg && ( (p_old_pi->capability_mask & IB_PORT_CAP_HAS_CLIENT_REREG) != 0 ) ) ib_port_info_set_client_rereg( p_pi, 1 ); else @@ -1265,7 +1301,7 @@ __osm_lid_mgr_process_our_sm_node( { osm_log( p_mgr->p_log, OSM_LOG_ERROR, "__osm_lid_mgr_process_our_sm_node: ERR 0308: " - "Can't acquire SM's Port object, GUID = 0x%016" PRIx64 "\n", + "Can't acquire SM's port object, GUID 0x%016" PRIx64 "\n", cl_ntoh64( p_mgr->p_subn->sm_port_guid ) ); res = FALSE; goto Exit; @@ -1334,9 +1370,9 @@ osm_lid_mgr_process_sm( { osm_log( p_mgr->p_log, OSM_LOG_VERBOSE, "osm_lid_mgr_process_sm: " - "Invoking UI function pfn_ui_pre_lid_assign\n"); + "Invoking UI function pfn_ui_pre_lid_assign\n" ); p_mgr->p_subn->opt.pfn_ui_pre_lid_assign( - p_mgr->p_subn->opt.ui_pre_lid_assign_ctx); + p_mgr->p_subn->opt.ui_pre_lid_assign_ctx ); } /* Set the send_set_reqs of the p_mgr to FALSE, and @@ -1447,3 +1483,4 @@ osm_lid_mgr_process_subnet( OSM_LOG_EXIT( p_mgr->p_log ); return( signal ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_lin_fwd_rcv.c b/trunk/ulp/opensm/user/opensm/osm_lin_fwd_rcv.c index b358cec7..70e9673d 100644 --- a/trunk/ulp/opensm/user/opensm/osm_lin_fwd_rcv.c +++ b/trunk/ulp/opensm/user/opensm/osm_lin_fwd_rcv.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Implementation of osm_lft_rcv_t. @@ -44,15 +45,11 @@ * $Revision: 1.5 $ */ -/* - Next available error code: 0x403 -*/ - #if HAVE_CONFIG_H # include #endif /* HAVE_CONFIG_H */ -#include +#include #include #include #include @@ -63,7 +60,7 @@ void osm_lft_rcv_construct( IN osm_lft_rcv_t* const p_rcv ) { - cl_memclr( p_rcv, sizeof(*p_rcv) ); + memset( p_rcv, 0, sizeof(*p_rcv) ); } /********************************************************************** @@ -109,7 +106,6 @@ osm_lft_rcv_process( IN const osm_lft_rcv_t* const p_rcv, IN osm_madw_t* const p_madw ) { - cl_qmap_t *p_sw_tbl; ib_smp_t *p_smp; uint32_t block_num; osm_switch_t *p_sw; @@ -124,7 +120,6 @@ osm_lft_rcv_process( CL_ASSERT( p_madw ); - p_sw_tbl = &p_rcv->p_subn->sw_guid_tbl; p_smp = osm_madw_get_smp_ptr( p_madw ); p_block = (uint8_t*)ib_smp_get_payload_ptr( p_smp ); block_num = cl_ntoh32( p_smp->attr_mod ); @@ -136,9 +131,9 @@ osm_lft_rcv_process( node_guid = p_lft_context->node_guid; CL_PLOCK_EXCL_ACQUIRE( p_rcv->p_lock ); - p_sw = (osm_switch_t*)cl_qmap_get( p_sw_tbl, node_guid ); + p_sw = osm_get_switch_by_guid( p_rcv->p_subn, node_guid ); - if( p_sw == (osm_switch_t*)cl_qmap_end( p_sw_tbl ) ) + if( !p_sw ) { osm_log( p_rcv->p_log, OSM_LOG_ERROR, "osm_lft_rcv_process: ERR 0401: " @@ -162,3 +157,4 @@ osm_lft_rcv_process( CL_PLOCK_RELEASE( p_rcv->p_lock ); OSM_LOG_EXIT( p_rcv->p_log ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_lin_fwd_rcv_ctrl.c b/trunk/ulp/opensm/user/opensm/osm_lin_fwd_rcv_ctrl.c index b6285fb7..b3071b60 100644 --- a/trunk/ulp/opensm/user/opensm/osm_lin_fwd_rcv_ctrl.c +++ b/trunk/ulp/opensm/user/opensm/osm_lin_fwd_rcv_ctrl.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Implementation of osm_lft_rcv_ctrl_t. @@ -48,7 +49,7 @@ # include #endif /* HAVE_CONFIG_H */ -#include +#include #include #include @@ -70,7 +71,7 @@ void osm_lft_rcv_ctrl_construct( IN osm_lft_rcv_ctrl_t* const p_ctrl ) { - cl_memclr( p_ctrl, sizeof(*p_ctrl) ); + memset( p_ctrl, 0, sizeof(*p_ctrl) ); p_ctrl->h_disp = CL_DISP_INVALID_HANDLE; } @@ -121,3 +122,4 @@ osm_lft_rcv_ctrl_init( OSM_LOG_EXIT( p_log ); return( status ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_lin_fwd_tbl.c b/trunk/ulp/opensm/user/opensm/osm_lin_fwd_tbl.c index 75e94d2d..9a8d8034 100644 --- a/trunk/ulp/opensm/user/opensm/osm_lin_fwd_tbl.c +++ b/trunk/ulp/opensm/user/opensm/osm_lin_fwd_tbl.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Implementation of osm_lin_fwd_tbl_t. @@ -48,7 +49,8 @@ # include #endif /* HAVE_CONFIG_H */ -#include +#include +#include #include #include #include @@ -74,13 +76,13 @@ osm_lin_tbl_new( so add 1 to the end of the range here for this assert. */ CL_ASSERT( size <= IB_LID_UCAST_END_HO + 1 ); - p_tbl = (osm_lin_fwd_tbl_t*)cl_malloc( + p_tbl = (osm_lin_fwd_tbl_t*)malloc( __osm_lin_tbl_compute_obj_size( size ) ); /* Initialize the table to OSM_NO_PATH, which means "invalid port" */ - cl_memset( p_tbl, OSM_NO_PATH, __osm_lin_tbl_compute_obj_size( size ) ); + memset( p_tbl, OSM_NO_PATH, __osm_lin_tbl_compute_obj_size( size ) ); if( p_tbl != NULL ) { p_tbl->size = (uint16_t)size; @@ -94,6 +96,7 @@ void osm_lin_tbl_delete( IN osm_lin_fwd_tbl_t** const pp_tbl ) { - cl_free( *pp_tbl ); + free( *pp_tbl ); *pp_tbl = NULL; } + diff --git a/trunk/ulp/opensm/user/opensm/osm_link_mgr.c b/trunk/ulp/opensm/user/opensm/osm_link_mgr.c index d0bc8c90..4eddf18c 100644 --- a/trunk/ulp/opensm/user/opensm/osm_link_mgr.c +++ b/trunk/ulp/opensm/user/opensm/osm_link_mgr.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Implementation of osm_link_mgr_t. @@ -47,8 +48,8 @@ # include #endif /* HAVE_CONFIG_H */ +#include #include -#include #include #include #include @@ -63,7 +64,7 @@ void osm_link_mgr_construct( IN osm_link_mgr_t* const p_mgr ) { - cl_memclr( p_mgr, sizeof(*p_mgr) ); + memset( p_mgr, 0, sizeof(*p_mgr) ); } /********************************************************************** @@ -108,8 +109,8 @@ osm_link_mgr_init( /********************************************************************** **********************************************************************/ -void -osm_link_mgr_set_physp_pi( +static void +__osm_link_mgr_set_physp_pi( IN osm_link_mgr_t* const p_mgr, IN osm_physp_t* const p_physp, IN uint8_t const port_state ) @@ -123,10 +124,11 @@ osm_link_mgr_set_physp_pi( uint8_t port_num; uint8_t mtu; uint8_t op_vls; + boolean_t esp0 = FALSE; boolean_t send_set = FALSE; osm_physp_t *p_remote_physp; - OSM_LOG_ENTER( p_mgr->p_log, osm_link_mgr_set_physp_pi ); + OSM_LOG_ENTER( p_mgr->p_log, __osm_link_mgr_set_physp_pi ); CL_ASSERT( p_physp ); CL_ASSERT( osm_physp_is_valid( p_physp ) ); @@ -137,50 +139,49 @@ osm_link_mgr_set_physp_pi( if( port_num == 0 ) { - osm_switch_t *p_switch; ib_switch_info_t* p_sw_info; + /* HCA's don't have a port 0, and for switch port 0, we need to check if this is enhanced port 0 or base port 0. - For base port 0 the following parameters are not valid. (p734, table132) + For base port 0 the following parameters are not valid. (p824, table 145) */ - p_switch = osm_get_switch_by_guid( p_mgr->p_subn, p_node->node_info.node_guid ); - if (! p_switch ) + if (!p_node->sw) { osm_log( p_mgr->p_log, OSM_LOG_ERROR, - "osm_link_mgr_set_physp_pi: ERR 4201: " + "__osm_link_mgr_set_physp_pi: ERR 4201: " "Cannot find switch by guid: 0x%" PRIx64 "\n", cl_ntoh64( p_node->node_info.node_guid ) ); goto Exit; } - p_sw_info = osm_switch_get_si_ptr( p_switch ); - if (ib_switch_info_is_enhanced_port_0( p_sw_info ) == FALSE) + p_sw_info = osm_switch_get_si_ptr(p_node->sw); + if (ib_switch_info_is_enhanced_port0( p_sw_info ) == FALSE) { /* This means the switch doesn't support enhanced port zero. Can skip it. */ if( osm_log_is_active( p_mgr->p_log, OSM_LOG_DEBUG ) ) { osm_log( p_mgr->p_log, OSM_LOG_DEBUG, - "osm_link_mgr_set_physp_pi: " - "Skipping port 0, GUID = 0x%016" PRIx64 "\n", + "__osm_link_mgr_set_physp_pi: " + "Skipping port 0, GUID 0x%016" PRIx64 "\n", cl_ntoh64( osm_physp_get_port_guid( p_physp ) ) ); } goto Exit; } + esp0 = TRUE; } /* PAST THIS POINT WE ARE HANDLING EITHER A NON PORT 0 OR ENHANCED PORT 0 */ - p_node = osm_physp_get_node_ptr( p_physp ); p_old_pi = osm_physp_get_port_info_ptr( p_physp ); - cl_memclr( payload, IB_SMP_DATA_SIZE ); + memset( payload, 0, IB_SMP_DATA_SIZE ); /* Correction by FUJITSU */ - cl_memcpy( payload, p_old_pi, sizeof(ib_port_info_t) ); + memcpy( payload, p_old_pi, sizeof(ib_port_info_t) ); /* Correction following a bug injected by the previous @@ -203,37 +204,45 @@ osm_link_mgr_set_physp_pi( /* we only change port fields if we do not change state */ if (port_state == IB_LINK_NO_CHANGE) { - /* The following fields are relevant only for CA port or Enh.SP0 */ + /* The following fields are relevant only for CA port or Enh. SP0 */ if( osm_node_get_type( p_node ) != IB_NODE_TYPE_SWITCH || port_num == 0 ) { p_pi->m_key = p_mgr->p_subn->opt.m_key; - if (cl_memcmp( &p_pi->m_key, &p_old_pi->m_key, sizeof(p_pi->m_key) )) + if (memcmp( &p_pi->m_key, &p_old_pi->m_key, sizeof(p_pi->m_key) )) send_set = TRUE; p_pi->subnet_prefix = p_mgr->p_subn->opt.subnet_prefix; - if (cl_memcmp( &p_pi->subnet_prefix, &p_old_pi->subnet_prefix, - sizeof(p_pi->subnet_prefix) )) + if (memcmp( &p_pi->subnet_prefix, &p_old_pi->subnet_prefix, + sizeof(p_pi->subnet_prefix) )) send_set = TRUE; p_pi->base_lid = osm_physp_get_base_lid( p_physp ); - if (cl_memcmp( &p_pi->base_lid, &p_old_pi->base_lid, - sizeof(p_pi->base_lid) )) + if (memcmp( &p_pi->base_lid, &p_old_pi->base_lid, + sizeof(p_pi->base_lid) )) send_set = TRUE; - /* we are initializing the ports with our local sm_base_lid */ + /* we are initializing the ports with our local sm_base_lid */ p_pi->master_sm_base_lid = p_mgr->p_subn->sm_base_lid; - if (cl_memcmp( &p_pi->master_sm_base_lid, &p_old_pi->master_sm_base_lid, - sizeof(p_pi->master_sm_base_lid) )) + if (memcmp( &p_pi->master_sm_base_lid, &p_old_pi->master_sm_base_lid, + sizeof(p_pi->master_sm_base_lid) )) send_set = TRUE; p_pi->m_key_lease_period = p_mgr->p_subn->opt.m_key_lease_period; - if (cl_memcmp( &p_pi->m_key_lease_period, &p_old_pi->m_key_lease_period, - sizeof(p_pi->m_key_lease_period) )) + if (memcmp( &p_pi->m_key_lease_period, &p_old_pi->m_key_lease_period, + sizeof(p_pi->m_key_lease_period) )) send_set = TRUE; - p_pi->mkey_lmc = p_mgr->p_subn->opt.lmc; - if (cl_memcmp( &p_pi->mkey_lmc, &p_old_pi->mkey_lmc, sizeof(p_pi->mkey_lmc) )) + if (esp0 == FALSE) + p_pi->mkey_lmc = p_mgr->p_subn->opt.lmc; + else + { + if (p_mgr->p_subn->opt.lmc_esp0) + p_pi->mkey_lmc = p_mgr->p_subn->opt.lmc; + else + p_pi->mkey_lmc = 0; + } + if (memcmp( &p_pi->mkey_lmc, &p_old_pi->mkey_lmc, sizeof(p_pi->mkey_lmc) )) send_set = TRUE; ib_port_info_set_timeout( p_pi, p_mgr->p_subn->opt.subnet_timeout ); @@ -245,34 +254,47 @@ osm_link_mgr_set_physp_pi( Several timeout mechanisms: */ p_remote_physp = osm_physp_get_remote( p_physp ); - - if (p_remote_physp && - osm_physp_is_valid(p_remote_physp) && - (osm_node_get_type( osm_physp_get_node_ptr(p_remote_physp) ) != - IB_NODE_TYPE_SWITCH)) - { - /* we drive an HCA port so we need to set stall-count to 1 and - use leaf hoq value */ - ib_port_info_set_hoq_lifetime( - p_pi, p_mgr->p_subn->opt.leaf_head_of_queue_lifetime); - ib_port_info_set_vl_stall_count( - p_pi, OSM_DEFAULT_LEAF_VL_STALL_COUNT); - } - else - { - ib_port_info_set_hoq_lifetime( - p_pi, p_mgr->p_subn->opt.head_of_queue_lifetime); + if (port_num != 0 && p_remote_physp && + osm_physp_is_valid(p_remote_physp)) { + if (osm_node_get_type(osm_physp_get_node_ptr(p_physp)) == + IB_NODE_TYPE_ROUTER) + { + ib_port_info_set_hoq_lifetime( + p_pi, p_mgr->p_subn->opt.leaf_head_of_queue_lifetime); + } + else if (osm_node_get_type(osm_physp_get_node_ptr(p_physp)) == + IB_NODE_TYPE_SWITCH) + { + /* Is remote end CA or router (a leaf port) ? */ + if (osm_node_get_type(osm_physp_get_node_ptr(p_remote_physp)) != + IB_NODE_TYPE_SWITCH) + { + ib_port_info_set_hoq_lifetime( + p_pi, p_mgr->p_subn->opt.leaf_head_of_queue_lifetime); + ib_port_info_set_vl_stall_count( + p_pi, p_mgr->p_subn->opt.leaf_vl_stall_count); + } + else + { + ib_port_info_set_hoq_lifetime( + p_pi, p_mgr->p_subn->opt.head_of_queue_lifetime); + ib_port_info_set_vl_stall_count( + p_pi, p_mgr->p_subn->opt.vl_stall_count); + } + } + if ( ib_port_info_get_hoq_lifetime(p_pi) != + ib_port_info_get_hoq_lifetime(p_old_pi) || + ib_port_info_get_vl_stall_count(p_pi) != + ib_port_info_get_vl_stall_count(p_old_pi) ) + send_set = TRUE; } - if ( ib_port_info_get_hoq_lifetime(p_pi) != - ib_port_info_get_hoq_lifetime(p_old_pi) ) - send_set = TRUE; ib_port_info_set_phy_and_overrun_err_thd( p_pi, p_mgr->p_subn->opt.local_phy_errors_threshold, p_mgr->p_subn->opt.overrun_errors_threshold); - if (cl_memcmp( &p_pi->error_threshold, &p_old_pi->error_threshold, - sizeof(p_pi->error_threshold) )) + if (memcmp( &p_pi->error_threshold, &p_old_pi->error_threshold, + sizeof(p_pi->error_threshold) )) send_set = TRUE; /* @@ -280,14 +302,24 @@ osm_link_mgr_set_physp_pi( then determine the neighbor MTU. */ p_pi->link_width_enabled = p_old_pi->link_width_supported; - if (cl_memcmp( &p_pi->link_width_enabled, &p_old_pi->link_width_enabled, - sizeof(p_pi->link_width_enabled) )) + if (memcmp( &p_pi->link_width_enabled, &p_old_pi->link_width_enabled, + sizeof(p_pi->link_width_enabled) )) + send_set = TRUE; + + if ( p_mgr->p_subn->opt.force_link_speed ) + ib_port_info_set_link_speed_enabled( p_pi, IB_LINK_SPEED_ACTIVE_2_5 ); + else if (ib_port_info_get_link_speed_enabled( p_old_pi ) != ib_port_info_get_link_speed_sup( p_pi )) + ib_port_info_set_link_speed_enabled( p_pi, IB_PORT_LINK_SPEED_ENABLED_MASK ); + else + ib_port_info_set_link_speed_enabled( p_pi, ib_port_info_get_link_speed_enabled( p_old_pi )); + if (memcmp( &p_pi->link_speed, &p_old_pi->link_speed, + sizeof(p_pi->link_speed) )) send_set = TRUE; /* calc new op_vls and mtu */ op_vls = - osm_physp_calc_link_op_vls(p_mgr->p_log, p_mgr->p_subn, p_physp ); - mtu = osm_physp_calc_link_mtu(p_mgr->p_log, p_physp ); + osm_physp_calc_link_op_vls( p_mgr->p_log, p_mgr->p_subn, p_physp ); + mtu = osm_physp_calc_link_mtu( p_mgr->p_log, p_physp ); ib_port_info_set_neighbor_mtu( p_pi, mtu ); if ( ib_port_info_get_neighbor_mtu(p_pi) != @@ -306,7 +338,7 @@ osm_link_mgr_set_physp_pi( { /* Since the only change we try to do is to modify the port - state we can ignore the errors that might becaused by a + state we can ignore the errors that might be caused by a race in setting the state and the actual state the port is in. */ @@ -317,7 +349,13 @@ osm_link_mgr_set_physp_pi( if (port_state != IB_LINK_NO_CHANGE && ib_port_info_get_port_state(p_pi) != ib_port_info_get_port_state(p_old_pi) ) + { send_set = TRUE; + if (port_state == IB_LINK_ACTIVE) + context.pi_context.active_transition = TRUE; + else + context.pi_context.active_transition = FALSE; + } context.pi_context.node_guid = osm_node_get_node_guid( p_node ); context.pi_context.port_guid = osm_physp_get_port_guid( p_physp ); @@ -329,15 +367,15 @@ osm_link_mgr_set_physp_pi( in the following cases: 1. There is a change in the values (send_set == TRUE) 2. This is an hca port or a switch port zero and got_set_resp is FALSE - (in this case we sent a PortInfoSet in the osm_lid_mgr, but for some reason we - didn't get a response) - try and re-send. + (in this case we sent a PortInfoSet in the osm_lid_mgr, but for some + reason we didn't get a response) - try and re-send. 3. This is a switch port and: a. first_time_master_sweep flag on the subnet is TRUE. This means the SM just became master, and it then needs to send at PortInfoSet to - every port (and this is the first time we can send a PortInfoSet to switch - external ports). - b. got_set_resp on the physical port is FALSE. This means we haven't seen - this port before - need to send PortInfoSet to it. + every port (and this is the first time we can send a PortInfoSet to + switch external ports). + b. got_set_resp on the physical port is FALSE. This means we haven't + seen this port before - need to send PortInfoSet to it. */ if (send_set || (osm_node_get_type(p_node) != IB_NODE_TYPE_SWITCH && p_physp->got_set_resp == FALSE) || @@ -363,7 +401,7 @@ osm_link_mgr_set_physp_pi( /********************************************************************** **********************************************************************/ -osm_signal_t +static osm_signal_t __osm_link_mgr_process_port( IN osm_link_mgr_t* const p_mgr, IN osm_port_t* const p_port, @@ -416,7 +454,7 @@ __osm_link_mgr_process_port( (current_state < link_state) ) { p_mgr->send_set_reqs = FALSE; - osm_link_mgr_set_physp_pi( + __osm_link_mgr_set_physp_pi( p_mgr, p_physp, link_state ); @@ -473,3 +511,4 @@ osm_link_mgr_process( OSM_LOG_EXIT( p_mgr->p_log ); return( signal ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_matrix.c b/trunk/ulp/opensm/user/opensm/osm_matrix.c index 26763e82..8fb8e128 100644 --- a/trunk/ulp/opensm/user/opensm/osm_matrix.c +++ b/trunk/ulp/opensm/user/opensm/osm_matrix.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -47,9 +47,9 @@ # include #endif /* HAVE_CONFIG_H */ +#include #include - /********************************************************************** **********************************************************************/ void @@ -69,7 +69,7 @@ __osm_lid_matrix_vec_init( { osm_lid_matrix_t* const p_lmx = (osm_lid_matrix_t*)context; - cl_memset( p_elem, OSM_NO_PATH, p_lmx->num_ports + 1); + memset( p_elem, OSM_NO_PATH, p_lmx->num_ports + 1); return( CL_SUCCESS ); } @@ -85,7 +85,7 @@ __osm_lid_matrix_vec_clear( osm_lid_matrix_t* const p_lmx = (osm_lid_matrix_t*)context; UNUSED_PARAM( index ); - cl_memset( p_elem, OSM_NO_PATH, p_lmx->num_ports + 1); + memset( p_elem, OSM_NO_PATH, p_lmx->num_ports + 1); } /********************************************************************** @@ -153,3 +153,4 @@ osm_lid_matrix_set( } return( status ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_mcast_fwd_rcv.c b/trunk/ulp/opensm/user/opensm/osm_mcast_fwd_rcv.c index abe35ab7..54f9dba7 100644 --- a/trunk/ulp/opensm/user/opensm/osm_mcast_fwd_rcv.c +++ b/trunk/ulp/opensm/user/opensm/osm_mcast_fwd_rcv.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -48,8 +48,8 @@ # include #endif /* HAVE_CONFIG_H */ +#include #include -#include #include #include #include @@ -65,7 +65,7 @@ void osm_mft_rcv_construct( IN osm_mft_rcv_t* const p_rcv ) { - cl_memclr( p_rcv, sizeof(*p_rcv) ); + memset( p_rcv, 0, sizeof(*p_rcv) ); } /********************************************************************** @@ -111,7 +111,6 @@ osm_mft_rcv_process( IN const osm_mft_rcv_t* const p_rcv, IN osm_madw_t* const p_madw ) { - cl_qmap_t *p_sw_tbl; ib_smp_t *p_smp; uint32_t block_num; uint8_t position; @@ -127,7 +126,6 @@ osm_mft_rcv_process( CL_ASSERT( p_madw ); - p_sw_tbl = &p_rcv->p_subn->sw_guid_tbl; p_smp = osm_madw_get_smp_ptr( p_madw ); p_block = (uint16_t*)ib_smp_get_payload_ptr( p_smp ); block_num = cl_ntoh32( p_smp->attr_mod ) & IB_MCAST_BLOCK_ID_MASK_HO; @@ -151,13 +149,13 @@ osm_mft_rcv_process( } CL_PLOCK_EXCL_ACQUIRE( p_rcv->p_lock ); - p_sw = (osm_switch_t*)cl_qmap_get( p_sw_tbl, node_guid ); + p_sw = osm_get_switch_by_guid( p_rcv->p_subn, node_guid ); - if( p_sw == (osm_switch_t*)cl_qmap_end( p_sw_tbl ) ) + if( !p_sw ) { osm_log( p_rcv->p_log, OSM_LOG_ERROR, "osm_mft_rcv_process: ERR 0801: " - "LFT received for nonexistent node " + "MFT received for nonexistent node " "0x%016" PRIx64 "\n", cl_ntoh64( node_guid ) ); } else @@ -168,9 +166,9 @@ osm_mft_rcv_process( { osm_log( p_rcv->p_log, OSM_LOG_ERROR, "osm_mft_rcv_process: ERR 0802: " - "Setting forwarding table block failed (%s)" + "Setting MFT block failed (%s)" "\n\t\t\t\tSwitch 0x%016" PRIx64 - ", block_num = %u, position = %u\n", + ", block %u, position %u\n", ib_get_err_str( status ), cl_ntoh64( node_guid ), block_num, position ); @@ -180,3 +178,4 @@ osm_mft_rcv_process( CL_PLOCK_RELEASE( p_rcv->p_lock ); OSM_LOG_EXIT( p_rcv->p_log ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_mcast_fwd_rcv_ctrl.c b/trunk/ulp/opensm/user/opensm/osm_mcast_fwd_rcv_ctrl.c index 832914a9..0a492180 100644 --- a/trunk/ulp/opensm/user/opensm/osm_mcast_fwd_rcv_ctrl.c +++ b/trunk/ulp/opensm/user/opensm/osm_mcast_fwd_rcv_ctrl.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -48,7 +48,7 @@ # include #endif /* HAVE_CONFIG_H */ -#include +#include #include #include @@ -70,7 +70,7 @@ void osm_mft_rcv_ctrl_construct( IN osm_mft_rcv_ctrl_t* const p_ctrl ) { - cl_memclr( p_ctrl, sizeof(*p_ctrl) ); + memset( p_ctrl, 0, sizeof(*p_ctrl) ); p_ctrl->h_disp = CL_DISP_INVALID_HANDLE; } @@ -122,3 +122,4 @@ osm_mft_rcv_ctrl_init( return( status ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_mcast_mgr.c b/trunk/ulp/opensm/user/opensm/osm_mcast_mgr.c index fffb8e60..b40b64dc 100644 --- a/trunk/ulp/opensm/user/opensm/osm_mcast_mgr.c +++ b/trunk/ulp/opensm/user/opensm/osm_mcast_mgr.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Implementation of osm_mcast_mgr_t. @@ -47,8 +48,11 @@ # include #endif /* HAVE_CONFIG_H */ +#include +#include +#include +#include #include -#include #include #include #include @@ -65,7 +69,6 @@ typedef struct _osm_mcast_work_obj { cl_list_item_t list_item; osm_port_t* p_port; - } osm_mcast_work_obj_t; /********************************************************************** @@ -84,9 +87,12 @@ __osm_mcast_work_obj_new( qlist. see cl_qlist_insert_tail(): CL_ASSERT(p_list_item->p_list != p_list) */ - p_obj = cl_zalloc( sizeof( *p_obj ) ); + p_obj = malloc( sizeof( *p_obj ) ); if( p_obj ) + { + memset( p_obj, 0, sizeof( *p_obj ) ); p_obj->p_port = (osm_port_t*)p_port; + } return( p_obj ); } @@ -97,13 +103,13 @@ static void __osm_mcast_work_obj_delete( IN osm_mcast_work_obj_t* p_wobj ) { - cl_free( p_wobj ); + free( p_wobj ); } /********************************************************************** Recursively remove nodes from the tree **********************************************************************/ -void +static void __osm_mcast_mgr_purge_tree_node( IN osm_mtree_node_t* p_mtn ) { @@ -119,7 +125,7 @@ __osm_mcast_mgr_purge_tree_node( } - cl_free( p_mtn ); + free( p_mtn ); } /********************************************************************** @@ -141,7 +147,7 @@ __osm_mcast_mgr_purge_tree( /********************************************************************** **********************************************************************/ -float +static float osm_mcast_mgr_compute_avg_hops( osm_mcast_mgr_t* const p_mgr, const osm_mgrp_t* const p_mgrp, @@ -208,7 +214,7 @@ osm_mcast_mgr_compute_avg_hops( Calculate the maximal "min hops" from the given switch to any of the group HCAs **********************************************************************/ -float +static float osm_mcast_mgr_compute_max_hops( osm_mcast_mgr_t* const p_mgr, const osm_mgrp_t* const p_mgrp, @@ -246,7 +252,7 @@ osm_mcast_mgr_compute_max_hops( if( p_port == (osm_port_t*)cl_qmap_end( p_port_tbl ) ) { osm_log( p_mgr->p_log, OSM_LOG_ERROR, - "osm_mcast_mgr_compute_max_hops: ERR 0A18: " + "osm_mcast_mgr_compute_max_hops: ERR 0A1A: " "No port object for port 0x%016" PRIx64 "\n", cl_ntoh64( ib_gid_get_guid( &p_mcm_port->port_gid ) ) ); continue; @@ -382,7 +388,7 @@ void osm_mcast_mgr_construct( IN osm_mcast_mgr_t* const p_mgr ) { - cl_memclr( p_mgr, sizeof(*p_mgr) ); + memset( p_mgr, 0, sizeof(*p_mgr) ); } /********************************************************************** @@ -497,7 +503,7 @@ __osm_mcast_mgr_set_tbl( { osm_log( p_mgr->p_log, OSM_LOG_ERROR, "__osm_mcast_mgr_set_tbl: ERR 0A02: " - "Sending linear fwd. tbl. block failed (%s)\n", + "Sending multicast fwd. tbl. block failed (%s)\n", ib_get_err_str( status ) ); } @@ -539,7 +545,7 @@ __osm_mcast_mgr_subdivide( mlid_ho = cl_ntoh16( osm_mgrp_get_mlid( p_mgrp ) ); /* - For Multicast Groups we want to not count on previous + For Multicast Groups, we want not to count on previous configurations - since we can easily generate a storm by loops. */ @@ -585,10 +591,9 @@ __osm_mcast_mgr_subdivide( osm_log( p_mgr->p_log, OSM_LOG_ERROR, "__osm_mcast_mgr_subdivide: ERR 0A04: " - "Error routing MLID 0x%X through switch " - "0x%" PRIx64 "\n" - "\t\t\t\tNo multicast paths from this switch " - "to port with LID 0x%X\n", + "Error routing MLID 0x%X through switch 0x%" PRIx64 "\n" + "\t\t\t\tNo multicast paths from this switch to port " + "with LID 0x%X\n", mlid_ho, node_guid_ho, lid_ho ); __osm_mcast_work_obj_delete( p_wobj ); @@ -630,7 +635,7 @@ __osm_mcast_mgr_purge_list( /********************************************************************** This is the recursive function to compute the paths in the spanning - tree that eminate from this switch. On input, the p_list contains + tree that emanate from this switch. On input, the p_list contains the group members that must be routed from this switch. The function returns the newly created mtree node element. @@ -649,7 +654,6 @@ __osm_mcast_mgr_branch( osm_mtree_node_t* p_mtn = NULL; cl_qlist_t* list_array = NULL; uint8_t i; - cl_qmap_t* p_sw_guid_tbl; ib_net64_t node_guid; uint64_t node_guid_ho; osm_mcast_work_obj_t* p_wobj; @@ -724,8 +728,6 @@ __osm_mcast_mgr_branch( goto Exit; } - p_sw_guid_tbl = &p_mgr->p_subn->sw_guid_tbl; - max_children = osm_mtree_node_get_max_children( p_mtn ); CL_ASSERT( max_children > 1 ); @@ -735,7 +737,7 @@ __osm_mcast_mgr_branch( TO DO - this list array could probably be moved inside the switch element to save on malloc thrashing. */ - list_array = cl_zalloc( sizeof(cl_qlist_t) * max_children ); + list_array = malloc( sizeof(cl_qlist_t) * max_children ); if( list_array == NULL ) { osm_log( p_mgr->p_log, OSM_LOG_ERROR, @@ -745,6 +747,8 @@ __osm_mcast_mgr_branch( goto Exit; } + memset( list_array, 0, sizeof(cl_qlist_t) * max_children ); + for( i = 0; i < max_children; i++ ) cl_qlist_init( &list_array[i] ); @@ -780,11 +784,10 @@ __osm_mcast_mgr_branch( for( i = 0; i < max_children; i++ ) { - const osm_physp_t *p_physp; - const osm_physp_t *p_remote_physp; + const osm_physp_t *p_physp; + const osm_physp_t *p_remote_physp; const osm_node_t *p_node; const osm_node_t *p_remote_node; - osm_switch_t *p_remote_sw; p_port_list = &list_array[i]; @@ -803,7 +806,7 @@ __osm_mcast_mgr_branch( { osm_log( p_mgr->p_log, OSM_LOG_DEBUG, "__osm_mcast_mgr_branch: " - "Routing %u destination(s) via switch port 0x%X\n", + "Routing %zu destination(s) via switch port 0x%X\n", count, i ); } @@ -827,9 +830,7 @@ __osm_mcast_mgr_branch( /* Acquire a pointer to the remote switch then recurse. */ - p_remote_sw = (osm_switch_t*)cl_qmap_get( - p_sw_guid_tbl, osm_node_get_node_guid( p_remote_node ) ); - CL_ASSERT( p_remote_sw ); + CL_ASSERT( p_remote_node->sw ); p_physp = osm_node_get_physp_ptr( p_node, i ); CL_ASSERT( p_physp ); @@ -840,7 +841,7 @@ __osm_mcast_mgr_branch( CL_ASSERT( osm_physp_is_valid( p_remote_physp ) ); p_mtn->child_array[i] = __osm_mcast_mgr_branch( - p_mgr, p_mgrp, p_remote_sw, + p_mgr, p_mgrp, p_remote_node->sw, p_port_list, depth, osm_physp_get_port_num( p_remote_physp), p_max_depth ); @@ -872,7 +873,7 @@ __osm_mcast_mgr_branch( } } - cl_free( list_array ); + free( list_array ); Exit: OSM_LOG_EXIT( p_mgr->p_log ); return( p_mtn ); @@ -1001,6 +1002,7 @@ __osm_mcast_mgr_build_spanning_tree( OSM_LOG_EXIT( p_mgr->p_log ); return( status ); } + #if 0 /* unused */ /********************************************************************** @@ -1066,7 +1068,7 @@ __osm_mcast_mgr_clear( IN osm_mgrp_t* const p_mgrp ) { osm_switch_t* p_sw; - cl_qmap_t* p_tbl; + cl_qmap_t* p_sw_tbl; osm_mcast_tbl_t* p_mcast_tbl; OSM_LOG_ENTER( p_mgr->p_log, __osm_mcast_mgr_clear ); @@ -1075,9 +1077,9 @@ __osm_mcast_mgr_clear( Walk the switches and clear the routing entries for this MLID. */ - p_tbl = &p_mgr->p_subn->sw_guid_tbl; - p_sw = (osm_switch_t*)cl_qmap_head( p_tbl ); - while( p_sw != (osm_switch_t*)cl_qmap_end( p_tbl ) ) + p_sw_tbl = &p_mgr->p_subn->sw_guid_tbl; + p_sw = (osm_switch_t*)cl_qmap_head( p_sw_tbl ); + while( p_sw != (osm_switch_t*)cl_qmap_end( p_sw_tbl ) ) { p_mcast_tbl = osm_switch_get_mcast_tbl_ptr( p_sw ); osm_mcast_tbl_clear_mlid( p_mcast_tbl, cl_ntoh16(p_mgrp->mlid) ); @@ -1094,21 +1096,20 @@ __osm_mcast_mgr_clear( **********************************************************************/ ib_api_status_t osm_mcast_mgr_process_single( - IN osm_mcast_mgr_t* const p_mgr, + IN osm_mcast_mgr_t* const p_mgr, IN ib_net16_t const mlid, IN ib_net64_t const port_guid, IN uint8_t const join_state ) { uint8_t port_num; - uint16_t mlid_ho; + uint16_t mlid_ho; osm_switch_t* p_sw; ib_net64_t sw_guid; osm_port_t* p_port; - osm_physp_t* p_physp; - osm_physp_t* p_remote_physp; + osm_physp_t* p_physp; + osm_physp_t* p_remote_physp; osm_node_t* p_remote_node; cl_qmap_t* p_port_tbl; - cl_qmap_t* p_sw_tbl; osm_mcast_tbl_t* p_mcast_tbl; ib_api_status_t status = IB_SUCCESS; @@ -1118,10 +1119,9 @@ osm_mcast_mgr_process_single( CL_ASSERT( port_guid ); p_port_tbl = &p_mgr->p_subn->port_guid_tbl; - p_sw_tbl = &p_mgr->p_subn->sw_guid_tbl; mlid_ho = cl_ntoh16( mlid ); - if( osm_log_is_active( p_mgr->p_log, OSM_LOG_VERBOSE ) ) + if( osm_log_is_active( p_mgr->p_log, OSM_LOG_DEBUG ) ) { osm_log( p_mgr->p_log, OSM_LOG_DEBUG, "osm_mcast_mgr_process_single: " @@ -1205,8 +1205,8 @@ osm_mcast_mgr_process_single( goto Exit; } - p_sw = (osm_switch_t*)cl_qmap_get( p_sw_tbl, sw_guid ); - if( p_sw == (osm_switch_t*)cl_qmap_end( p_sw_tbl ) ) + p_sw = p_remote_node->sw; + if( !p_sw ) { osm_log( p_mgr->p_log, OSM_LOG_ERROR, "osm_mcast_mgr_process_single: ERR 0A12: " @@ -1240,7 +1240,7 @@ osm_mcast_mgr_process_single( { if( join_state & IB_JOIN_STATE_SEND_ONLY ) { - if( osm_log_is_active( p_mgr->p_log, OSM_LOG_VERBOSE ) ) + if( osm_log_is_active( p_mgr->p_log, OSM_LOG_DEBUG ) ) { osm_log( p_mgr->p_log, OSM_LOG_DEBUG, "osm_mcast_mgr_process_single: " @@ -1260,7 +1260,7 @@ osm_mcast_mgr_process_single( } else { - if( osm_log_is_active( p_mgr->p_log, OSM_LOG_VERBOSE ) ) + if( osm_log_is_active( p_mgr->p_log, OSM_LOG_DEBUG ) ) { osm_log( p_mgr->p_log, OSM_LOG_DEBUG, "osm_mcast_mgr_process_single: " @@ -1277,7 +1277,7 @@ osm_mcast_mgr_process_single( /********************************************************************** lock must already be held on entry **********************************************************************/ -ib_api_status_t +static ib_api_status_t osm_mcast_mgr_process_tree( IN osm_mcast_mgr_t* const p_mgr, IN osm_mgrp_t* const p_mgrp, @@ -1285,14 +1285,12 @@ osm_mcast_mgr_process_tree( ib_net64_t port_guid ) { ib_api_status_t status = IB_SUCCESS; - cl_qmap_t* p_tbl; ib_net16_t mlid; boolean_t ui_mcast_fdb_assign_func_defined; OSM_LOG_ENTER( p_mgr->p_log, osm_mcast_mgr_process_tree ); mlid = osm_mgrp_get_mlid( p_mgrp ); - p_tbl = &p_mgr->p_subn->sw_guid_tbl; if( osm_log_is_active( p_mgr->p_log, OSM_LOG_DEBUG ) ) { @@ -1368,55 +1366,38 @@ osm_mcast_mgr_process_tree( /********************************************************************** **********************************************************************/ -void -osm_mcast_mgr_dump_mcast_routes( +static void +mcast_mgr_dump_sw_routes( IN const osm_mcast_mgr_t* const p_mgr, - IN const osm_switch_t* const p_sw ) + IN const osm_switch_t* const p_sw, + IN FILE *file ) { osm_mcast_tbl_t* p_tbl; int16_t mlid_ho = 0; int16_t mlid_start_ho; uint8_t position = 0; int16_t block_num = 0; - char line[OSM_REPORT_LINE_SIZE]; - boolean_t print_lid; + boolean_t first_mlid; + boolean_t first_port; const osm_node_t* p_node; - FILE * p_mcfdbFile; uint16_t i, j; uint16_t mask_entry; - char *file_name = NULL; + char sw_hdr[256]; + char mlid_hdr[32]; - OSM_LOG_ENTER( p_mgr->p_log, osm_mcast_mgr_dump_mcast_routes ); + OSM_LOG_ENTER( p_mgr->p_log, mcast_mgr_dump_sw_routes ); if( !osm_log_is_active( p_mgr->p_log, OSM_LOG_ROUTING ) ) goto Exit; - file_name = - (char*)cl_malloc(strlen(p_mgr->p_subn->opt.dump_files_dir) + 12); - - CL_ASSERT(file_name); - - strcpy(file_name, p_mgr->p_subn->opt.dump_files_dir); - strcat(file_name,"/osm.mcfdbs"); - - /* Open the file or error */ - p_mcfdbFile = fopen(file_name, "a"); - if (! p_mcfdbFile) - { - osm_log( p_mgr->p_log, OSM_LOG_ERROR, - "osm_mcast_mgr_dump_mcast_routes: ERR 0A23: " - "Failed to open mcfdb file (%s)\n", - file_name ); - goto Exit; - } - p_node = osm_switch_get_node_ptr( p_sw ); p_tbl = osm_switch_get_mcast_tbl_ptr( p_sw ); - fprintf( p_mcfdbFile, "\nSwitch 0x%016" PRIx64 "\n" + sprintf( sw_hdr, "\nSwitch 0x%016" PRIx64 "\n" "LID : Out Port(s)\n", - cl_ntoh64( osm_node_get_node_guid( p_node ) ) ); + cl_ntoh64( osm_node_get_node_guid( p_node ) ) ); + first_mlid = TRUE; while ( block_num <= p_tbl->max_block_in_use ) { mlid_start_ho = (uint16_t)(block_num * IB_MCAST_BLOCK_SIZE); @@ -1424,8 +1405,8 @@ osm_mcast_mgr_dump_mcast_routes( { mlid_ho = mlid_start_ho + i; position = 0; - print_lid = FALSE; - sprintf( line, "0x%04X :", mlid_ho + IB_LID_MCAST_START_HO ); + first_port = TRUE; + sprintf( mlid_hdr, "0x%04X :", mlid_ho + IB_LID_MCAST_START_HO ); while ( position <= p_tbl->max_position ) { mask_entry = cl_ntoh16((*p_tbl->p_mask_tbl)[mlid_ho][position]); @@ -1434,36 +1415,90 @@ osm_mcast_mgr_dump_mcast_routes( position++; continue; } - print_lid = TRUE; for (j = 0 ; j < 16 ; j++) { if ( (1 << j) & mask_entry ) - sprintf( line, "%s 0x%03X ", line, j+(position*16) ); + { + if (first_mlid) + { + fprintf( file,"%s", sw_hdr ); + first_mlid = FALSE; + } + if (first_port) + { + fprintf( file,"%s", mlid_hdr ); + first_port = FALSE; + } + fprintf( file, " 0x%03X ", j+(position*16) ); + } } position++; } - if (print_lid) + if (first_port == FALSE) { - fprintf( p_mcfdbFile, "%s\n", line ); + fprintf( file, "\n" ); } } block_num++; } - fclose(p_mcfdbFile); - Exit: - if (file_name) - cl_free(file_name); OSM_LOG_EXIT( p_mgr->p_log ); } +/********************************************************************** + **********************************************************************/ +struct mcast_mgr_dump_context { + osm_mcast_mgr_t *p_mgr; + FILE *file; +}; + +static void +mcast_mgr_dump_table(cl_map_item_t *p_map_item, void *context) +{ + osm_switch_t *p_sw = (osm_switch_t *)p_map_item; + struct mcast_mgr_dump_context *cxt = context; + + mcast_mgr_dump_sw_routes(cxt->p_mgr, p_sw, cxt->file); +} + +static void +mcast_mgr_dump_mcast_routes(osm_mcast_mgr_t *p_mgr) +{ + char file_name[1024]; + struct mcast_mgr_dump_context dump_context; + FILE *file; + + if (!osm_log_is_active(p_mgr->p_log, OSM_LOG_ROUTING)) + return; + + snprintf(file_name, sizeof(file_name), "%s/%s", + p_mgr->p_subn->opt.dump_files_dir, "osm.mcfdbs"); + + file = fopen(file_name, "w"); + if (!file) { + osm_log(p_mgr->p_log, OSM_LOG_ERROR, + "mcast_dump_mcast_routes: ERR 0A18: " + "cannot create mcfdb file \'%s\': %s\n", + file_name, strerror(errno)); + return; + } + + dump_context.p_mgr = p_mgr; + dump_context.file = file; + + cl_qmap_apply_func(&p_mgr->p_subn->sw_guid_tbl, + mcast_mgr_dump_table, &dump_context); + + fclose(file); +} + /********************************************************************** Process the entire group. NOTE : The lock should be held externally! **********************************************************************/ -osm_signal_t +static osm_signal_t osm_mcast_mgr_process_mgrp( IN osm_mcast_mgr_t* const p_mgr, IN osm_mgrp_t* const p_mgrp, @@ -1471,14 +1506,14 @@ osm_mcast_mgr_process_mgrp( IN ib_net64_t port_guid ) { osm_signal_t signal = OSM_SIGNAL_DONE; - ib_api_status_t status; - osm_switch_t* p_sw; - cl_qmap_t* p_tbl; + ib_api_status_t status; + osm_switch_t* p_sw; + cl_qmap_t* p_sw_tbl; boolean_t pending_transactions = FALSE; OSM_LOG_ENTER( p_mgr->p_log, osm_mcast_mgr_process_mgrp ); - p_tbl = &p_mgr->p_subn->sw_guid_tbl; + p_sw_tbl = &p_mgr->p_subn->sw_guid_tbl; status = osm_mcast_mgr_process_tree( p_mgr, p_mgrp, req_type, port_guid ); if( status != IB_SUCCESS ) @@ -1491,25 +1526,21 @@ osm_mcast_mgr_process_mgrp( goto Exit; } - /* initialize the mc fdb dump file: */ - if( osm_log_is_active( p_mgr->p_log, OSM_LOG_ROUTING ) ) - unlink("/tmp/osm.mcfdbs"); - /* Walk the switches and download the tables for each. */ - p_sw = (osm_switch_t*)cl_qmap_head( p_tbl ); - while( p_sw != (osm_switch_t*)cl_qmap_end( p_tbl ) ) + p_sw = (osm_switch_t*)cl_qmap_head( p_sw_tbl ); + while( p_sw != (osm_switch_t*)cl_qmap_end( p_sw_tbl ) ) { signal = __osm_mcast_mgr_set_tbl( p_mgr, p_sw ); if( signal == OSM_SIGNAL_DONE_PENDING ) pending_transactions = TRUE; - osm_mcast_mgr_dump_mcast_routes( p_mgr, p_sw ); - p_sw = (osm_switch_t*)cl_qmap_next( &p_sw->map_item ); } + mcast_mgr_dump_mcast_routes( p_mgr ); + Exit: OSM_LOG_EXIT( p_mgr->p_log ); @@ -1527,7 +1558,7 @@ osm_mcast_mgr_process( { osm_signal_t signal; osm_switch_t* p_sw; - cl_qmap_t* p_tbl; + cl_qmap_t* p_sw_tbl; cl_qmap_t* p_mcast_tbl; osm_mgrp_t* p_mgrp; ib_api_status_t status; @@ -1535,7 +1566,7 @@ osm_mcast_mgr_process( OSM_LOG_ENTER( p_mgr->p_log, osm_mcast_mgr_process ); - p_tbl = &p_mgr->p_subn->sw_guid_tbl; + p_sw_tbl = &p_mgr->p_subn->sw_guid_tbl; p_mcast_tbl = &p_mgr->p_subn->mgrp_mlid_tbl; /* @@ -1565,25 +1596,21 @@ osm_mcast_mgr_process( p_mgrp = (osm_mgrp_t*)cl_qmap_next( &p_mgrp->map_item ); } - /* initialize the mc fdb dump file: */ - if( osm_log_is_active( p_mgr->p_log, OSM_LOG_ROUTING ) ) - unlink("/tmp/osm.mcfdbs"); - /* Walk the switches and download the tables for each. */ - p_sw = (osm_switch_t*)cl_qmap_head( p_tbl ); - while( p_sw != (osm_switch_t*)cl_qmap_end( p_tbl ) ) + p_sw = (osm_switch_t*)cl_qmap_head( p_sw_tbl ); + while( p_sw != (osm_switch_t*)cl_qmap_end( p_sw_tbl ) ) { signal = __osm_mcast_mgr_set_tbl( p_mgr, p_sw ); if( signal == OSM_SIGNAL_DONE_PENDING ) pending_transactions = TRUE; - osm_mcast_mgr_dump_mcast_routes( p_mgr, p_sw ); - p_sw = (osm_switch_t*)cl_qmap_next( &p_sw->map_item ); } + mcast_mgr_dump_mcast_routes( p_mgr ); + CL_PLOCK_RELEASE( p_mgr->p_lock ); OSM_LOG_EXIT( p_mgr->p_log ); @@ -1625,7 +1652,7 @@ osm_mcast_mgr_process_mgrp_cb( osm_mcast_mgr_t* p_mgr = (osm_mcast_mgr_t*)Context1; osm_mgrp_t* p_mgrp; ib_net16_t mlid; - osm_signal_t signal; + osm_signal_t signal = OSM_SIGNAL_DONE; osm_mcast_mgr_ctxt_t* p_ctxt = (osm_mcast_mgr_ctxt_t*)Context2; osm_mcast_req_type_t req_type = p_ctxt->req_type; ib_net64_t port_guid = p_ctxt->port_guid; @@ -1633,10 +1660,10 @@ osm_mcast_mgr_process_mgrp_cb( OSM_LOG_ENTER( p_mgr->p_log, osm_mcast_mgr_process_mgrp_cb ); /* nice copy no warning on size diff */ - cl_memcpy(&mlid, &p_ctxt->mlid, sizeof(mlid)); + memcpy(&mlid, &p_ctxt->mlid, sizeof(mlid)); /* we can destroy the context now */ - cl_free(p_ctxt); + free(p_ctxt); /* we need a lock to make sure the p_mgrp is not change other ways */ CL_PLOCK_EXCL_ACQUIRE( p_mgr->p_lock ); @@ -1653,7 +1680,6 @@ osm_mcast_mgr_process_mgrp_cb( */ if ( p_mgrp->last_change_id == p_mgrp->last_tree_id) { - signal = OSM_SIGNAL_DONE; osm_log( p_mgr->p_log, OSM_LOG_DEBUG, "osm_mcast_mgr_process_mgrp_cb: " "Skip processing mgrp with lid:0x%X change id:%u\n", @@ -1691,16 +1717,10 @@ osm_mcast_mgr_process_mgrp_cb( osm_mgrp_destroy(p_mgrp); } - - CL_PLOCK_RELEASE( p_mgr->p_lock ); - OSM_LOG_EXIT( p_mgr->p_log ); - return signal; - } - else - { - CL_PLOCK_RELEASE( p_mgr->p_lock ); - OSM_LOG_EXIT( p_mgr->p_log ); - return OSM_SIGNAL_DONE; } + CL_PLOCK_RELEASE( p_mgr->p_lock ); + OSM_LOG_EXIT( p_mgr->p_log ); + return signal; } + diff --git a/trunk/ulp/opensm/user/opensm/osm_mcast_tbl.c b/trunk/ulp/opensm/user/opensm/osm_mcast_tbl.c index fe388718..bb175802 100644 --- a/trunk/ulp/opensm/user/opensm/osm_mcast_tbl.c +++ b/trunk/ulp/opensm/user/opensm/osm_mcast_tbl.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -48,7 +48,8 @@ # include #endif /* HAVE_CONFIG_H */ -#include +#include +#include #include #include #include @@ -65,7 +66,7 @@ osm_mcast_tbl_init( CL_ASSERT( p_tbl ); CL_ASSERT( num_ports ); - cl_memclr( p_tbl, sizeof(*p_tbl) ); + memset( p_tbl, 0, sizeof(*p_tbl) ); p_tbl->max_block_in_use = -1; @@ -98,12 +99,14 @@ osm_mcast_tbl_init( since it is (and must be) defined that way the table structure in order to create a pointer to a two dimensional array. */ - p_tbl->p_mask_tbl = cl_zalloc( p_tbl->num_entries * - (IB_MCAST_POSITION_MAX + 1) * IB_MCAST_MASK_SIZE / 8 ); + p_tbl->p_mask_tbl = malloc( p_tbl->num_entries * + (IB_MCAST_POSITION_MAX + 1) * IB_MCAST_MASK_SIZE / 8 ); if( p_tbl->p_mask_tbl == NULL ) return( IB_INSUFFICIENT_MEMORY ); + memset(p_tbl->p_mask_tbl, 0, + p_tbl->num_entries * (IB_MCAST_POSITION_MAX + 1) * IB_MCAST_MASK_SIZE / 8 ); return( IB_SUCCESS ); } @@ -113,7 +116,7 @@ void osm_mcast_tbl_destroy( IN osm_mcast_tbl_t* const p_tbl ) { - cl_free( p_tbl->p_mask_tbl ); + free( p_tbl->p_mask_tbl ); } /********************************************************************** @@ -263,7 +266,7 @@ osm_mcast_tbl_clear_mlid( **********************************************************************/ boolean_t osm_mcast_tbl_get_block( - IN osm_mcast_tbl_t* const p_tbl, + IN osm_mcast_tbl_t* const p_tbl, IN int16_t const block_num, IN uint8_t const position, OUT ib_net16_t* const p_block ) @@ -282,7 +285,7 @@ osm_mcast_tbl_get_block( /* Caller shouldn't do this for efficiency's sake... */ - cl_memclr( p_block, IB_SMP_DATA_SIZE ); + memset( p_block, 0, IB_SMP_DATA_SIZE ); return( TRUE ); } @@ -296,3 +299,4 @@ osm_mcast_tbl_get_block( return( TRUE ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_mcm_info.c b/trunk/ulp/opensm/user/opensm/osm_mcm_info.c index aff3831e..47eeb2e6 100644 --- a/trunk/ulp/opensm/user/opensm/osm_mcm_info.c +++ b/trunk/ulp/opensm/user/opensm/osm_mcm_info.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Declaration of osm_mcm_info_t. @@ -48,6 +49,7 @@ # include #endif /* HAVE_CONFIG_H */ +#include #include /********************************************************************** @@ -78,9 +80,10 @@ osm_mcm_info_new( { osm_mcm_info_t* p_mcm; - p_mcm = (osm_mcm_info_t*)cl_zalloc( sizeof(*p_mcm) ); + p_mcm = (osm_mcm_info_t*)malloc( sizeof(*p_mcm) ); if( p_mcm ) { + memset(p_mcm, 0, sizeof(*p_mcm) ); osm_mcm_info_init( p_mcm, mlid ); } @@ -94,6 +97,6 @@ osm_mcm_info_delete( IN osm_mcm_info_t* const p_mcm ) { osm_mcm_info_destroy( p_mcm ); - cl_free( p_mcm ); + free( p_mcm ); } diff --git a/trunk/ulp/opensm/user/opensm/osm_mcm_port.c b/trunk/ulp/opensm/user/opensm/osm_mcm_port.c index edbf1c8d..af15ef4b 100644 --- a/trunk/ulp/opensm/user/opensm/osm_mcm_port.c +++ b/trunk/ulp/opensm/user/opensm/osm_mcm_port.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Implementation of osm_mcm_port_t. @@ -48,6 +49,8 @@ # include #endif /* HAVE_CONFIG_H */ +#include +#include #include /********************************************************************** @@ -56,7 +59,7 @@ void osm_mcm_port_construct( IN osm_mcm_port_t* const p_mcm ) { - cl_memclr( p_mcm, sizeof(*p_mcm) ); + memset( p_mcm, 0, sizeof(*p_mcm) ); } /********************************************************************** @@ -100,7 +103,7 @@ osm_mcm_port_new( { osm_mcm_port_t* p_mcm; - p_mcm = cl_malloc( sizeof(*p_mcm) ); + p_mcm = malloc( sizeof(*p_mcm) ); if( p_mcm ) { osm_mcm_port_init( p_mcm, p_port_gid, @@ -119,5 +122,6 @@ osm_mcm_port_delete( CL_ASSERT( p_mcm ); osm_mcm_port_destroy( p_mcm ); - cl_free( p_mcm ); + free( p_mcm ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_mtree.c b/trunk/ulp/opensm/user/opensm/osm_mtree.c index 89e30e9b..256ec281 100644 --- a/trunk/ulp/opensm/user/opensm/osm_mtree.c +++ b/trunk/ulp/opensm/user/opensm/osm_mtree.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Implementation of osm_mtree_node_t. @@ -47,6 +48,7 @@ # include #endif /* HAVE_CONFIG_H */ +#include #include #include @@ -79,8 +81,8 @@ osm_mtree_node_new( { osm_mtree_node_t *p_mtn; - p_mtn = cl_malloc( sizeof(osm_mtree_node_t) + - sizeof(void*) * (osm_switch_get_num_ports( p_sw ) - 1) ); + p_mtn = malloc( sizeof(osm_mtree_node_t) + + sizeof(void*) * (osm_switch_get_num_ports( p_sw ) - 1) ); if( p_mtn != NULL ) osm_mtree_node_init( p_mtn, p_sw ); @@ -96,7 +98,8 @@ osm_mtree_destroy( { uint32_t i; - if (p_mtn == NULL) return; + if (p_mtn == NULL) + return; if ( p_mtn->child_array != NULL ) for (i = 0 ; i< p_mtn->max_children; i++ ) @@ -104,7 +107,7 @@ osm_mtree_destroy( (p_mtn->child_array[i] != OSM_MTREE_LEAF) ) osm_mtree_destroy(p_mtn->child_array[i]); - cl_free( p_mtn ); + free( p_mtn ); } /********************************************************************** @@ -115,10 +118,11 @@ __osm_mtree_dump( { uint32_t i; - if (p_mtn == NULL) return; + if (p_mtn == NULL) + return; - printf("GUID:0x%016" PRIx64 " max_children:%d\n", - p_mtn->p_sw->p_node->node_info.node_guid, + printf("GUID:0x%016" PRIx64 " max_children:%u\n", + cl_ntoh64(p_mtn->p_sw->p_node->node_info.node_guid), p_mtn->max_children ); if ( p_mtn->child_array != NULL ) { @@ -129,5 +133,5 @@ __osm_mtree_dump( __osm_mtree_dump(p_mtn->child_array[i]); } } - } + diff --git a/trunk/ulp/opensm/user/opensm/osm_multicast.c b/trunk/ulp/opensm/user/opensm/osm_multicast.c index beffd471..b12bcbe3 100644 --- a/trunk/ulp/opensm/user/opensm/osm_multicast.c +++ b/trunk/ulp/opensm/user/opensm/osm_multicast.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -46,7 +46,8 @@ # include #endif /* HAVE_CONFIG_H */ -#include +#include +#include #include #include #include @@ -78,7 +79,7 @@ void osm_mgrp_construct( IN osm_mgrp_t* const p_mgrp ) { - cl_memclr( p_mgrp, sizeof(*p_mgrp) ); + memset( p_mgrp, 0, sizeof(*p_mgrp) ); cl_qmap_init( &p_mgrp->mcm_port_tbl ); } @@ -103,7 +104,7 @@ osm_mgrp_destroy( /* destroy the mtree_node structure */ osm_mtree_destroy(p_mgrp->p_root); - cl_free(p_mgrp); + free(p_mgrp); } /********************************************************************** @@ -131,7 +132,7 @@ osm_mgrp_new( { osm_mgrp_t* p_mgrp; - p_mgrp = (osm_mgrp_t*)cl_malloc( sizeof(*p_mgrp) ); + p_mgrp = (osm_mgrp_t*)malloc( sizeof(*p_mgrp) ); if( p_mgrp ) osm_mgrp_init( p_mgrp, mlid ); @@ -159,14 +160,14 @@ osm_mgrp_add_port( port_guid = p_port_gid->unicast.interface_id; /* - prev_item = cl_qmap_insert(... + prev_item = cl_qmap_insert(...) Pointer to the item in the map with the specified key. If insertion was successful, this is the pointer to the item. If an item with the specified key already exists in the map, the pointer to that item is returned. */ - prev_item = cl_qmap_insert(&p_mgrp->mcm_port_tbl, - port_guid, &p_mcm_port->map_item ); + prev_item = cl_qmap_insert( &p_mgrp->mcm_port_tbl, + port_guid, &p_mcm_port->map_item ); /* if already exists - revert the insertion and only update join state */ if( prev_item != &p_mcm_port->map_item ) @@ -177,14 +178,16 @@ osm_mgrp_add_port( /* o15.0.1.11 - Join state of the end portshould be the or of the + Join state of the end port should be the or of the previous setting with the current one */ ib_member_get_scope_state(p_mcm_port->scope_state, &prev_scope, &prev_join_state); p_mcm_port->scope_state = ib_member_set_scope_state(prev_scope, prev_join_state | join_state); - } else { + } + else + { /* track the fact we modified the group ports */ p_mgrp->last_change_id++; } @@ -230,7 +233,7 @@ osm_mgrp_remove_port( /* Send a Report to any InformInfo registered for Trap 67 : MCGroup delete */ - osm_mgrp_send_delete_notice( p_subn, p_log, p_mgrp); + osm_mgrp_send_delete_notice( p_subn, p_log, p_mgrp ); } } @@ -240,7 +243,7 @@ boolean_t osm_mgrp_is_port_present( IN const osm_mgrp_t* const p_mgrp, IN const ib_net64_t port_guid, - OUT osm_mcm_port_t ** const pp_mcm_port) + OUT osm_mcm_port_t ** const pp_mcm_port ) { cl_map_item_t *p_map_item; @@ -310,7 +313,7 @@ osm_mgrp_apply_func( **********************************************************************/ void osm_mgrp_send_delete_notice( - IN osm_subn_t* const p_subn, + IN osm_subn_t* const p_subn, IN osm_log_t* const p_log, IN osm_mgrp_t *p_mgrp ) { @@ -323,15 +326,15 @@ osm_mgrp_send_delete_notice( /* details of the notice */ notice.generic_type = 0x83; /* is generic subn mgt type */ - ib_notice_set_prod_type(¬ice, CL_NTOH32(4)); /* A Class Manager generator */ + ib_notice_set_prod_type_ho(¬ice, 4); /* A Class Manager generator */ notice.g_or_v.generic.trap_num = CL_HTON16(67); /* delete of mcg */ /* The sm_base_lid is saved in network order already. */ notice.issuer_lid = p_subn->sm_base_lid; /* following o14-12.1.11 and table 120 p726 */ /* we need to provide the MGID */ - cl_memcpy(&(notice.data_details.ntc_64_67.gid), - &(p_mgrp->mcmember_rec.mgid), - sizeof(ib_gid_t)); + memcpy(&(notice.data_details.ntc_64_67.gid), + &(p_mgrp->mcmember_rec.mgid), + sizeof(ib_gid_t)); /* According to page 653 - the issuer gid in this case of trap is the SM gid, since the SM is the initiator of this trap. */ @@ -356,29 +359,28 @@ osm_mgrp_send_delete_notice( **********************************************************************/ void osm_mgrp_send_create_notice( - IN osm_subn_t* const p_subn, + IN osm_subn_t* const p_subn, IN osm_log_t* const p_log, IN osm_mgrp_t *p_mgrp ) { ib_mad_notice_attr_t notice; ib_api_status_t status; - OSM_LOG_ENTER( p_log, osm_mgrp_send_create_notice ); /* prepare the needed info */ /* details of the notice */ notice.generic_type = 0x83; /* Generic SubnMgt type */ - ib_notice_set_prod_type(¬ice, CL_HTON32(4)); /* A Class Manager generator */ + ib_notice_set_prod_type_ho(¬ice, 4); /* A Class Manager generator */ notice.g_or_v.generic.trap_num = CL_HTON16(66); /* create of mcg */ /* The sm_base_lid is saved in network order already. */ notice.issuer_lid = p_subn->sm_base_lid; /* following o14-12.1.11 and table 120 p726 */ /* we need to provide the MGID */ - cl_memcpy(&(notice.data_details.ntc_64_67.gid), - &(p_mgrp->mcmember_rec.mgid), - sizeof(ib_gid_t)); + memcpy(&(notice.data_details.ntc_64_67.gid), + &(p_mgrp->mcmember_rec.mgid), + sizeof(ib_gid_t)); /* According to page 653 - the issuer gid in this case of trap is the SM gid, since the SM is the initiator of this trap. */ @@ -398,3 +400,4 @@ osm_mgrp_send_create_notice( Exit: OSM_LOG_EXIT( p_log ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_node.c b/trunk/ulp/opensm/user/opensm/osm_node.c index 250aac4b..064c1db5 100644 --- a/trunk/ulp/opensm/user/opensm/osm_node.c +++ b/trunk/ulp/opensm/user/opensm/osm_node.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Implementation of osm_node_t. @@ -48,7 +49,7 @@ # include #endif /* HAVE_CONFIG_H */ -#include +#include #include #include #include @@ -95,7 +96,6 @@ osm_node_new( osm_node_t *p_node; ib_smp_t *p_smp; ib_node_info_t *p_ni; - uint8_t port_num; uint8_t i; uint32_t size; @@ -106,7 +106,6 @@ osm_node_new( CL_ASSERT( p_smp->attr_id == IB_MAD_ATTR_NODE_INFO ); p_ni = (ib_node_info_t*)ib_smp_get_payload_ptr( p_smp ); - port_num = ib_node_info_get_local_port_num( p_ni ); /* The node object already contains one physical port object. @@ -117,9 +116,10 @@ osm_node_new( */ size = p_ni->num_ports; - p_node = cl_zalloc( sizeof(*p_node) + sizeof(osm_physp_t) * size ); + p_node = malloc( sizeof(*p_node) + sizeof(osm_physp_t) * size ); if( p_node != NULL ) { + memset( p_node, 0, sizeof(*p_node) + sizeof(osm_physp_t) * size ); p_node->node_info = *p_ni; p_node->physp_tbl_size = size + 1; @@ -171,7 +171,7 @@ osm_node_delete( IN OUT osm_node_t** const p_node ) { osm_node_destroy( *p_node ); - cl_free( *p_node ); + free( *p_node ); *p_node = NULL; } @@ -194,6 +194,11 @@ osm_node_link( p_remote_physp = osm_node_get_physp_ptr( p_remote_node, remote_port_num ); + if (p_physp->p_remote_physp) + p_physp->p_remote_physp->p_remote_physp = NULL; + if (p_remote_physp->p_remote_physp) + p_remote_physp->p_remote_physp->p_remote_physp = NULL; + osm_physp_link( p_physp, p_remote_physp ); } @@ -327,3 +332,4 @@ osm_node_get_remote_base_lid( return( 0 ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_node_desc_rcv.c b/trunk/ulp/opensm/user/opensm/osm_node_desc_rcv.c index 68d0bc9f..d3e8cfbd 100644 --- a/trunk/ulp/opensm/user/opensm/osm_node_desc_rcv.c +++ b/trunk/ulp/opensm/user/opensm/osm_node_desc_rcv.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Implementation of osm_nd_rcv_t. @@ -44,16 +45,12 @@ * $Revision: 1.5 $ */ -/* - Next available error code: 0x403 -*/ - #if HAVE_CONFIG_H # include #endif /* HAVE_CONFIG_H */ +#include #include -#include #include #include #include @@ -76,7 +73,7 @@ __osm_nd_rcv_process_nd( if( osm_log_is_active( p_rcv->p_log, OSM_LOG_VERBOSE ) ) { - cl_memcpy( desc, p_nd, sizeof(*p_nd) ); + memcpy( desc, p_nd, sizeof(*p_nd) ); /* Guarantee null termination before printing. */ desc[IB_NODE_DESCRIPTION_SIZE] = '\0'; @@ -86,7 +83,7 @@ __osm_nd_rcv_process_nd( cl_ntoh64( osm_node_get_node_guid( p_node )), desc ); } - cl_memcpy( &p_node->node_desc.description, p_nd, sizeof(*p_nd) ); + memcpy( &p_node->node_desc.description, p_nd, sizeof(*p_nd) ); OSM_LOG_EXIT( p_rcv->p_log ); } @@ -97,7 +94,7 @@ void osm_nd_rcv_construct( IN osm_nd_rcv_t* const p_rcv ) { - cl_memclr( p_rcv, sizeof(*p_rcv) ); + memset( p_rcv, 0, sizeof(*p_rcv) ); } /********************************************************************** @@ -182,3 +179,4 @@ osm_nd_rcv_process( CL_PLOCK_RELEASE( p_rcv->p_lock ); OSM_LOG_EXIT( p_rcv->p_log ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_node_desc_rcv_ctrl.c b/trunk/ulp/opensm/user/opensm/osm_node_desc_rcv_ctrl.c index 03c807b6..f038e7b2 100644 --- a/trunk/ulp/opensm/user/opensm/osm_node_desc_rcv_ctrl.c +++ b/trunk/ulp/opensm/user/opensm/osm_node_desc_rcv_ctrl.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Implementation of osm_nd_rcv_ctrl_t. @@ -44,15 +45,11 @@ * $Revision: 1.5 $ */ -/* - Next available error code: 0x601 -*/ - #if HAVE_CONFIG_H # include #endif /* HAVE_CONFIG_H */ -#include +#include #include #include @@ -74,7 +71,7 @@ void osm_nd_rcv_ctrl_construct( IN osm_nd_rcv_ctrl_t* const p_ctrl ) { - cl_memclr( p_ctrl, sizeof(*p_ctrl) ); + memset( p_ctrl, 0, sizeof(*p_ctrl) ); p_ctrl->h_disp = CL_DISP_INVALID_HANDLE; } @@ -127,3 +124,4 @@ osm_nd_rcv_ctrl_init( return( status ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_node_info_rcv.c b/trunk/ulp/opensm/user/opensm/osm_node_info_rcv.c index ec17dcbb..76151f2c 100755 --- a/trunk/ulp/opensm/user/opensm/osm_node_info_rcv.c +++ b/trunk/ulp/opensm/user/opensm/osm_node_info_rcv.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -44,16 +44,13 @@ * $Revision: 1.9 $ */ -/* - Next available error code: 0x403 -*/ - #if HAVE_CONFIG_H # include #endif /* HAVE_CONFIG_H */ +#include +#include #include -#include #include #include #include @@ -63,15 +60,15 @@ #include #include #include +#include #include #include #include - /********************************************************************** The plock must be held before calling this function. **********************************************************************/ -void +static void __osm_ni_rcv_set_links( IN const osm_ni_rcv_t* const p_rcv, osm_node_t* p_node, @@ -126,12 +123,17 @@ __osm_ni_rcv_set_links( } else { - if( osm_node_has_any_link( p_node, port_num ) ) + if( osm_node_has_any_link( p_node, port_num ) && + p_rcv->p_subn->force_immediate_heavy_sweep == FALSE ) { /* Uh oh... This means that we found 2 nodes with the same guid, or a 12x link with lane reversal that is not configured correctly. + If the force_immediate_heavy_sweep == TRUE, then this might be a case + of port being moved (causing trap 128), and thus rediscovered. + In this case, just continue. There will be another heavy sweep + immediately after, when the subnet is stable again. */ char line[BUF_SIZE]; char dr_new_path[BUF_SIZE]; @@ -197,18 +199,19 @@ __osm_ni_rcv_set_links( ); osm_log( p_rcv->p_log, OSM_LOG_SYS, - "Errors on subnet. SM found duplicated guids or 12x " - "link with lane reversal badly configured. " - "See osm log for more details\n"); + "FATAL: duplicated guids or 12x lane reversal\n"); if ( p_rcv->p_subn->opt.exit_on_fatal == TRUE ) - exit( 1 ); + { + osm_log( p_rcv->p_log, OSM_LOG_SYS, "Exiting\n"); + exit( 1 ); + } } /* - When there are only two nodes with exact same guids (connected back to - back) - the previous check for duplicated guid will not catch them. - But the link will be from the port to itself ... + When there are only two nodes with exact same guids (connected back + to back) - the previous check for duplicated guid will not catch + them. But the link will be from the port to itself... Enhanced Port 0 is an exception to this */ if ((osm_node_get_node_guid( p_node ) == p_ni_context->node_guid) && @@ -274,11 +277,10 @@ __osm_ni_rcv_set_links( OSM_LOG_EXIT( p_rcv->p_log ); } - /********************************************************************** The plock must be held before calling this function. **********************************************************************/ -void +static void __osm_ni_rcv_process_new_node( IN const osm_ni_rcv_t* const p_rcv, IN osm_node_t* const p_node, @@ -322,6 +324,7 @@ __osm_ni_rcv_process_new_node( context.pi_context.update_master_sm_base_lid = FALSE; context.pi_context.ignore_errors = FALSE; context.pi_context.light_sweep = FALSE; + context.pi_context.active_transition = FALSE; status = osm_req_get( p_rcv->p_gen_req, osm_physp_get_dr_path_ptr( p_physp ), @@ -343,7 +346,7 @@ __osm_ni_rcv_process_new_node( /********************************************************************** The plock must be held before calling this function. **********************************************************************/ -void +static void __osm_ni_rcv_get_node_desc( IN const osm_ni_rcv_t* const p_rcv, IN osm_node_t* const p_node, @@ -403,13 +406,13 @@ __osm_ni_rcv_get_node_desc( /********************************************************************** The plock must be held before calling this function. **********************************************************************/ -void -__osm_ni_rcv_process_new_ca( +static void +__osm_ni_rcv_process_new_ca_or_router( IN const osm_ni_rcv_t* const p_rcv, IN osm_node_t* const p_node, IN const osm_madw_t* const p_madw ) { - OSM_LOG_ENTER( p_rcv->p_log, __osm_ni_rcv_process_new_ca ); + OSM_LOG_ENTER( p_rcv->p_log, __osm_ni_rcv_process_new_ca_or_router ); __osm_ni_rcv_process_new_node( p_rcv, p_node, p_madw ); @@ -429,8 +432,8 @@ __osm_ni_rcv_process_new_ca( /********************************************************************** The plock must be held before calling this function. **********************************************************************/ -void -__osm_ni_rcv_process_ca_port( +static void +__osm_ni_rcv_process_existing_ca_or_router( IN const osm_ni_rcv_t* const p_rcv, IN osm_node_t* const p_node, IN const osm_madw_t* const p_madw ) @@ -448,7 +451,7 @@ __osm_ni_rcv_process_ca_port( osm_bind_handle_t h_bind; cl_status_t cl_status; - OSM_LOG_ENTER( p_rcv->p_log, __osm_ni_rcv_process_ca_port ); + OSM_LOG_ENTER( p_rcv->p_log, __osm_ni_rcv_process_existing_ca_or_router ); p_smp = osm_madw_get_smp_ptr( p_madw ); p_ni = (ib_node_info_t*)ib_smp_get_payload_ptr( p_smp ); @@ -466,8 +469,8 @@ __osm_ni_rcv_process_ca_port( if( p_port == (osm_port_t*)cl_qmap_end( p_guid_tbl ) ) { osm_log( p_rcv->p_log, OSM_LOG_VERBOSE, - "__osm_ni_rcv_process_ca_port: " - "Creating new Port object with GUID = 0x%" PRIx64 "\n", + "__osm_ni_rcv_process_existing_ca_or_router: " + "Creating new port object with GUID 0x%" PRIx64 "\n", cl_ntoh64( p_ni->port_guid ) ); osm_node_init_physp( p_node, p_madw ); @@ -476,7 +479,7 @@ __osm_ni_rcv_process_ca_port( if( p_port == NULL ) { osm_log( p_rcv->p_log, OSM_LOG_ERROR, - "__osm_ni_rcv_process_ca_port: ERR 0D04: " + "__osm_ni_rcv_process_existing_ca_or_router: ERR 0D04: " "Unable to create new port object\n" ); goto Exit; } @@ -493,7 +496,7 @@ __osm_ni_rcv_process_ca_port( Somehow, this port GUID already exists in the table. */ osm_log( p_rcv->p_log, OSM_LOG_ERROR, - "__osm_ni_rcv_process_ca_port: ERR 0D12: " + "__osm_ni_rcv_process_existing_ca_or_router: ERR 0D12: " "Port 0x%" PRIx64 " already in the database!\n", cl_ntoh64( p_ni->port_guid ) ); @@ -514,7 +517,7 @@ __osm_ni_rcv_process_ca_port( if( cl_status != CL_SUCCESS ) { osm_log( p_rcv->p_log, OSM_LOG_ERROR, - "__osm_ni_rcv_process_ca_port: ERR 0D08: " + "__osm_ni_rcv_process_existing_ca_or_router: ERR 0D08: " "Error %s adding to list\n", CL_STATUS_MSG( cl_status ) ); osm_port_delete( &p_port ); @@ -523,7 +526,7 @@ __osm_ni_rcv_process_ca_port( else { osm_log( p_rcv->p_log, OSM_LOG_DEBUG, - "__osm_ni_rcv_process_ca_port: " + "__osm_ni_rcv_process_existing_ca_or_router: " "Adding port GUID:0x%016" PRIx64 " to new_ports_list\n", cl_ntoh64(osm_node_get_node_guid( p_port->p_node )) ); } @@ -536,7 +539,14 @@ __osm_ni_rcv_process_ca_port( p_physp = osm_node_get_physp_ptr( p_node, port_num ); CL_ASSERT( p_physp ); - CL_ASSERT( osm_physp_is_valid( p_physp ) ); + + if ( !osm_physp_is_valid( p_physp ) ) + { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "__osm_ni_rcv_process_existing_ca_or_router: ERR 0D19: " + "Invalid physical port. Aborting discovery\n"); + goto Exit; + } /* Update the DR Path to the port, @@ -565,7 +575,7 @@ __osm_ni_rcv_process_ca_port( if( status != IB_SUCCESS ) { osm_log( p_rcv->p_log, OSM_LOG_ERROR, - "__osm_ni_rcv_process_ca_port: ERR 0D13: " + "__osm_ni_rcv_process_existing_ca_or_router: ERR 0D13: " "Failure initiating PortInfo request (%s)\n", ib_get_err_str(status)); } @@ -574,41 +584,9 @@ __osm_ni_rcv_process_ca_port( OSM_LOG_EXIT( p_rcv->p_log ); } -/********************************************************************** - The plock must be held before calling this function. -**********************************************************************/ -void -__osm_ni_rcv_process_existing_ca( - IN const osm_ni_rcv_t* const p_rcv, - IN osm_node_t* const p_node, - IN const osm_madw_t* const p_madw ) -{ - OSM_LOG_ENTER( p_rcv->p_log, __osm_ni_rcv_process_existing_ca ); - - __osm_ni_rcv_process_ca_port( p_rcv, p_node, p_madw ); - - OSM_LOG_EXIT( p_rcv->p_log ); -} - -/********************************************************************** - The plock must be held before calling this function. -**********************************************************************/ -void -__osm_ni_rcv_process_new_router( - IN const osm_ni_rcv_t* const p_rcv, - IN osm_node_t* const p_node, - IN const osm_madw_t* const p_madw ) -{ - OSM_LOG_ENTER( p_rcv->p_log, __osm_ni_rcv_process_new_router ); - - __osm_ni_rcv_process_new_node( p_rcv, p_node, p_madw ); - - OSM_LOG_EXIT( p_rcv->p_log ); -} - /********************************************************************** **********************************************************************/ -void +static void __osm_ni_rcv_process_switch( IN const osm_ni_rcv_t* const p_rcv, IN osm_node_t* const p_node, @@ -657,16 +635,12 @@ __osm_ni_rcv_process_switch( /********************************************************************** The plock must be held before calling this function. **********************************************************************/ -void +static void __osm_ni_rcv_process_existing_switch( IN const osm_ni_rcv_t* const p_rcv, IN osm_node_t* const p_node, IN const osm_madw_t* const p_madw ) { - cl_qmap_t *p_sw_guid_tbl; - ib_net64_t node_guid; - osm_switch_t *p_sw; - OSM_LOG_ENTER( p_rcv->p_log, __osm_ni_rcv_process_existing_switch ); /* @@ -682,18 +656,13 @@ __osm_ni_rcv_process_existing_switch( else { /* Make sure we have SwitchInfo on this node */ - p_sw_guid_tbl = &p_rcv->p_subn->sw_guid_tbl; - node_guid = osm_node_get_node_guid( p_node ); - p_sw = (osm_switch_t*)cl_qmap_get( p_sw_guid_tbl, - node_guid ); - if( p_sw == (osm_switch_t*)cl_qmap_end( p_sw_guid_tbl ) || - osm_switch_discovery_count_get( p_sw ) == 0 ) + if( !p_node->sw || osm_switch_discovery_count_get( p_node->sw ) == 0 ) { /* we don't have the SwitchInfo - retry to get it */ osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "__osm_ni_rcv_process_existing_switch: " "Retry to get SwitchInfo on node GUID:0x%" - PRIx64 "\n", cl_ntoh64(node_guid) ); + PRIx64 "\n", cl_ntoh64(osm_node_get_node_guid(p_node)) ); __osm_ni_rcv_process_switch( p_rcv, p_node, p_madw ); } } @@ -704,7 +673,7 @@ __osm_ni_rcv_process_existing_switch( /********************************************************************** The plock must be held before calling this function. **********************************************************************/ -void +static void __osm_ni_rcv_process_new_switch( IN const osm_ni_rcv_t* const p_rcv, IN osm_node_t* const p_node, @@ -730,7 +699,7 @@ __osm_ni_rcv_process_new_switch( /********************************************************************** The plock must NOT be held before calling this function. **********************************************************************/ -void +static void __osm_ni_rcv_process_new( IN const osm_ni_rcv_t* const p_rcv, IN const osm_madw_t* const p_madw ) @@ -739,8 +708,11 @@ __osm_ni_rcv_process_new( osm_node_t *p_node_check; osm_port_t *p_port; osm_port_t *p_port_check; + osm_router_t *p_rtr = NULL; + osm_router_t *p_rtr_check; cl_qmap_t *p_node_guid_tbl; cl_qmap_t *p_port_guid_tbl; + cl_qmap_t *p_rtr_guid_tbl; ib_node_info_t *p_ni; ib_smp_t *p_smp; osm_ni_context_t *p_ni_context; @@ -759,7 +731,7 @@ __osm_ni_rcv_process_new( osm_log( p_rcv->p_log, OSM_LOG_VERBOSE, "__osm_ni_rcv_process_new: " "Discovered new %s node," - "\n\t\t\t\tGUID = 0x%" PRIx64 ", TID = 0x%" PRIx64 "\n", + "\n\t\t\t\tGUID 0x%" PRIx64 ", TID 0x%" PRIx64 "\n", ib_get_node_type_str( p_ni->node_type ), cl_ntoh64( p_ni->node_guid ), cl_ntoh64( p_smp->trans_id ) ); @@ -774,7 +746,7 @@ __osm_ni_rcv_process_new( } /* - Create a new Port object to represent this node's physical + Create a new port object to represent this node's physical ports in the port table. */ p_port = osm_port_new( p_ni, p_node ); @@ -787,14 +759,26 @@ __osm_ni_rcv_process_new( goto Exit; } - p_node_guid_tbl = &p_rcv->p_subn->node_guid_tbl; - p_port_guid_tbl = &p_rcv->p_subn->port_guid_tbl; + /* If there were RouterInfo or other router attribute, + this would be elsewhere */ + if ( p_ni->node_type == IB_NODE_TYPE_ROUTER ) + { + p_rtr = osm_router_new( p_port ); + if ( p_rtr == NULL ) + { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "__osm_ni_rcv_process_new: ERR 0D1A: " + "Unable to create new router object\n" ); + } + } /* Add the new port object to the database. */ + p_port_guid_tbl = &p_rcv->p_subn->port_guid_tbl; p_port_check = (osm_port_t*)cl_qmap_insert( p_port_guid_tbl, - p_ni->port_guid, &p_port->map_item ); + p_ni->port_guid, + &p_port->map_item ); if( p_port_check != p_port ) { /* @@ -813,11 +797,13 @@ __osm_ni_rcv_process_new( osm_physp_get_dr_path_ptr( osm_port_get_default_phys_ptr ( p_port_check) ), OSM_LOG_ERROR); - + if ( p_rtr ) + osm_router_delete( &p_rtr ); osm_port_delete( &p_port ); osm_node_delete( &p_node ); goto Exit; } + /* If we are a master, then this means the port is new on the subnet. Add it to the new_ports_list - need to send trap 64 on these ports. The condition that we are master is true, since if we are in discovering @@ -832,8 +818,10 @@ __osm_ni_rcv_process_new( { osm_log( p_rcv->p_log, OSM_LOG_ERROR, "__osm_ni_rcv_process_new: ERR 0D05: " - "Error %s adding to list\n", - CL_STATUS_MSG(status ) ); + "Error %s adding to new_ports_list\n", + CL_STATUS_MSG( status ) ); + if ( p_rtr ) + osm_router_delete( &p_rtr ); osm_port_delete( &p_port ); osm_node_delete( &p_node ); goto Exit; @@ -843,12 +831,29 @@ __osm_ni_rcv_process_new( osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "__osm_ni_rcv_process_new: " "Adding port GUID:0x%016" PRIx64 " to new_ports_list\n", - cl_ntoh64(osm_node_get_node_guid( p_port->p_node )) ); + cl_ntoh64( osm_node_get_node_guid( p_port->p_node ) ) ); + } + } + + if ( p_rtr && p_ni->node_type == IB_NODE_TYPE_ROUTER ) + { + p_rtr_guid_tbl = &p_rcv->p_subn->rtr_guid_tbl; + p_rtr_check = (osm_router_t*)cl_qmap_insert( p_rtr_guid_tbl, + p_ni->port_guid, + &p_rtr->map_item ); + if( p_rtr_check != p_rtr ) + { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "__osm_ni_rcv_process_new: ERR 0D1B: " + "Unable to add port GUID:0x%016" PRIx64 " to router table\n", + cl_ntoh64( p_ni->port_guid ) ); } } + p_node_guid_tbl = &p_rcv->p_subn->node_guid_tbl; p_node_check = (osm_node_t*)cl_qmap_insert( p_node_guid_tbl, - p_ni->node_guid, &p_node->map_item ); + p_ni->node_guid, + &p_node->map_item ); if( p_node_check != p_node ) { /* @@ -861,7 +866,6 @@ __osm_ni_rcv_process_new( "__osm_ni_rcv_process_new: " "Discovery race detected at node 0x%" PRIx64 "\n", cl_ntoh64( p_ni->node_guid ) ); - osm_node_delete( &p_node ); p_node = p_node_check; __osm_ni_rcv_set_links( p_rcv, p_node, port_num, p_ni_context ); @@ -876,18 +880,16 @@ __osm_ni_rcv_process_new( switch( p_ni->node_type ) { case IB_NODE_TYPE_CA: - __osm_ni_rcv_process_new_ca( p_rcv, p_node, p_madw ); + case IB_NODE_TYPE_ROUTER: + __osm_ni_rcv_process_new_ca_or_router( p_rcv, p_node, p_madw ); break; case IB_NODE_TYPE_SWITCH: __osm_ni_rcv_process_new_switch( p_rcv, p_node, p_madw ); break; - case IB_NODE_TYPE_ROUTER: - __osm_ni_rcv_process_new_router( p_rcv, p_node, p_madw ); - break; default: osm_log( p_rcv->p_log, OSM_LOG_ERROR, "__osm_ni_rcv_process_new: ERR 0D16: " - "Unknown node type = %u with GUID = 0x%" PRIx64 "\n", + "Unknown node type %u with GUID 0x%" PRIx64 "\n", p_ni->node_type, cl_ntoh64( p_ni->node_guid ) ); break; } @@ -899,7 +901,7 @@ __osm_ni_rcv_process_new( /********************************************************************** The plock must be held before calling this function. **********************************************************************/ -void +static void __osm_ni_rcv_process_existing( IN const osm_ni_rcv_t* const p_rcv, IN osm_node_t* const p_node, @@ -922,7 +924,7 @@ __osm_ni_rcv_process_existing( osm_log( p_rcv->p_log, OSM_LOG_VERBOSE, "__osm_ni_rcv_process_existing: " "Rediscovered %s node 0x%" PRIx64 - "\n\t\t\t\tTID = 0x%" PRIx64 + "\n\t\t\t\tTID 0x%" PRIx64 ", discovered %u times already\n", ib_get_node_type_str(p_ni->node_type), cl_ntoh64( p_ni->node_guid ), @@ -938,12 +940,9 @@ __osm_ni_rcv_process_existing( switch( p_ni->node_type ) { - case IB_NODE_TYPE_ROUTER: - /* Not supported yet. */ - break; - case IB_NODE_TYPE_CA: - __osm_ni_rcv_process_existing_ca( p_rcv, p_node, p_madw ); + case IB_NODE_TYPE_ROUTER: + __osm_ni_rcv_process_existing_ca_or_router( p_rcv, p_node, p_madw ); break; case IB_NODE_TYPE_SWITCH: @@ -953,7 +952,7 @@ __osm_ni_rcv_process_existing( default: osm_log( p_rcv->p_log, OSM_LOG_ERROR, "__osm_ni_rcv_process_existing: ERR 0D09: " - "Unknown node type = %u with GUID = 0x%" PRIx64 "\n", + "Unknown node type %u with GUID 0x%" PRIx64 "\n", p_ni->node_type, cl_ntoh64( p_ni->node_guid ) ); break; } @@ -969,7 +968,7 @@ void osm_ni_rcv_construct( IN osm_ni_rcv_t* const p_rcv ) { - cl_memclr( p_rcv, sizeof(*p_rcv) ); + memset( p_rcv, 0, sizeof(*p_rcv) ); } /********************************************************************** @@ -1088,3 +1087,4 @@ osm_ni_rcv_process( Exit: OSM_LOG_EXIT( p_rcv->p_log ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_node_info_rcv_ctrl.c b/trunk/ulp/opensm/user/opensm/osm_node_info_rcv_ctrl.c index a86a5522..8633dd3e 100644 --- a/trunk/ulp/opensm/user/opensm/osm_node_info_rcv_ctrl.c +++ b/trunk/ulp/opensm/user/opensm/osm_node_info_rcv_ctrl.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Implementation of osm_ni_rcv_ctrl_t. @@ -44,15 +45,11 @@ * $Revision: 1.5 $ */ -/* - Next available error code: 0x203 -*/ - #if HAVE_CONFIG_H # include #endif /* HAVE_CONFIG_H */ -#include +#include #include #include @@ -74,7 +71,7 @@ void osm_ni_rcv_ctrl_construct( IN osm_ni_rcv_ctrl_t* const p_ctrl ) { - cl_memclr( p_ctrl, sizeof(*p_ctrl) ); + memset( p_ctrl, 0, sizeof(*p_ctrl) ); p_ctrl->h_disp = CL_DISP_INVALID_HANDLE; } @@ -127,3 +124,4 @@ osm_ni_rcv_ctrl_init( return( status ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_opensm.c b/trunk/ulp/opensm/user/opensm/osm_opensm.c index f2b5dba3..e80d6c34 100644 --- a/trunk/ulp/opensm/user/opensm/osm_opensm.c +++ b/trunk/ulp/opensm/user/opensm/osm_opensm.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Implementation of osm_opensm_t. @@ -50,14 +51,11 @@ #include #include -#include -#include +#include +#include #include #include #include -#ifdef OSM_VENDOR_INTF_OPENIB -#include -#endif #include #include #include @@ -65,13 +63,63 @@ #include #include +struct routing_engine_module { + const char *name; + int (*setup)(osm_opensm_t *p_osm); +}; + +extern int osm_ucast_updn_setup(osm_opensm_t *p_osm); +extern int osm_ucast_file_setup(osm_opensm_t *p_osm); +extern int osm_ucast_ftree_setup(osm_opensm_t *p_osm); + +static int osm_ucast_null_setup(osm_opensm_t *p_osm); + +const static struct routing_engine_module routing_modules[] = { + { "null", osm_ucast_null_setup }, + { "updn", osm_ucast_updn_setup }, + { "file", osm_ucast_file_setup }, + { "ftree", osm_ucast_ftree_setup }, + { NULL, NULL } +}; + +static int setup_routing_engine(osm_opensm_t *p_osm, const char *name) +{ + const struct routing_engine_module *r; + + for (r = routing_modules; r->name && *r->name; r++) { + if(!strcmp(r->name, name)) { + p_osm->routing_engine.name = r->name; + if (r->setup(p_osm)) { + osm_log(&p_osm->log, OSM_LOG_VERBOSE, + "setup_routing_engine: setup of routing" + " engine \'%s\' failed\n", name); + return -2; + } + osm_log (&p_osm->log, OSM_LOG_DEBUG, + "setup_routing_engine: " + "\'%s\' routing engine set up\n", + p_osm->routing_engine.name); + return 0; + } + } + return -1; +} + +static int osm_ucast_null_setup(osm_opensm_t *p_osm) +{ + osm_log(&p_osm->log, OSM_LOG_VERBOSE, + "osm_ucast_null_setup: nothing yet - " + "will use default routing engine\n"); + return 0; +} + /********************************************************************** **********************************************************************/ void osm_opensm_construct( IN osm_opensm_t * const p_osm ) { - cl_memclr( p_osm, sizeof( *p_osm ) ); + memset( p_osm, 0, sizeof( *p_osm ) ); osm_subn_construct( &p_osm->subn ); osm_sm_construct( &p_osm->sm ); osm_sa_construct( &p_osm->sa ); @@ -114,8 +162,12 @@ osm_opensm_destroy( /* shut down the dispatcher - so no new messages cross */ cl_disp_shutdown( &p_osm->disp ); + /* dump SA DB */ + osm_sa_db_file_dump(p_osm); + /* do the destruction in reverse order as init */ - updn_destroy( p_osm->p_updn_ucast_routing ); + if (p_osm->routing_engine.delete) + p_osm->routing_engine.delete(p_osm->routing_engine.context); osm_sa_destroy( &p_osm->sa ); osm_sm_destroy( &p_osm->sm ); osm_db_destroy( &p_osm->db ); @@ -127,23 +179,9 @@ osm_opensm_destroy( cl_plock_destroy( &p_osm->lock ); - cl_mem_display( ); - osm_log_destroy( &p_osm->log ); } -/********************************************************************** - **********************************************************************/ -static void -osm_opensm_create_mcgroups( - IN osm_opensm_t * const p_osm, - IN const osm_subn_opt_t * const p_opt ) -{ - OSM_LOG_ENTER( &p_osm->log, osm_opensm_create_mcgroups ); - osm_sa_create_template_record_ipoib( &p_osm->sa, p_opt ); - OSM_LOG_EXIT( &p_osm->log ); -} - /********************************************************************** **********************************************************************/ ib_api_status_t @@ -156,38 +194,18 @@ osm_opensm_init( /* Can't use log macros here, since we're initializing the log. */ osm_opensm_construct( p_osm ); - status = osm_log_init( &p_osm->log, p_opt->force_log_flush, - p_opt->log_flags, p_opt->log_file, p_opt->accum_log_file ); + status = osm_log_init_v2( &p_osm->log, p_opt->force_log_flush, + p_opt->log_flags, p_opt->log_file, + p_opt->log_max_size, p_opt->accum_log_file ); if( status != IB_SUCCESS ) return ( status ); -#ifndef OSM_VENDOR_INTF_OPENIB /* If there is a log level defined - add the OSM_VERSION to it. */ osm_log( &p_osm->log, osm_log_get_level( &p_osm->log ) & ( OSM_LOG_SYS ^ 0xFF ), "%s\n", OSM_VERSION ); /* Write the OSM_VERSION to the SYS_LOG */ osm_log( &p_osm->log, OSM_LOG_SYS, "%s\n", OSM_VERSION ); /* Format Waived */ -#else - if (strlen(OSM_SVN_REVISION)) - { - /* If there is a log level defined - add OSM_VERSION and OSM_SVN_REVISION to it. */ - osm_log( &p_osm->log, - osm_log_get_level( &p_osm->log ) & ( OSM_LOG_SYS ^ 0xFF ), "%s OpenIB svn %s\n", - OSM_VERSION, OSM_SVN_REVISION ); - /* Write the OSM_VERSION and OSM_SVN_REVISION to the SYS_LOG */ - osm_log( &p_osm->log, OSM_LOG_SYS, "%s OpenIB svn %s\n", OSM_VERSION, OSM_SVN_REVISION ); /* Format Waived */ - } - else - { - /* If there is a log level defined - add the OSM_VERSION to it. */ - osm_log( &p_osm->log, - osm_log_get_level( &p_osm->log ) & ( OSM_LOG_SYS ^ 0xFF ), "%s\n", - OSM_VERSION ); - /* Write the OSM_VERSION to the SYS_LOG */ - osm_log( &p_osm->log, OSM_LOG_SYS, "%s\n", OSM_VERSION ); /* Format Waived */ - } -#endif osm_log( &p_osm->log, OSM_LOG_FUNCS, "osm_opensm_init: [\n" ); /* Format Waived */ @@ -212,7 +230,7 @@ osm_opensm_init( if( status != IB_SUCCESS ) goto Exit; - status = osm_subn_init( &p_osm->subn, p_opt ); + status = osm_subn_init( &p_osm->subn, p_osm, p_opt ); if( status != IB_SUCCESS ) goto Exit; @@ -263,14 +281,14 @@ osm_opensm_init( if( status != IB_SUCCESS ) goto Exit; - osm_opensm_create_mcgroups( p_osm, p_opt ); - - /* HACK - the UpDown manager should have been a part of the osm_sm_t */ - /* Init updn struct */ - p_osm->p_updn_ucast_routing = updn_construct( ); - status = updn_init( p_osm->p_updn_ucast_routing ); - if( status != IB_SUCCESS ) + if( p_opt->routing_engine_name && + setup_routing_engine(p_osm, p_opt->routing_engine_name)) { + osm_log( &p_osm->log, OSM_LOG_VERBOSE, + "osm_opensm_init: cannot find or setup routing engine" + " \'%s\'. Default will be used instead\n", + p_opt->routing_engine_name); goto Exit; + } Exit: osm_log( &p_osm->log, OSM_LOG_FUNCS, "osm_opensm_init: ]\n" ); /* Format Waived */ @@ -299,3 +317,4 @@ osm_opensm_bind( OSM_LOG_EXIT( &p_osm->log ); return ( status ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_pkey.c b/trunk/ulp/opensm/user/opensm/osm_pkey.c index f2d594b5..49edbdf6 100644 --- a/trunk/ulp/opensm/user/opensm/osm_pkey.c +++ b/trunk/ulp/opensm/user/opensm/osm_pkey.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Implementation of opensm pkey manipulation functions. @@ -48,7 +49,7 @@ #include #include -#include +#include #include #include #include @@ -64,6 +65,7 @@ void osm_pkey_tbl_construct( IN osm_pkey_tbl_t *p_pkey_tbl) { cl_ptr_vector_construct( &p_pkey_tbl->blocks ); + cl_ptr_vector_construct( &p_pkey_tbl->new_blocks ); cl_map_construct( &p_pkey_tbl->keys ); } @@ -72,44 +74,71 @@ void osm_pkey_tbl_construct( void osm_pkey_tbl_destroy( IN osm_pkey_tbl_t *p_pkey_tbl) { + ib_pkey_table_t *p_block; uint16_t num_blocks, i; num_blocks = (uint16_t)(cl_ptr_vector_get_size( &p_pkey_tbl->blocks )); for (i = 0; i < num_blocks; i++) - cl_free(cl_ptr_vector_get( &p_pkey_tbl->blocks, i )); + if ((p_block = cl_ptr_vector_get( &p_pkey_tbl->blocks, i ))) + free(p_block); cl_ptr_vector_destroy( &p_pkey_tbl->blocks ); + num_blocks = (uint16_t)(cl_ptr_vector_get_size( &p_pkey_tbl->new_blocks )); + for (i = 0; i < num_blocks; i++) + if ((p_block = cl_ptr_vector_get( &p_pkey_tbl->new_blocks, i ))) + free(p_block); + cl_ptr_vector_destroy( &p_pkey_tbl->new_blocks ); + cl_map_remove_all( &p_pkey_tbl->keys ); cl_map_destroy( &p_pkey_tbl->keys ); } /********************************************************************** **********************************************************************/ -int osm_pkey_tbl_init( +ib_api_status_t +osm_pkey_tbl_init( IN osm_pkey_tbl_t *p_pkey_tbl) { - ib_pkey_table_t *p_pkey_block; - /* - we always need one block to be pre-allocated for the sake of - empty table test - */ - cl_ptr_vector_init( &p_pkey_tbl->blocks, 1, 1); - p_pkey_block = (ib_pkey_table_t *)cl_zalloc(sizeof(ib_pkey_table_t)); - if (! p_pkey_block) - { - return(IB_ERROR); - } + cl_ptr_vector_init(&p_pkey_tbl->blocks, 0, 1); + cl_ptr_vector_init(&p_pkey_tbl->new_blocks, 0, 1); + cl_map_init(&p_pkey_tbl->keys, 1); + cl_qlist_init(&p_pkey_tbl->pending); + p_pkey_tbl->used_blocks = 0; + p_pkey_tbl->max_blocks = 0; + return(IB_SUCCESS); +} - cl_ptr_vector_set(&p_pkey_tbl->blocks, 0, p_pkey_block); +/********************************************************************** + **********************************************************************/ +void osm_pkey_tbl_init_new_blocks( + IN const osm_pkey_tbl_t *p_pkey_tbl) +{ + ib_pkey_table_t *p_block; + size_t b, num_blocks = cl_ptr_vector_get_size(&p_pkey_tbl->new_blocks); - /* deal with the map */ - cl_map_init( &p_pkey_tbl->keys, 1 ); - return(IB_SUCCESS); + for (b = 0; b < num_blocks; b++) + if ((p_block = cl_ptr_vector_get(&p_pkey_tbl->new_blocks, b))) + memset(p_block, 0, sizeof(*p_block)); +} + +/********************************************************************** + **********************************************************************/ +void osm_pkey_tbl_cleanup_pending( + IN osm_pkey_tbl_t *p_pkey_tbl) +{ + cl_list_item_t *p_item; + + p_item = cl_qlist_remove_head(&p_pkey_tbl->pending); + while (p_item != cl_qlist_end(&p_pkey_tbl->pending)) + { + free((osm_pending_pkey_t *)p_item); + } } /********************************************************************** **********************************************************************/ -int osm_pkey_tbl_set( +ib_api_status_t +osm_pkey_tbl_set( IN osm_pkey_tbl_t *p_pkey_tbl, IN uint16_t block, IN ib_pkey_table_t *p_tbl) @@ -128,12 +157,14 @@ int osm_pkey_tbl_set( if ( !p_pkey_block ) { - p_pkey_block = (ib_pkey_table_t *)cl_zalloc(sizeof(ib_pkey_table_t)); + p_pkey_block = (ib_pkey_table_t *)malloc(sizeof(ib_pkey_table_t)); + if (p_pkey_block) + memset(p_pkey_block, 0, sizeof(ib_pkey_table_t)); cl_ptr_vector_set( &p_pkey_tbl->blocks, block, p_pkey_block ); } /* sets the block values */ - cl_memcpy( p_pkey_block, p_tbl, sizeof(ib_pkey_table_t) ); + memcpy( p_pkey_block, p_tbl, sizeof(ib_pkey_table_t) ); /* NOTE: as the spec does not require uniqueness of PKeys in @@ -148,12 +179,14 @@ int osm_pkey_tbl_set( { p_pkey_block = cl_ptr_vector_get( &p_pkey_tbl->blocks, b ); - if (! p_pkey_block) continue; + if (! p_pkey_block) + continue; for (i = 0; i < IB_NUM_PKEY_ELEMENTS_IN_BLOCK; i++) { pkey = p_pkey_block->pkey_entry[i]; - if (ib_pkey_is_invalid(pkey)) continue; + if (ib_pkey_is_invalid(pkey)) + continue; /* ignore the PKey Full Member bit in the key but store @@ -176,9 +209,106 @@ int osm_pkey_tbl_set( /********************************************************************** **********************************************************************/ -boolean_t __osm_match_pkey ( +/* + Store the given pkey in the "new" blocks array. + Also, make sure the regular block exists. +*/ +ib_api_status_t +osm_pkey_tbl_set_new_entry( + IN osm_pkey_tbl_t *p_pkey_tbl, + IN uint16_t block_idx, + IN uint8_t pkey_idx, + IN uint16_t pkey) +{ + ib_pkey_table_t *p_block; + + if (!(p_block = osm_pkey_tbl_new_block_get(p_pkey_tbl, block_idx))) { + p_block = (ib_pkey_table_t *)malloc(sizeof(ib_pkey_table_t)); + if (!p_block) + return(IB_ERROR); + memset(p_block, 0, sizeof(ib_pkey_table_t)); + cl_ptr_vector_set(&p_pkey_tbl->new_blocks, block_idx, p_block); + } + + p_block->pkey_entry[pkey_idx] = pkey; + if (p_pkey_tbl->used_blocks <= block_idx) + p_pkey_tbl->used_blocks = block_idx + 1; + + return(IB_SUCCESS); +} + +/********************************************************************** + **********************************************************************/ +boolean_t +osm_pkey_find_next_free_entry( + IN osm_pkey_tbl_t *p_pkey_tbl, + OUT uint16_t *p_block_idx, + OUT uint8_t *p_pkey_idx) +{ + ib_pkey_table_t *p_new_block; + + CL_ASSERT(p_block_idx); + CL_ASSERT(p_pkey_idx); + + while (*p_block_idx < p_pkey_tbl->max_blocks) + { + if (*p_pkey_idx > IB_NUM_PKEY_ELEMENTS_IN_BLOCK - 1) + { + *p_pkey_idx = 0; + (*p_block_idx)++; + if (*p_block_idx >= p_pkey_tbl->max_blocks) + return FALSE; + } + + p_new_block = osm_pkey_tbl_new_block_get(p_pkey_tbl, *p_block_idx); + + if (!p_new_block || + ib_pkey_is_invalid(p_new_block->pkey_entry[*p_pkey_idx])) + return TRUE; + else + (*p_pkey_idx)++; + } + return FALSE; +} + +/********************************************************************** + **********************************************************************/ +ib_api_status_t +osm_pkey_tbl_get_block_and_idx( + IN osm_pkey_tbl_t *p_pkey_tbl, + IN uint16_t *p_pkey, + OUT uint16_t *p_block_idx, + OUT uint8_t *p_pkey_idx) +{ + uint16_t num_of_blocks; + uint16_t block_index; + ib_pkey_table_t *block; + + CL_ASSERT( p_block_idx != NULL ); + CL_ASSERT( p_pkey_idx != NULL ); + + num_of_blocks = (uint16_t)cl_ptr_vector_get_size( &p_pkey_tbl->blocks ); + for (block_index = 0; block_index < num_of_blocks; block_index++) + { + block = osm_pkey_tbl_block_get(p_pkey_tbl, block_index); + if ((block->pkey_entry <= p_pkey) && + (p_pkey < block->pkey_entry + IB_NUM_PKEY_ELEMENTS_IN_BLOCK)) + { + *p_block_idx = block_index; + *p_pkey_idx = (uint8_t)(p_pkey - block->pkey_entry); + return(IB_SUCCESS); + } + } + return(IB_NOT_FOUND); +} + +/********************************************************************** + **********************************************************************/ +static boolean_t +__osm_match_pkey ( IN const ib_net16_t *pkey1, - IN const ib_net16_t *pkey2 ) { + IN const ib_net16_t *pkey2 ) +{ /* if both pkeys are not full member - this is not a match */ if (!(ib_pkey_is_full_member(*pkey1) || ib_pkey_is_full_member(*pkey2))) @@ -195,41 +325,39 @@ boolean_t __osm_match_pkey ( /********************************************************************** **********************************************************************/ boolean_t -osm_physp_share_pkey( - IN osm_log_t* p_log, - IN const osm_physp_t* const p_physp_1, - IN const osm_physp_t* const p_physp_2 ) { +osm_physp_share_this_pkey( + IN const osm_physp_t* const p_physp1, + IN const osm_physp_t* const p_physp2, + IN const ib_net16_t pkey ) +{ + ib_net16_t *pkey1, *pkey2; + + pkey1 = cl_map_get( &(osm_physp_get_pkey_tbl(p_physp1))->keys, + ib_pkey_get_base(pkey)); + pkey2 = cl_map_get( &(osm_physp_get_pkey_tbl(p_physp2))->keys, + ib_pkey_get_base(pkey)); + return (pkey1 && pkey2 && __osm_match_pkey(pkey1, pkey2)); +} +/********************************************************************** + **********************************************************************/ +ib_net16_t +osm_physp_find_common_pkey( + IN const osm_physp_t* const p_physp1, + IN const osm_physp_t* const p_physp2 ) +{ ib_net16_t *pkey1, *pkey2; uint64_t pkey1_base, pkey2_base; const osm_pkey_tbl_t *pkey_tbl1, *pkey_tbl2; cl_map_iterator_t map_iter1, map_iter2; - OSM_LOG_ENTER( p_log, osm_physp_share_pkey ); - - /* If two ports are same, no need to check */ - if (p_physp_1 == p_physp_2) - return (TRUE); + pkey_tbl1 = osm_physp_get_pkey_tbl(p_physp1); + pkey_tbl2 = osm_physp_get_pkey_tbl(p_physp2); - pkey_tbl1 = osm_physp_get_pkey_tbl(p_physp_1); - pkey_tbl2 = osm_physp_get_pkey_tbl(p_physp_2); - - /* - The spec: 10.9.2 does not require each phys port to have PKey Table. - So actually if it does not, we need to use the default port instead. + map_iter1 = cl_map_head(&pkey_tbl1->keys); + map_iter2 = cl_map_head(&pkey_tbl2->keys); - HACK: meanwhile we will ignore the check - */ - if (cl_is_map_empty(&pkey_tbl1->keys) || cl_is_map_empty(&pkey_tbl2->keys)) - { - OSM_LOG_EXIT( p_log ); - return(TRUE); - } - /* we rely on the fact the map are sorted by pkey */ - map_iter1 = cl_map_head( &pkey_tbl1->keys ); - map_iter2 = cl_map_head( &pkey_tbl2->keys ); - while ( (map_iter1 != cl_map_end( &pkey_tbl1->keys )) && (map_iter2 != cl_map_end( &pkey_tbl2->keys ))) { @@ -237,15 +365,8 @@ osm_physp_share_pkey( pkey2 = (ib_net16_t *)cl_map_obj( map_iter2 ); if (__osm_match_pkey(pkey1, pkey2)) - { - osm_log( p_log, OSM_LOG_DEBUG, - "osm_physp_share_pkey: " - "Matched pkeys: 0x%04x 0x%04x\n", - cl_ntoh16(*pkey1), cl_ntoh16(*pkey2)); - OSM_LOG_EXIT( p_log ); - return(TRUE); - } - + return *pkey1; + /* advance the lower value if they are not equal */ pkey1_base = cl_map_key( map_iter1 ); pkey2_base = cl_map_key( map_iter2 ); @@ -260,12 +381,35 @@ osm_physp_share_pkey( map_iter1 = cl_map_next( map_iter1 ); } - osm_log( p_log, OSM_LOG_DEBUG, - "osm_physp_share_pkey: " - "Ports do not share a pkey\n"); + return 0; +} - OSM_LOG_EXIT( p_log ); - return(FALSE); +/********************************************************************** + **********************************************************************/ +boolean_t +osm_physp_share_pkey( + IN osm_log_t* p_log, + IN const osm_physp_t* const p_physp_1, + IN const osm_physp_t* const p_physp_2 ) +{ + const osm_pkey_tbl_t *pkey_tbl1, *pkey_tbl2; + + if (p_physp_1 == p_physp_2) + return TRUE; + + pkey_tbl1 = osm_physp_get_pkey_tbl(p_physp_1); + pkey_tbl2 = osm_physp_get_pkey_tbl(p_physp_2); + + /* + The spec: 10.9.2 does not require each phys port to have PKey Table. + So actually if it does not, we need to use the default port instead. + + HACK: meanwhile we will ignore the check + */ + if (cl_is_map_empty(&pkey_tbl1->keys) || cl_is_map_empty(&pkey_tbl2->keys)) + return TRUE; + + return !ib_pkey_is_invalid(osm_physp_find_common_pkey(p_physp_1, p_physp_2)); } /********************************************************************** @@ -281,17 +425,19 @@ osm_port_share_pkey( OSM_LOG_ENTER( p_log, osm_port_share_pkey ); - if (!p_port_1 || !p_port_2) { - ret = FALSE; - goto Exit; + if (!p_port_1 || !p_port_2) + { + ret = FALSE; + goto Exit; } p_physp1 = osm_port_get_default_phys_ptr(p_port_1); p_physp2 = osm_port_get_default_phys_ptr(p_port_2); - if (!p_physp1 || !p_physp2) { - ret = FALSE; - goto Exit; + if (!p_physp1 || !p_physp2) + { + ret = FALSE; + goto Exit; } ret = osm_physp_share_pkey(p_log, p_physp1, p_physp2); @@ -398,3 +544,4 @@ osm_physp_has_pkey( OSM_LOG_EXIT( p_log ); return res; } + diff --git a/trunk/ulp/opensm/user/opensm/osm_pkey_mgr.c b/trunk/ulp/opensm/user/opensm/osm_pkey_mgr.c index c3a1ccf3..a03f7a4b 100644 --- a/trunk/ulp/opensm/user/opensm/osm_pkey_mgr.c +++ b/trunk/ulp/opensm/user/opensm/osm_pkey_mgr.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,11 +32,11 @@ */ + /* * Abstract: - * Implementation of osm_pkey_mgr_t. - * This object represents the P_Key Manager object. - * This object is part of the opensm family of objects. + * Implementation of the P_Key Manager (Partititon Manager). + * This is part of the OpenSM. * * Environment: * Linux User Mode @@ -48,231 +48,549 @@ # include #endif /* HAVE_CONFIG_H */ +#include #include #include #include #include +#include #include +#include +#include /********************************************************************** **********************************************************************/ -void -osm_pkey_mgr_construct( - IN osm_pkey_mgr_t * const p_mgr ) +/* + The max number of pkey blocks for a physical port is located in + a different place for switch external ports (SwitchInfo) and the + rest of the ports (NodeInfo). +*/ +static uint16_t +pkey_mgr_get_physp_max_blocks( + IN const osm_subn_t *p_subn, + IN const osm_physp_t *p_physp ) { - CL_ASSERT( p_mgr ); - cl_memclr( p_mgr, sizeof( *p_mgr ) ); + osm_node_t *p_node = osm_physp_get_node_ptr( p_physp ); + uint16_t num_pkeys = 0; + + if ( !p_node->sw || + ( osm_physp_get_port_num( p_physp ) == 0 ) ) + num_pkeys = cl_ntoh16( p_node->node_info.partition_cap ); + else + num_pkeys = cl_ntoh16( p_node->sw->switch_info.enforce_cap ); + return((num_pkeys + 31) / 32); } /********************************************************************** **********************************************************************/ -void -osm_pkey_mgr_destroy( - IN osm_pkey_mgr_t * const p_mgr ) +/* + * Insert new pending pkey entry to the specific port pkey table + * pending pkeys. New entries are inserted at the back. + */ +static void +pkey_mgr_process_physical_port( + IN osm_log_t *p_log, + IN const osm_req_t *p_req, + IN const ib_net16_t pkey, + IN osm_physp_t *p_physp ) { - CL_ASSERT( p_mgr ); + osm_node_t *p_node = osm_physp_get_node_ptr( p_physp ); + osm_pkey_tbl_t *p_pkey_tbl; + ib_net16_t *p_orig_pkey; + char *stat = NULL; + osm_pending_pkey_t *p_pending; - OSM_LOG_ENTER( p_mgr->p_log, osm_pkey_mgr_destroy ); + p_pkey_tbl = osm_physp_get_mod_pkey_tbl( p_physp ); + p_pending = (osm_pending_pkey_t *)malloc( sizeof( osm_pending_pkey_t ) ); + if (!p_pending) + { + osm_log( p_log, OSM_LOG_ERROR, + "pkey_mgr_process_physical_port: ERR 0502: " + "Failed to allocate new pending pkey entry for node " + "0x%016" PRIx64 " port %u\n", + cl_ntoh64( osm_node_get_node_guid( p_node ) ), + osm_physp_get_port_num( p_physp ) ); + return; + } + p_pending->pkey = pkey; + p_orig_pkey = cl_map_get( &p_pkey_tbl->keys, ib_pkey_get_base( pkey ) ); + if (!p_orig_pkey) + { + p_pending->is_new = TRUE; + cl_qlist_insert_tail( &p_pkey_tbl->pending, (cl_list_item_t*)p_pending ); + stat = "inserted"; + } + else + { + CL_ASSERT( ib_pkey_get_base( *p_orig_pkey ) == ib_pkey_get_base( pkey ) ); + p_pending->is_new = FALSE; + if (osm_pkey_tbl_get_block_and_idx( + p_pkey_tbl, p_orig_pkey, + &p_pending->block, &p_pending->index ) != IB_SUCCESS) + { + osm_log( p_log, OSM_LOG_ERROR, + "pkey_mgr_process_physical_port: ERR 0503: " + "Failed to obtain P_Key 0x%04x block and index for node " + "0x%016" PRIx64 " port %u\n", + ib_pkey_get_base( pkey ), + cl_ntoh64( osm_node_get_node_guid( p_node ) ), + osm_physp_get_port_num( p_physp ) ); + return; + } + cl_qlist_insert_head( &p_pkey_tbl->pending, (cl_list_item_t*)p_pending ); + stat = "updated"; + } - OSM_LOG_EXIT( p_mgr->p_log ); + osm_log( p_log, OSM_LOG_DEBUG, + "pkey_mgr_process_physical_port: " + "pkey 0x%04x was %s for node 0x%016" PRIx64 + " port %u\n", + cl_ntoh16( pkey ), stat, + cl_ntoh64( osm_node_get_node_guid( p_node ) ), + osm_physp_get_port_num( p_physp ) ); } /********************************************************************** **********************************************************************/ -ib_api_status_t -osm_pkey_mgr_init( - IN osm_pkey_mgr_t * const p_mgr, - IN osm_subn_t * const p_subn, - IN osm_log_t * const p_log, - IN osm_req_t * const p_req, - IN cl_plock_t * const p_lock ) +static void +pkey_mgr_process_partition_table( + osm_log_t *p_log, + const osm_req_t *p_req, + const osm_prtn_t *p_prtn, + const boolean_t full ) { - ib_api_status_t status = IB_SUCCESS; + const cl_map_t *p_tbl = + full ? &p_prtn->full_guid_tbl : &p_prtn->part_guid_tbl; + cl_map_iterator_t i, i_next; + ib_net16_t pkey = p_prtn->pkey; + osm_physp_t *p_physp; - OSM_LOG_ENTER( p_log, osm_pkey_mgr_init ); + if (full) + pkey |= cl_hton16( 0x8000 ); - osm_pkey_mgr_construct( p_mgr ); + i_next = cl_map_head( p_tbl ); + while ( i_next != cl_map_end( p_tbl ) ) + { + i = i_next; + i_next = cl_map_next( i ); + p_physp = cl_map_obj( i ); + if ( p_physp && osm_physp_is_valid( p_physp ) ) + pkey_mgr_process_physical_port( p_log, p_req, pkey, p_physp ); + } +} - p_mgr->p_log = p_log; - p_mgr->p_subn = p_subn; - p_mgr->p_lock = p_lock; - p_mgr->p_req = p_req; +/********************************************************************** + **********************************************************************/ +static ib_api_status_t +pkey_mgr_update_pkey_entry( + IN const osm_req_t *p_req, + IN const osm_physp_t *p_physp, + IN const ib_pkey_table_t *block, + IN const uint16_t block_index ) +{ + osm_madw_context_t context; + osm_node_t *p_node = osm_physp_get_node_ptr( p_physp ); + uint32_t attr_mod; - OSM_LOG_EXIT( p_mgr->p_log ); - return ( status ); + context.pkey_context.node_guid = osm_node_get_node_guid( p_node ); + context.pkey_context.port_guid = osm_physp_get_port_guid( p_physp ); + context.pkey_context.set_method = TRUE; + attr_mod = block_index; + if ( osm_node_get_type( p_node ) == IB_NODE_TYPE_SWITCH ) + attr_mod |= osm_physp_get_port_num( p_physp ) << 16; + return osm_req_set( p_req, osm_physp_get_dr_path_ptr( p_physp ), + ( uint8_t * ) block, sizeof( *block ), + IB_MAD_ATTR_P_KEY_TABLE, + cl_hton32( attr_mod ), CL_DISP_MSGID_NONE, &context ); } /********************************************************************** **********************************************************************/ -boolean_t -__osm_pkey_mgr_process_physical_port( - IN const osm_pkey_mgr_t * const p_mgr, - IN osm_node_t * p_node, - IN uint8_t port_num, - IN osm_physp_t * p_physp ) +static boolean_t +pkey_mgr_enforce_partition( + IN osm_log_t *p_log, + IN const osm_req_t *p_req, + IN const osm_physp_t *p_physp, + IN const boolean_t enforce) { - boolean_t return_val = FALSE; /* TRUE if IB_DEFAULT_PKEY was inserted */ - osm_madw_context_t context; - ib_pkey_table_t *block = NULL; - uint16_t block_index; - uint16_t num_of_blocks; - const osm_pkey_tbl_t *p_pkey_tbl; - uint32_t attr_mod; - uint32_t i; - ib_net16_t pkey; - ib_api_status_t status; - boolean_t block_with_empty_entry_found; - - OSM_LOG_ENTER( p_mgr->p_log, __osm_pkey_mgr_process_physical_port ); - - /* - * Send a new entry for the pkey table for this node that includes - * IB_DEFAULT_PKEY when IB_DEFAULT_PARTIAL_PKEY or IB_DEFAULT_PKEY - * don't exist - */ - if ( ( osm_physp_has_pkey( p_mgr->p_log, - IB_DEFAULT_PKEY, - p_physp ) == FALSE ) && - ( osm_physp_has_pkey( p_mgr->p_log, - IB_DEFAULT_PARTIAL_PKEY, p_physp ) == FALSE ) ) + osm_madw_context_t context; + uint8_t payload[IB_SMP_DATA_SIZE]; + ib_port_info_t *p_pi; + ib_api_status_t status; + + if (!(p_pi = osm_physp_get_port_info_ptr( p_physp ))) + { + osm_log( p_log, OSM_LOG_ERROR, + "pkey_mgr_enforce_partition: ERR 0507: " + "No port info for " + "node 0x%016" PRIx64 " port %u\n", + cl_ntoh64( + osm_node_get_node_guid( + osm_physp_get_node_ptr( p_physp ))), + osm_physp_get_port_num( p_physp ) ); + return FALSE; + } + + if ((p_pi->vl_enforce & 0xc) == (0xc)*(enforce == TRUE)) + { + osm_log( p_log, OSM_LOG_DEBUG, + "pkey_mgr_enforce_partition: " + "No need to update PortInfo for " + "node 0x%016" PRIx64 " port %u\n", + cl_ntoh64( + osm_node_get_node_guid( + osm_physp_get_node_ptr( p_physp ))), + osm_physp_get_port_num( p_physp ) ); + return FALSE; + } + + memset( payload, 0, IB_SMP_DATA_SIZE ); + memcpy( payload, p_pi, sizeof(ib_port_info_t) ); + + p_pi = (ib_port_info_t*)payload; + if (enforce == TRUE) + p_pi->vl_enforce |= 0xc; + else + p_pi->vl_enforce &= ~0xc; + p_pi->state_info2 = 0; + ib_port_info_set_port_state( p_pi, IB_LINK_NO_CHANGE ); + + context.pi_context.node_guid = + osm_node_get_node_guid( osm_physp_get_node_ptr( p_physp ) ); + context.pi_context.port_guid = osm_physp_get_port_guid( p_physp ); + context.pi_context.set_method = TRUE; + context.pi_context.update_master_sm_base_lid = FALSE; + context.pi_context.ignore_errors = FALSE; + context.pi_context.light_sweep = FALSE; + context.pi_context.active_transition = FALSE; + + status = osm_req_set( p_req, osm_physp_get_dr_path_ptr( p_physp ), + payload, sizeof(payload), + IB_MAD_ATTR_PORT_INFO, + cl_hton32( osm_physp_get_port_num( p_physp ) ), + CL_DISP_MSGID_NONE, &context ); + if (status != IB_SUCCESS) + { + osm_log( p_log, OSM_LOG_ERROR, + "pkey_mgr_enforce_partition: ERR 0511: " + "Failed to set PortInfo for " + "node 0x%016" PRIx64 " port %u\n", + cl_ntoh64( + osm_node_get_node_guid( + osm_physp_get_node_ptr( p_physp ))), + osm_physp_get_port_num( p_physp ) ); + return FALSE; + } + else + { + osm_log( p_log, OSM_LOG_DEBUG, + "pkey_mgr_enforce_partition: " + "Set PortInfo for " + "node 0x%016" PRIx64 " port %u\n", + cl_ntoh64( + osm_node_get_node_guid( + osm_physp_get_node_ptr( p_physp ))), + osm_physp_get_port_num( p_physp ) ); + return TRUE; + } +} + +/********************************************************************** + **********************************************************************/ +static boolean_t pkey_mgr_update_port( + osm_log_t *p_log, + osm_req_t *p_req, + const osm_port_t * const p_port ) +{ + osm_physp_t *p_physp; + osm_node_t *p_node; + ib_pkey_table_t *block, *new_block; + osm_pkey_tbl_t *p_pkey_tbl; + uint16_t block_index; + uint8_t pkey_index; + uint16_t last_free_block_index = 0; + uint8_t last_free_pkey_index = 0; + uint16_t num_of_blocks; + uint16_t max_num_of_blocks; + ib_api_status_t status; + boolean_t ret_val = FALSE; + osm_pending_pkey_t *p_pending; + boolean_t found; + ib_pkey_table_t empty_block; + + memset(&empty_block, 0, sizeof(ib_pkey_table_t)); + + p_physp = osm_port_get_default_phys_ptr( p_port ); + if ( !osm_physp_is_valid( p_physp ) ) + return FALSE; + + p_node = osm_physp_get_node_ptr( p_physp ); + p_pkey_tbl = osm_physp_get_mod_pkey_tbl( p_physp ); + num_of_blocks = osm_pkey_tbl_get_num_blocks( p_pkey_tbl ); + max_num_of_blocks = pkey_mgr_get_physp_max_blocks( p_req->p_subn, p_physp ); + if ( p_pkey_tbl->max_blocks > max_num_of_blocks ) + { + osm_log( p_log, OSM_LOG_INFO, + "pkey_mgr_update_port: " + "Max number of blocks reduced from %u to %u " + "for node 0x%016" PRIx64 " port %u\n", + p_pkey_tbl->max_blocks, max_num_of_blocks, + cl_ntoh64( osm_node_get_node_guid( p_node ) ), + osm_physp_get_port_num( p_physp ) ); + } + p_pkey_tbl->max_blocks = max_num_of_blocks; + + osm_pkey_tbl_init_new_blocks( p_pkey_tbl ); + p_pkey_tbl->used_blocks = 0; + + /* + process every pending pkey in order - + first must be "updated" last are "new" + */ + p_pending = (osm_pending_pkey_t *)cl_qlist_remove_head( &p_pkey_tbl->pending ); + while ( p_pending != (osm_pending_pkey_t *)cl_qlist_end( &p_pkey_tbl->pending )) + { + if (p_pending->is_new == FALSE) + { + block_index = p_pending->block; + pkey_index = p_pending->index; + found = TRUE; + } + else + { + found = osm_pkey_find_next_free_entry( p_pkey_tbl, + &last_free_block_index, + &last_free_pkey_index ); + if (!found) + { + osm_log( p_log, OSM_LOG_ERROR, + "pkey_mgr_update_port: ERR 0504: " + "Failed to find empty space for new pkey 0x%04x " + "for node 0x%016" PRIx64 " port %u\n", + cl_ntoh16( p_pending->pkey ), + cl_ntoh64( osm_node_get_node_guid( p_node )), + osm_physp_get_port_num( p_physp ) ); + } + else + { + block_index = last_free_block_index; + pkey_index = last_free_pkey_index++; + } + } + + if (found) { - context.pkey_context.node_guid = osm_node_get_node_guid( p_node ); - context.pkey_context.port_guid = osm_physp_get_port_guid( p_physp ); - context.pkey_context.set_method = TRUE; - - p_pkey_tbl = osm_physp_get_pkey_tbl( p_physp ); - num_of_blocks = osm_pkey_tbl_get_num_blocks( p_pkey_tbl ); - block_with_empty_entry_found = FALSE; - - for ( block_index = 0; block_index < num_of_blocks; block_index++ ) - { - block = osm_pkey_tbl_block_get( p_pkey_tbl, block_index ); - for ( i = 0; i < IB_NUM_PKEY_ELEMENTS_IN_BLOCK; i++ ) - { - pkey = block->pkey_entry[i]; - if ( ib_pkey_is_invalid( pkey ) ) - { - block->pkey_entry[i] = IB_DEFAULT_PKEY; - block_with_empty_entry_found = TRUE; - break; - } - } - if ( block_with_empty_entry_found ) - { - break; - } - } - - if ( block_with_empty_entry_found == FALSE ) - { - osm_log( p_mgr->p_log, OSM_LOG_ERROR, - "__osm_pkey_mgr_process_physical_port: ERR 0501: " - "No empty entry was found to insert IB_DEFAULT_PKEY for node " - "0x%016" PRIx64 " and port %u\n", - cl_ntoh64( osm_node_get_node_guid( p_node ) ), port_num ); - } + if (IB_SUCCESS != osm_pkey_tbl_set_new_entry( p_pkey_tbl, block_index, + pkey_index, p_pending->pkey )) + { + osm_log( p_log, OSM_LOG_ERROR, + "pkey_mgr_update_port: ERR 0505: " + "Failed to set PKey 0x%04x in block %u idx %u " + "for node 0x%016" PRIx64 " port %u\n", + p_pending->pkey, block_index, pkey_index, + cl_ntoh64( osm_node_get_node_guid( p_node ) ), + osm_physp_get_port_num( p_physp ) ); + } + } + + free(p_pending); + p_pending = (osm_pending_pkey_t *)cl_qlist_remove_head( &p_pkey_tbl->pending ); + } + + /* now look for changes and store */ + for (block_index = 0; block_index < num_of_blocks; block_index++) + { + block = osm_pkey_tbl_block_get( p_pkey_tbl, block_index ); + new_block = osm_pkey_tbl_new_block_get( p_pkey_tbl, block_index ); + if (!new_block) + new_block = &empty_block; + if (block && !memcmp( new_block, block, sizeof( *block ) )) + continue; + + status = pkey_mgr_update_pkey_entry( p_req, p_physp, new_block, block_index ); + if (status == IB_SUCCESS) + { + osm_log( p_log, OSM_LOG_DEBUG, + "pkey_mgr_update_port: " + "Updated " + "pkey table block %d for node 0x%016" PRIx64 " port %u\n", + block_index, + cl_ntoh64( osm_node_get_node_guid( p_node ) ), + osm_physp_get_port_num( p_physp ) ); + ret_val = TRUE; + } + else + { + osm_log( p_log, OSM_LOG_ERROR, + "pkey_mgr_update_port: ERR 0506: " + "pkey_mgr_update_pkey_entry() failed to update " + "pkey table block %d for node 0x%016" PRIx64 " port %u\n", + block_index, + cl_ntoh64( osm_node_get_node_guid( p_node ) ), + osm_physp_get_port_num( p_physp ) ); + } + } + + return ret_val; +} + +/********************************************************************** + **********************************************************************/ +static boolean_t +pkey_mgr_update_peer_port( + osm_log_t *p_log, + const osm_req_t *p_req, + const osm_subn_t *p_subn, + const osm_port_t * const p_port, + boolean_t enforce ) +{ + osm_physp_t *p_physp, *peer; + osm_node_t *p_node; + ib_pkey_table_t *block, *peer_block; + const osm_pkey_tbl_t *p_pkey_tbl; + osm_pkey_tbl_t *p_peer_pkey_tbl; + uint16_t block_index; + uint16_t num_of_blocks; + uint16_t peer_max_blocks; + ib_api_status_t status = IB_SUCCESS; + boolean_t ret_val = FALSE; + boolean_t port_info_set = FALSE; + ib_pkey_table_t empty_block; + + memset(&empty_block, 0, sizeof(ib_pkey_table_t)); + + p_physp = osm_port_get_default_phys_ptr( p_port ); + if (!osm_physp_is_valid( p_physp )) + return FALSE; + peer = osm_physp_get_remote( p_physp ); + if ( !peer || !osm_physp_is_valid( peer ) ) + return FALSE; + p_node = osm_physp_get_node_ptr( peer ); + if ( !p_node->sw || !p_node->sw->switch_info.enforce_cap ) + return FALSE; + + p_pkey_tbl = osm_physp_get_pkey_tbl( p_physp ); + p_peer_pkey_tbl = osm_physp_get_mod_pkey_tbl( peer ); + num_of_blocks = osm_pkey_tbl_get_num_blocks( p_pkey_tbl ); + peer_max_blocks = pkey_mgr_get_physp_max_blocks( p_subn, peer ); + if (peer_max_blocks < p_pkey_tbl->used_blocks) + { + osm_log( p_log, OSM_LOG_ERROR, + "pkey_mgr_update_peer_port: ERR 0508: " + "Not enough pkey entries (%u < %u) on switch 0x%016" PRIx64 + " port %u. Clearing Enforcement bit\n", + peer_max_blocks, num_of_blocks, + cl_ntoh64( osm_node_get_node_guid( p_node ) ), + osm_physp_get_port_num( peer ) ); + enforce = FALSE; + } + + if ( pkey_mgr_enforce_partition( p_log, p_req, peer, enforce ) ) + port_info_set = TRUE; + + if (enforce == FALSE) + return port_info_set; + + p_peer_pkey_tbl->used_blocks = p_pkey_tbl->used_blocks; + for (block_index = 0; block_index < p_pkey_tbl->used_blocks; block_index++) + { + block = osm_pkey_tbl_new_block_get( p_pkey_tbl, block_index ); + if (!block) + block = &empty_block; + + peer_block = osm_pkey_tbl_block_get( p_peer_pkey_tbl, block_index ); + if ( !peer_block || memcmp( peer_block, block, sizeof( *peer_block ) ) ) + { + status = pkey_mgr_update_pkey_entry( p_req, peer, block, block_index ); + if ( status == IB_SUCCESS ) + ret_val = TRUE; else - { - /* Building the attribute modifier */ - if ( osm_node_get_type( p_node ) == IB_NODE_TYPE_SWITCH ) - { - /* Port num | Block Index */ - attr_mod = port_num << 16 | block_index; - } - else - { - attr_mod = block_index; - } - - status = osm_req_set( p_mgr->p_req, - osm_physp_get_dr_path_ptr( p_physp ), - ( uint8_t * ) block, - sizeof( *block ), - IB_MAD_ATTR_P_KEY_TABLE, - cl_hton32( attr_mod ), - CL_DISP_MSGID_NONE, &context ); - return_val = TRUE; /*IB_DEFAULT_PKEY was inserted */ - - if ( osm_log_is_active( p_mgr->p_log, OSM_LOG_VERBOSE ) ) - { - osm_log( p_mgr->p_log, OSM_LOG_VERBOSE, - "__osm_pkey_mgr_process_physical_port: " - "IB_DEFAULT_PKEY was inserted for node 0x%016" PRIx64 - " and port %u\n", - cl_ntoh64( osm_node_get_node_guid( p_node ) ), - port_num ); - } - } - } - else - { - /* default key or partial default key already exist */ - if ( osm_log_is_active( p_mgr->p_log, OSM_LOG_VERBOSE ) ) - { - osm_log( p_mgr->p_log, OSM_LOG_VERBOSE, - "__osm_pkey_mgr_process_physical_port: " - "No need to insert IB_DEFAULT_PKEY for node 0x%016" PRIx64 - " port %u\n", - cl_ntoh64( osm_node_get_node_guid( p_node ) ), port_num ); - } - } - - OSM_LOG_EXIT( p_mgr->p_log ); - return ( return_val ); + osm_log( p_log, OSM_LOG_ERROR, + "pkey_mgr_update_peer_port: ERR 0509: " + "pkey_mgr_update_pkey_entry() failed to update " + "pkey table block %d for node 0x%016" PRIx64 + " port %u\n", + block_index, + cl_ntoh64( osm_node_get_node_guid( p_node ) ), + osm_physp_get_port_num( peer ) ); + } + } + + if ( (ret_val == TRUE) && osm_log_is_active( p_log, OSM_LOG_DEBUG ) ) + { + osm_log( p_log, OSM_LOG_DEBUG, + "pkey_mgr_update_peer_port: " + "Pkey table was updated for node 0x%016" PRIx64 + " port %u\n", + cl_ntoh64( osm_node_get_node_guid( p_node ) ), + osm_physp_get_port_num( peer ) ); + } + + if (port_info_set) + return TRUE; + return ret_val; } /********************************************************************** **********************************************************************/ osm_signal_t osm_pkey_mgr_process( - IN const osm_pkey_mgr_t * const p_mgr ) + IN osm_opensm_t *p_osm ) { - cl_qmap_t *p_node_guid_tbl; - osm_node_t *p_node; - osm_node_t *p_next_node; - uint8_t port_num; - osm_physp_t *p_physp; - osm_signal_t result = OSM_SIGNAL_DONE; + cl_qmap_t *p_tbl; + cl_map_item_t *p_next; + osm_prtn_t *p_prtn; + osm_port_t *p_port; + osm_signal_t signal = OSM_SIGNAL_DONE; + osm_node_t *p_node; - CL_ASSERT( p_mgr ); + CL_ASSERT( p_osm ); - OSM_LOG_ENTER( p_mgr->p_log, osm_pkey_mgr_process ); + OSM_LOG_ENTER( &p_osm->log, osm_pkey_mgr_process ); - p_node_guid_tbl = &p_mgr->p_subn->node_guid_tbl; + CL_PLOCK_EXCL_ACQUIRE( &p_osm->lock ); - CL_PLOCK_EXCL_ACQUIRE( p_mgr->p_lock ); + if ( osm_prtn_make_partitions( &p_osm->log, &p_osm->subn ) != IB_SUCCESS ) + { + osm_log( &p_osm->log, OSM_LOG_ERROR, + "osm_pkey_mgr_process: ERR 0510: " + "osm_prtn_make_partitions() failed\n" ); + goto _err; + } - p_next_node = ( osm_node_t * ) cl_qmap_head( p_node_guid_tbl ); - while ( p_next_node != ( osm_node_t * ) cl_qmap_end( p_node_guid_tbl ) ) - { - p_node = p_next_node; - p_next_node = ( osm_node_t * ) cl_qmap_next( &p_next_node->map_item ); - - for ( port_num = 0; port_num < osm_node_get_num_physp( p_node ); - port_num++ ) - { - p_physp = osm_node_get_physp_ptr( p_node, port_num ); - if ( osm_physp_is_valid( p_physp ) ) - { - if ( __osm_pkey_mgr_process_physical_port - ( p_mgr, p_node, port_num, p_physp ) ) - { - if ( osm_log_is_active( p_mgr->p_log, OSM_LOG_VERBOSE ) ) - { - osm_log( p_mgr->p_log, OSM_LOG_VERBOSE, - "osm_pkey_mgr_process: " - "Adding IB_DEFAULT_PKEY for pkey table of node " - "0x%016" PRIx64 " port %u\n", - cl_ntoh64( osm_node_get_node_guid( p_node ) ), - port_num ); - } - result = OSM_SIGNAL_DONE_PENDING; - } - } - } - } - - CL_PLOCK_RELEASE( p_mgr->p_lock ); - OSM_LOG_EXIT( p_mgr->p_log ); - return ( result ); + /* populate the pending pkey entries by scanning all partitions */ + p_tbl = &p_osm->subn.prtn_pkey_tbl; + p_next = cl_qmap_head( p_tbl ); + while ( p_next != cl_qmap_end( p_tbl ) ) + { + p_prtn = ( osm_prtn_t * ) p_next; + p_next = cl_qmap_next( p_next ); + pkey_mgr_process_partition_table( &p_osm->log, &p_osm->sm.req, + p_prtn, FALSE ); + pkey_mgr_process_partition_table( &p_osm->log, &p_osm->sm.req, + p_prtn, TRUE ); + } + + /* calculate and set new pkey tables */ + p_tbl = &p_osm->subn.port_guid_tbl; + p_next = cl_qmap_head( p_tbl ); + while ( p_next != cl_qmap_end( p_tbl ) ) + { + p_port = ( osm_port_t * ) p_next; + p_next = cl_qmap_next( p_next ); + if ( pkey_mgr_update_port( &p_osm->log, &p_osm->sm.req, p_port ) ) + signal = OSM_SIGNAL_DONE_PENDING; + p_node = osm_port_get_parent_node( p_port ); + if ( ( osm_node_get_type( p_node ) != IB_NODE_TYPE_SWITCH ) && + pkey_mgr_update_peer_port( &p_osm->log, &p_osm->sm.req, + &p_osm->subn, p_port, + !p_osm->subn.opt.no_partition_enforcement ) ) + signal = OSM_SIGNAL_DONE_PENDING; + } + + _err: + CL_PLOCK_RELEASE( &p_osm->lock ); + OSM_LOG_EXIT( &p_osm->log ); + return ( signal ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_pkey_rcv.c b/trunk/ulp/opensm/user/opensm/osm_pkey_rcv.c index 7897906a..47cbac6e 100644 --- a/trunk/ulp/opensm/user/opensm/osm_pkey_rcv.c +++ b/trunk/ulp/opensm/user/opensm/osm_pkey_rcv.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,12 +32,13 @@ */ + #if HAVE_CONFIG_H # include #endif /* HAVE_CONFIG_H */ +#include #include -#include #include #include #include @@ -59,7 +60,7 @@ void osm_pkey_rcv_construct( IN osm_pkey_rcv_t* const p_rcv ) { - cl_memclr( p_rcv, sizeof(*p_rcv) ); + memset( p_rcv, 0, sizeof(*p_rcv) ); } /********************************************************************** @@ -144,12 +145,11 @@ osm_pkey_rcv_process( if( p_port == (osm_port_t*)cl_qmap_end( p_guid_tbl) ) { - cl_plock_release( p_rcv->p_lock ); osm_log( p_rcv->p_log, OSM_LOG_ERROR, "osm_pkey_rcv_process: ERR 4806: " - "No Port object for port with GUID = 0x%" PRIx64 - "\n\t\t\t\tfor parent node GUID = 0x%" PRIx64 - ", TID = 0x%" PRIx64 "\n", + "No port object for port with GUID 0x%" PRIx64 + "\n\t\t\t\tfor parent node GUID 0x%" PRIx64 + ", TID 0x%" PRIx64 "\n", cl_ntoh64( port_guid ), cl_ntoh64( node_guid ), cl_ntoh64( p_smp->trans_id ) ); @@ -161,7 +161,7 @@ osm_pkey_rcv_process( block_num = (uint16_t)((cl_ntoh32(p_smp->attr_mod)) & 0x0000FFFF); /* in case of a non switch node the attr modifier should be ignored */ - if (osm_node_get_type( p_node ) == IB_NODE_TYPE_SWITCH) + if (osm_node_get_type( p_node ) == IB_NODE_TYPE_SWITCH) { port_num = (uint8_t)(((cl_ntoh32( p_smp->attr_mod)) & 0x00FF0000) >> 16 ); p_physp = osm_node_get_physp_ptr( p_node, port_num ); @@ -175,16 +175,16 @@ osm_pkey_rcv_process( CL_ASSERT( p_physp ); /* - We do not mind if this is a result of a set or get - all we want is to update - the subnet. + We do not mind if this is a result of a set or get - all we want is to + update the subnet. */ if( osm_log_is_active( p_rcv->p_log, OSM_LOG_VERBOSE ) ) { osm_log( p_rcv->p_log, OSM_LOG_VERBOSE, "osm_pkey_rcv_process: " - "Got GetResp(PKey) block:%u port_num %u with GUID = 0x%" PRIx64 - " for parent node GUID = 0x%" PRIx64 - ", TID = 0x%" PRIx64 "\n", + "Got GetResp(PKey) block:%u port_num %u with GUID 0x%" PRIx64 + " for parent node GUID 0x%" PRIx64 + ", TID 0x%" PRIx64 "\n", block_num, port_num, cl_ntoh64( port_guid ), cl_ntoh64( node_guid ), @@ -193,17 +193,14 @@ osm_pkey_rcv_process( /* Determine if we encountered a new Physical Port. - If so, Ignore it. + If so, ignore it. */ if( !osm_physp_is_valid( p_physp ) ) { - if( osm_log_is_active( p_rcv->p_log, OSM_LOG_VERBOSE ) ) - { - osm_log( p_rcv->p_log, OSM_LOG_ERROR, - "osm_pkey_rcv_process: ERR 4807: " - "Got invalid port number 0x%X\n", - port_num ); - } + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "osm_pkey_rcv_process: ERR 4807: " + "Got invalid port number 0x%X\n", + port_num ); goto Exit; } @@ -213,7 +210,7 @@ osm_pkey_rcv_process( OSM_LOG_DEBUG ); osm_physp_set_pkey_tbl( p_rcv->p_log, p_rcv->p_subn, - p_physp, p_pkey_tbl, block_num); + p_physp, p_pkey_tbl, block_num ); Exit: cl_plock_release( p_rcv->p_lock ); diff --git a/trunk/ulp/opensm/user/opensm/osm_pkey_rcv_ctrl.c b/trunk/ulp/opensm/user/opensm/osm_pkey_rcv_ctrl.c index e37f1e22..ca7fe0ad 100644 --- a/trunk/ulp/opensm/user/opensm/osm_pkey_rcv_ctrl.c +++ b/trunk/ulp/opensm/user/opensm/osm_pkey_rcv_ctrl.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,15 +32,11 @@ */ -/* - Next available error code: 0x203 -*/ - #if HAVE_CONFIG_H # include #endif /* HAVE_CONFIG_H */ -#include +#include #include #include @@ -62,7 +58,7 @@ void osm_pkey_rcv_ctrl_construct( IN osm_pkey_rcv_ctrl_t* const p_ctrl ) { - cl_memclr( p_ctrl, sizeof(*p_ctrl) ); + memset( p_ctrl, 0, sizeof(*p_ctrl) ); p_ctrl->h_disp = CL_DISP_INVALID_HANDLE; } @@ -107,7 +103,7 @@ osm_pkey_rcv_ctrl_init( { osm_log( p_log, OSM_LOG_ERROR, "osm_pkey_rcv_ctrl_init: ERR 4901: " - "Dispatcher registration failed.\n" ); + "Dispatcher registration failed\n" ); status = IB_INSUFFICIENT_RESOURCES; goto Exit; } @@ -117,3 +113,4 @@ osm_pkey_rcv_ctrl_init( return( status ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_port.c b/trunk/ulp/opensm/user/opensm/osm_port.c index f7033591..9afd2e4c 100644 --- a/trunk/ulp/opensm/user/opensm/osm_port.c +++ b/trunk/ulp/opensm/user/opensm/osm_port.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Implementation of osm_physp_t. @@ -49,7 +50,7 @@ #endif /* HAVE_CONFIG_H */ #include -#include +#include #include #include #include @@ -64,7 +65,7 @@ void osm_physp_construct( IN osm_physp_t* const p_physp ) { - cl_memclr( p_physp, sizeof(*p_physp) ); + memset( p_physp, 0, sizeof(*p_physp) ); osm_dr_path_construct( &p_physp->dr_path ); cl_ptr_vector_construct( &p_physp->slvl_by_port ); osm_pkey_tbl_construct( &p_physp->pkeys ); @@ -84,13 +85,13 @@ osm_physp_destroy( /* free the SL2VL Tables */ num_slvl = cl_ptr_vector_get_size(&p_physp->slvl_by_port); for (i = 0; i < num_slvl; i++) - cl_free(cl_ptr_vector_get(&p_physp->slvl_by_port, i)); + free(cl_ptr_vector_get(&p_physp->slvl_by_port, i)); cl_ptr_vector_destroy(&p_physp->slvl_by_port); /* free the P_Key Tables */ osm_pkey_tbl_destroy( &p_physp->pkeys ); - cl_memclr( p_physp, sizeof(*p_physp) ); + memset( p_physp, 0, sizeof(*p_physp) ); osm_dr_path_construct( &p_physp->dr_path ); /* clear dr_path */ } } @@ -109,6 +110,7 @@ osm_physp_init( { uint16_t num_slvl, i; ib_slvl_table_t *p_slvl; + CL_ASSERT( p_node ); osm_physp_construct( p_physp ); @@ -138,7 +140,9 @@ osm_physp_init( cl_ptr_vector_init( &p_physp->slvl_by_port, num_slvl, 1); for (i = 0; i < num_slvl; i++) { - p_slvl = (ib_slvl_table_t *)cl_zalloc(sizeof(ib_slvl_table_t)); + p_slvl = (ib_slvl_table_t *)malloc(sizeof(ib_slvl_table_t)); + if (p_slvl) + memset(p_slvl, 0, sizeof(ib_slvl_table_t)); cl_ptr_vector_set(&p_physp->slvl_by_port, i, p_slvl); } @@ -189,7 +193,7 @@ osm_port_init( /* Get the pointers to the physical node objects "owned" by this logical port GUID. - For switches, all the ports are owned, for HCA's and routers, + For switches, all the ports are owned; for HCA's and routers, only the singular part that has this GUID is owned. */ p_port->default_port_num = 0xFF; @@ -234,9 +238,12 @@ osm_port_new( */ size = p_ni->num_ports; - p_port = cl_zalloc( sizeof(*p_port) + sizeof(void *) * size ); + p_port = malloc( sizeof(*p_port) + sizeof(void *) * size ); if( p_port != NULL ) + { + memset( p_port, 0, sizeof(*p_port) + sizeof(void *) * size ); osm_port_init( p_port, p_ni, p_parent_node ); + } return( p_port ); } @@ -253,7 +260,49 @@ osm_port_get_lid_range_ho( *p_min_lid = cl_ntoh16( osm_port_get_base_lid( p_port ) ); lmc = osm_port_get_lmc( p_port ); - *p_max_lid = (uint16_t)(*p_min_lid + (1 << lmc) - 1 ); + *p_max_lid = (uint16_t)(*p_min_lid + (1 << lmc) - 1); +} + +/********************************************************************** + **********************************************************************/ +ib_api_status_t +osm_get_port_by_base_lid( + IN const osm_subn_t* const p_subn, + IN const ib_net16_t lid, + IN OUT const osm_port_t** const pp_port ) +{ + ib_api_status_t status; + uint16_t base_lid; + uint8_t lmc; + + *pp_port = NULL; + + /* Loop on lmc from 0 up through max LMC possible */ + for (lmc = 0; lmc <= IB_PORT_LMC_MAX; lmc++) + { + /* Calculate a base LID assuming this is the real LMC */ + base_lid = cl_ntoh16(lid) & ~((1 << lmc) - 1); + + /* Look for a match */ + status = cl_ptr_vector_at( &p_subn->port_lid_tbl, + base_lid, + (void**)pp_port ); + if ((status == CL_SUCCESS) && (*pp_port != NULL)) + { + /* Determine if base LID "tested" is the real base LID */ + /* This is true if the LMC "tested" is the port's actual LMC */ + if (lmc == osm_port_get_lmc( *pp_port ) ) + { + status = IB_SUCCESS; + goto Found; + } + } + } + *pp_port = NULL; + status = IB_NOT_FOUND; + + Found: + return status; } /********************************************************************** @@ -501,7 +550,7 @@ osm_physp_calc_link_op_vls( { osm_log( p_log, OSM_LOG_DEBUG, "osm_physp_calc_link_op_vls: ERR 4102: " - "Invalid OP_VLS = 0. Forcing correction to 256\n" ); + "Invalid OP_VLS = 0. Forcing correction to 1 (VL0)\n" ); op_vls = 1; } @@ -511,17 +560,21 @@ osm_physp_calc_link_op_vls( inline uint64_t -__osm_ptr_to_key(void const *p) { +__osm_ptr_to_key(void const *p) +{ uint64_t k = 0; - cl_memcpy(&k, p, sizeof(void *)); + + memcpy(&k, p, sizeof(void *)); return k; } inline void * -__osm_key_to_ptr(uint64_t k) { +__osm_key_to_ptr(uint64_t k) +{ void *p = 0; - cl_memcpy(&p, &k, sizeof(void *)); + + memcpy(&p, &k, sizeof(void *)); return p; } @@ -646,7 +699,7 @@ __osm_physp_update_new_dr_path( __osm_ptr_to_key(p_physp) ); } - cl_memclr( path_array, sizeof(path_array) ); + memset( path_array, 0, sizeof(path_array) ); p_physp = (osm_physp_t*)cl_list_remove_head( &tmpPortsList ); while ( p_physp != NULL ) { @@ -700,7 +753,7 @@ osm_physp_replace_dr_path_with_alternate_dr_path( BFS from OSM port until we find the target physp but avoid going through mapped ports */ - p_nextPortsList = (cl_list_t*)cl_malloc(sizeof(cl_list_t)); + p_nextPortsList = (cl_list_t*)malloc(sizeof(cl_list_t)); cl_list_construct( p_nextPortsList ); cl_list_init( p_nextPortsList, 10 ); @@ -735,7 +788,7 @@ osm_physp_replace_dr_path_with_alternate_dr_path( { next_list_is_full = FALSE; p_currPortsList = p_nextPortsList; - p_nextPortsList = (cl_list_t*)cl_malloc(sizeof(cl_list_t)); + p_nextPortsList = (cl_list_t*)malloc(sizeof(cl_list_t)); cl_list_construct( p_nextPortsList ); cl_list_init( p_nextPortsList, 10 ); p_physp = (osm_physp_t*)cl_list_remove_head( p_currPortsList ); @@ -800,13 +853,13 @@ osm_physp_replace_dr_path_with_alternate_dr_path( } } cl_list_destroy( p_currPortsList ); - cl_free(p_currPortsList); + free(p_currPortsList); } /* cleanup */ Exit: cl_list_destroy( p_nextPortsList ); - cl_free( p_nextPortsList ); + free( p_nextPortsList ); cl_map_destroy( &physp_map ); cl_map_destroy( &visited_map ); } @@ -837,7 +890,6 @@ osm_physp_set_pkey_tbl( IN uint16_t block_num ) { uint16_t max_blocks; - osm_switch_t* p_switch; CL_ASSERT( p_pkey_tbl ); CL_ASSERT( osm_physp_is_valid( p_physp ) ); @@ -846,16 +898,15 @@ osm_physp_set_pkey_tbl( limited by the size of the P_Key table specified by the PartitionCap on the node. */ - if (osm_node_get_type( p_physp->p_node ) != IB_NODE_TYPE_SWITCH || - p_physp->port_num == 0 ) + if (!p_physp->p_node->sw || p_physp->port_num == 0 ) { /* The maximum blocks is defined in the node info: partition cap for CA, routers and switch management ports. */ - max_blocks = (cl_ntoh16(p_physp->p_node->node_info.partition_cap)+ - IB_NUM_PKEY_ELEMENTS_IN_BLOCK -1) - / IB_NUM_PKEY_ELEMENTS_IN_BLOCK ; + max_blocks = (cl_ntoh16(p_physp->p_node->node_info.partition_cap) + + IB_NUM_PKEY_ELEMENTS_IN_BLOCK - 1) + / IB_NUM_PKEY_ELEMENTS_IN_BLOCK; } else { @@ -863,20 +914,9 @@ osm_physp_set_pkey_tbl( This is a switch, and not a management port. The maximum blocks is defined in the switch info: partition enforcement cap. */ - p_switch = - osm_get_switch_by_guid(p_subn, p_physp->p_node->node_info.node_guid); - if (! p_switch) - { - osm_log( p_log, OSM_LOG_ERROR, - "osm_physp_set_pkey_tbl: ERR 4107: " - "Cannot find switch by guid: %" PRIx64 "\n", - cl_ntoh64(p_physp->p_node->node_info.node_guid) ); - return; - } - max_blocks = - (cl_ntoh16(p_switch->switch_info.enforce_cap) + - IB_NUM_PKEY_ELEMENTS_IN_BLOCK -1) / IB_NUM_PKEY_ELEMENTS_IN_BLOCK ; + (cl_ntoh16(p_physp->p_node->sw->switch_info.enforce_cap) + + IB_NUM_PKEY_ELEMENTS_IN_BLOCK - 1) / IB_NUM_PKEY_ELEMENTS_IN_BLOCK; } if ( block_num >= max_blocks ) @@ -884,7 +924,7 @@ osm_physp_set_pkey_tbl( osm_log( p_log, OSM_LOG_ERROR, "osm_physp_set_pkey_tbl: ERR 4108: " "Got illegal set for block number:%u " - "For GUID: %" PRIx64 " port number:%u\n", + "For GUID: %" PRIx64 " port number:0x%X\n", block_num, cl_ntoh64(p_physp->p_node->node_info.node_guid), p_physp->port_num ); @@ -893,3 +933,4 @@ osm_physp_set_pkey_tbl( osm_pkey_tbl_set( &p_physp->pkeys, block_num, p_pkey_tbl); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_port_info_rcv.c b/trunk/ulp/opensm/user/opensm/osm_port_info_rcv.c index a460bf23..0b4c3462 100644 --- a/trunk/ulp/opensm/user/opensm/osm_port_info_rcv.c +++ b/trunk/ulp/opensm/user/opensm/osm_port_info_rcv.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Implementation of osm_pi_rcv_t. @@ -48,8 +49,8 @@ # include #endif /* HAVE_CONFIG_H */ +#include #include -#include #include #include #include @@ -115,7 +116,7 @@ __osm_pi_rcv_process_endport( port_guid = osm_physp_get_port_guid( p_physp ); - /* HACK should we track extended port 0 too? */ + /* HACK extended port 0 should be handled too! */ if (osm_physp_get_port_num( p_physp ) != 0) { /* track the minimal endport MTU and rate */ @@ -186,7 +187,7 @@ __osm_pi_rcv_process_endport( { osm_log( p_rcv->p_log, OSM_LOG_VERBOSE, "__osm_pi_rcv_process_endport: " - "Detected another SM. Requesting SMInfo." + "Detected another SM. Requesting SMInfo" "\n\t\t\t\tPort 0x%" PRIx64 "\n", cl_ntoh64( port_guid ) ); } @@ -195,7 +196,7 @@ __osm_pi_rcv_process_endport( This port indicates it's an SM and it's not our own port. Acquire the SMInfo Attribute. */ - cl_memclr( &context, sizeof(context) ); + memset( &context, 0, sizeof(context) ); context.smi_context.set_method = FALSE; status = osm_req_get( p_rcv->p_req, osm_physp_get_dr_path_ptr( p_physp ), @@ -292,13 +293,10 @@ __osm_pi_rcv_process_switch_port( { path = *osm_physp_get_dr_path_ptr( p_physp ); - osm_dr_path_extend( &path, - osm_physp_get_port_num( p_physp ) ); + osm_dr_path_extend( &path, osm_physp_get_port_num( p_physp ) ); - context.ni_context.node_guid = - osm_node_get_node_guid( p_node ); - context.ni_context.port_num = - osm_physp_get_port_num( p_physp ); + context.ni_context.node_guid = osm_node_get_node_guid( p_node ); + context.ni_context.port_num = osm_physp_get_port_num( p_physp ); status = osm_req_get( p_rcv->p_req, &path, @@ -350,6 +348,13 @@ __osm_pi_rcv_process_switch_port( "__osm_pi_rcv_process_switch_port: ERR 0F04: " "Invalid base LID 0x%x corrected\n", cl_ntoh16( orig_lid ) ); + /* Determine if base switch port 0 */ + if (p_node->sw && + !ib_switch_info_is_enhanced_port0(&p_node->sw->switch_info)) + { + /* PortState is not used on BSP0 but just in case it is DOWN */ + p_physp->port_info = *p_pi; + } __osm_pi_rcv_process_endport(p_rcv, p_physp, p_pi); } @@ -372,6 +377,7 @@ __osm_pi_rcv_process_ca_port( UNUSED_PARAM( p_node ); osm_physp_set_port_info( p_physp, p_pi ); + if ( (orig_lid = osm_physp_trim_base_lid_to_valid_range( p_physp ) ) ) osm_log( p_rcv->p_log, OSM_LOG_ERROR, "__osm_pi_rcv_process_ca_port: ERR 0F08: " @@ -402,6 +408,7 @@ __osm_pi_rcv_process_router_port( Update the PortInfo attribute. */ osm_physp_set_port_info( p_physp, p_pi ); + if ( (orig_lid = osm_physp_trim_base_lid_to_valid_range( p_physp ) ) ) osm_log( p_rcv->p_log, OSM_LOG_ERROR, "__osm_pi_rcv_process_router_port: ERR 0F09: " @@ -429,9 +436,8 @@ void osm_pkey_get_tables( uint8_t port_num; uint16_t block_num, max_blocks; uint32_t attr_mod_ho; - osm_switch_t* p_switch; - OSM_LOG_ENTER( p_log, osm_physp_has_pkey ); + OSM_LOG_ENTER( p_log, osm_pkey_get_tables ); path = *osm_physp_get_dr_path_ptr( p_physp ); @@ -443,39 +449,28 @@ void osm_pkey_get_tables( port_num = p_physp->port_num; - if (osm_node_get_type( p_node ) != IB_NODE_TYPE_SWITCH || - port_num == 0 ) + if (!p_node->sw || port_num == 0) { - /* The maximum blocks is defined by the node info partition cap for CA, routers and - switch management ports. */ + /* The maximum blocks is defined by the node info partition cap for CA, + router, and switch management ports. */ max_blocks = (cl_ntoh16(p_node->node_info.partition_cap)+IB_NUM_PKEY_ELEMENTS_IN_BLOCK -1) / IB_NUM_PKEY_ELEMENTS_IN_BLOCK ; } else { - /* This is a switch, and not a management port. The maximum blocks is defined - in the switch info partition enforcement cap. */ - p_switch = osm_get_switch_by_guid(p_subn, p_node->node_info.node_guid); - - if (! p_switch) - { - osm_log( p_log, OSM_LOG_ERROR, - "osm_physp_has_pkey: ERR 0F11: " - "Cannot find switch by guid: %" PRIx64 "\n", - cl_ntoh64(p_node->node_info.node_guid) ); - goto Exit; - } + /* This is a switch, and not a management port. The maximum blocks + is defined in the switch info partition enforcement cap. */ /* Check for IBM eHCA firmware defect in reporting partition enforcement cap */ if (cl_ntoh32(ib_node_info_get_vendor_id(&p_node->node_info)) == IBM_VENDOR_ID) - p_switch->switch_info.enforce_cap = 0; + p_node->sw->switch_info.enforce_cap = 0; /* Bail out if this is a switch with no partition enforcement capability */ - if (cl_ntoh16(p_switch->switch_info.enforce_cap) == 0) + if (cl_ntoh16(p_node->sw->switch_info.enforce_cap) == 0) goto Exit; - max_blocks = (cl_ntoh16(p_switch->switch_info.enforce_cap)+IB_NUM_PKEY_ELEMENTS_IN_BLOCK -1) - / IB_NUM_PKEY_ELEMENTS_IN_BLOCK ; + max_blocks = (cl_ntoh16(p_node->sw->switch_info.enforce_cap) + + IB_NUM_PKEY_ELEMENTS_IN_BLOCK -1) / IB_NUM_PKEY_ELEMENTS_IN_BLOCK ; } for (block_num = 0 ; block_num < max_blocks ; block_num++) @@ -507,7 +502,7 @@ void osm_pkey_get_tables( /********************************************************************** **********************************************************************/ -void +static void __osm_pi_rcv_get_pkey_slvl_vla_tables( IN const osm_pi_rcv_t* const p_rcv, IN osm_node_t* const p_node, @@ -527,7 +522,7 @@ void osm_pi_rcv_construct( IN osm_pi_rcv_t* const p_rcv ) { - cl_memclr( p_rcv, sizeof(*p_rcv) ); + memset( p_rcv, 0, sizeof(*p_rcv) ); } /********************************************************************** @@ -583,6 +578,7 @@ osm_pi_rcv_process_set( ib_smp_t *p_smp; ib_port_info_t *p_pi; osm_pi_context_t *p_context; + osm_log_level_t level; OSM_LOG_ENTER( p_rcv->p_log, osm_pi_rcv_process_set ); @@ -602,26 +598,41 @@ osm_pi_rcv_process_set( /* check for error */ if (!p_context->ignore_errors && (cl_ntoh16(p_smp->status) & 0x7fff)) { - osm_log( p_rcv->p_log, OSM_LOG_ERROR, - "osm_pi_rcv_process_set: ERR 0F10: " - "Received error status for SetResp()\n"); + /* If port already ACTIVE, don't treat status 7 as error */ + if (p_context->active_transition && + (cl_ntoh16(p_smp->status) & 0x7fff) == 0x1c) + { + level = OSM_LOG_INFO; + osm_log( p_rcv->p_log, OSM_LOG_INFO, + "osm_pi_rcv_process_set: " + "Received error status 0x%x for SetResp() during ACTIVE transition\n", + cl_ntoh16(p_smp->status) & 0x7fff); + /* Should there be a subsequent Get to validate that port is ACTIVE ? */ + } + else + { + level = OSM_LOG_ERROR; + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "osm_pi_rcv_process_set: ERR 0F10: " + "Received error status for SetResp()\n"); + } osm_dump_port_info( p_rcv->p_log, osm_node_get_node_guid( p_node ), port_guid, port_num, p_pi, - OSM_LOG_ERROR); + level); } if( osm_log_is_active( p_rcv->p_log, OSM_LOG_DEBUG ) ) { osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "osm_pi_rcv_process_set: " - "Received logical SetResp() for GUID = 0x%" PRIx64 - ", port num = %u" - "\n\t\t\t\tfor parent node GUID = 0x%" PRIx64 - " TID = 0x%" PRIx64 "\n", + "Received logical SetResp() for GUID 0x%" PRIx64 + ", port num 0x%X" + "\n\t\t\t\tfor parent node GUID 0x%" PRIx64 + " TID 0x%" PRIx64 "\n", cl_ntoh64( port_guid ), port_num, cl_ntoh64( osm_node_get_node_guid( p_node ) ), @@ -664,14 +675,16 @@ osm_pi_rcv_process( p_context = osm_madw_get_pi_context_ptr( p_madw ); p_pi = (ib_port_info_t*)ib_smp_get_payload_ptr( p_smp ); - /* On receive of client reregister - clear the reregister bit - so - reregistering won't be sent again and again*/ - if (ib_port_info_get_client_rereg(p_pi)) + CL_ASSERT( p_smp->attr_id == IB_MAD_ATTR_PORT_INFO ); + + /* On receipt of client reregister, clear the reregister bit so + reregistering won't be sent again and again */ + if ( ib_port_info_get_client_rereg( p_pi ) ) { - osm_log( p_rcv->p_log, OSM_LOG_DEBUG, - "osm_pi_rcv_process: " - "client reregister received on response\n"); - ib_port_info_set_client_rereg(p_pi,0); + osm_log( p_rcv->p_log, OSM_LOG_DEBUG, + "osm_pi_rcv_process: " + "Client reregister received on response\n"); + ib_port_info_set_client_rereg( p_pi, 0 ); } port_num = (uint8_t)cl_ntoh32( p_smp->attr_mod ); @@ -679,10 +692,9 @@ osm_pi_rcv_process( port_guid = p_context->port_guid; node_guid = p_context->node_guid; - CL_ASSERT( p_smp->attr_id == IB_MAD_ATTR_PORT_INFO ); - - osm_dump_port_info( - p_rcv->p_log, node_guid, port_guid, port_num, p_pi, OSM_LOG_DEBUG); + osm_dump_port_info( p_rcv->p_log, + node_guid, port_guid, port_num, p_pi, + OSM_LOG_DEBUG ); /* we might get a response during a light sweep looking for a change in @@ -694,8 +706,9 @@ osm_pi_rcv_process( { osm_log( p_rcv->p_log, OSM_LOG_VERBOSE, "osm_pi_rcv_process: " - "Got light sweep response from remote port of parent node GUID = 0x%" PRIx64 - " port = %u, Commencing heavy sweep\n", + "Got light sweep response from remote port of parent node " + "GUID 0x%" PRIx64 " port 0x%016" PRIx64 + ", Commencing heavy sweep\n", cl_ntoh64( node_guid ), cl_ntoh64( port_guid ) ); osm_state_mgr_process( p_rcv->p_state_mgr, @@ -712,9 +725,9 @@ osm_pi_rcv_process( CL_PLOCK_RELEASE( p_rcv->p_lock ); osm_log( p_rcv->p_log, OSM_LOG_ERROR, "osm_pi_rcv_process: ERR 0F06: " - "No Port object for port with GUID = 0x%" PRIx64 - "\n\t\t\t\tfor parent node GUID = 0x%" PRIx64 - ", TID = 0x%" PRIx64 "\n", + "No port object for port with GUID 0x%" PRIx64 + "\n\t\t\t\tfor parent node GUID 0x%" PRIx64 + ", TID 0x%" PRIx64 "\n", cl_ntoh64( port_guid ), cl_ntoh64( node_guid ), cl_ntoh64( p_smp->trans_id ) ); @@ -748,9 +761,9 @@ osm_pi_rcv_process( { osm_log( p_rcv->p_log, OSM_LOG_VERBOSE, "osm_pi_rcv_process: " - "Discovered port num %u with GUID = 0x%" PRIx64 - " for parent node GUID = 0x%" PRIx64 - ", TID = 0x%" PRIx64 "\n", + "Discovered port num 0x%X with GUID 0x%" PRIx64 + " for parent node GUID 0x%" PRIx64 + ", TID 0x%" PRIx64 "\n", port_num, cl_ntoh64( port_guid ), cl_ntoh64( node_guid ), @@ -800,10 +813,6 @@ osm_pi_rcv_process( p_smp->hop_count, p_smp->initial_path ); } - osm_dump_port_info( p_rcv->p_log, - node_guid, port_guid, port_num, p_pi, - OSM_LOG_DEBUG ); - /* Check if the update_sm_base_lid in the context is TRUE. If it is - then update the master_sm_base_lid of the variable @@ -837,7 +846,7 @@ osm_pi_rcv_process( default: osm_log( p_rcv->p_log, OSM_LOG_ERROR, "osm_pi_rcv_process: ERR 0F07: " - "Unknown node type %u with GUID = 0x%" PRIx64 "\n", + "Unknown node type %u with GUID 0x%" PRIx64 "\n", osm_node_get_type( p_node ), cl_ntoh64( node_guid ) ); break; @@ -858,3 +867,4 @@ osm_pi_rcv_process( */ OSM_LOG_EXIT( p_rcv->p_log ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_port_info_rcv_ctrl.c b/trunk/ulp/opensm/user/opensm/osm_port_info_rcv_ctrl.c index b9862203..ff6a8a1c 100644 --- a/trunk/ulp/opensm/user/opensm/osm_port_info_rcv_ctrl.c +++ b/trunk/ulp/opensm/user/opensm/osm_port_info_rcv_ctrl.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Implementation of osm_pi_rcv_ctrl_t. @@ -44,15 +45,11 @@ * $Revision: 1.5 $ */ -/* - Next available error code: 0x203 -*/ - #if HAVE_CONFIG_H # include #endif /* HAVE_CONFIG_H */ -#include +#include #include #include @@ -74,7 +71,7 @@ void osm_pi_rcv_ctrl_construct( IN osm_pi_rcv_ctrl_t* const p_ctrl ) { - cl_memclr( p_ctrl, sizeof(*p_ctrl) ); + memset( p_ctrl, 0, sizeof(*p_ctrl) ); p_ctrl->h_disp = CL_DISP_INVALID_HANDLE; } @@ -128,3 +125,4 @@ osm_pi_rcv_ctrl_init( return( status ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_prtn.c b/trunk/ulp/opensm/user/opensm/osm_prtn.c new file mode 100644 index 00000000..4440553d --- /dev/null +++ b/trunk/ulp/opensm/user/opensm/osm_prtn.c @@ -0,0 +1,399 @@ +/* + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. + * + * This software is available to you under the OpenIB.org BSD license + * below: + * + * Redistribution and use in source and binary forms, with or + * without modification, are permitted provided that the following + * conditions are met: + * + * - Redistributions of source code must retain the above + * copyright notice, this list of conditions and the following + * disclaimer. + * + * - Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials + * provided with the distribution. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS + * BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN + * ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN + * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + * + * $Id$ + */ + + +/* + * Abstract: + * Implementation of osm_prtn_t. + * This object represents an IBA partition. + * This object is part of the opensm family of objects. + * + * Environment: + * Linux User Mode + * + * $Revision$ + */ + +#if HAVE_CONFIG_H +# include +#endif /* HAVE_CONFIG_H */ + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +extern int osm_prtn_config_parse_file(osm_log_t * const p_log, + osm_subn_t * const p_subn, + const char *file_name); + +static uint16_t global_pkey_counter; + +osm_prtn_t* osm_prtn_new( + IN const char *name, + IN const uint16_t pkey ) +{ + osm_prtn_t *p = malloc(sizeof(*p)); + if (!p) + return NULL; + + memset(p, 0, sizeof(*p)); + p->pkey = pkey; + p->sl = OSM_DEFAULT_SL; + cl_map_construct(&p->full_guid_tbl); + cl_map_init(&p->full_guid_tbl, 32); + cl_map_construct(&p->part_guid_tbl); + cl_map_init(&p->part_guid_tbl, 32); + + if (name && *name) + strncpy(p->name, name, sizeof(p->name)); + else + snprintf(p->name, sizeof(p->name), "%04x", cl_ntoh16(pkey)); + + return p; +} + +void osm_prtn_delete( + IN OUT osm_prtn_t** const pp_prtn ) +{ + osm_prtn_t *p = *pp_prtn; + + cl_map_remove_all(&p->full_guid_tbl); + cl_map_destroy(&p->full_guid_tbl); + cl_map_remove_all(&p->part_guid_tbl); + cl_map_destroy(&p->part_guid_tbl); + free(p); + *pp_prtn = NULL; +} + +ib_api_status_t osm_prtn_add_port(osm_log_t *p_log, osm_subn_t *p_subn, + osm_prtn_t *p, ib_net64_t guid, boolean_t full) +{ + cl_qmap_t *p_port_tbl = &p_subn->port_guid_tbl; + ib_api_status_t status = IB_SUCCESS; + cl_map_t *p_tbl; + osm_port_t *p_port; + osm_physp_t *p_physp; + + p_port = (osm_port_t *)cl_qmap_get(p_port_tbl, guid); + if (!p_port || p_port == (osm_port_t *)cl_qmap_end(p_port_tbl)) { + osm_log(p_log, OSM_LOG_VERBOSE, "osm_prtn_add_port: " + "port 0x%" PRIx64 " not found\n", + cl_ntoh64(guid)); + return status; + } + + p_physp = osm_port_get_default_phys_ptr(p_port); + if (!p_physp) { + osm_log(p_log, OSM_LOG_VERBOSE, "osm_prtn_add_port: " + "no physical for port 0x%" PRIx64 "\n", + cl_ntoh64(guid)); + return status; + } + + if (cl_map_remove(&p->part_guid_tbl, guid) || + cl_map_remove(&p->full_guid_tbl, guid)) { + osm_log(p_log, OSM_LOG_VERBOSE, "osm_prtn_add_port: " + "port 0x%" PRIx64 " already in " + "partition \'%s\' (0x%04x). Will overwrite\n", + cl_ntoh64(guid), p->name, cl_ntoh16(p->pkey)); + } + + p_tbl = (full == TRUE) ? &p->full_guid_tbl : &p->part_guid_tbl ; + + if (cl_map_insert(p_tbl, guid, p_physp) == NULL) + return IB_INSUFFICIENT_MEMORY; + + return status; +} + +ib_api_status_t osm_prtn_add_all(osm_log_t *p_log, osm_subn_t *p_subn, + osm_prtn_t *p, boolean_t full) +{ + cl_qmap_t *p_port_tbl = &p_subn->port_guid_tbl; + cl_map_item_t *p_item; + osm_port_t *p_port; + ib_api_status_t status = IB_SUCCESS; + + p_item = cl_qmap_head(p_port_tbl); + while (p_item != cl_qmap_end(p_port_tbl)) { + p_port = (osm_port_t *)p_item; + p_item = cl_qmap_next(p_item); + status = osm_prtn_add_port(p_log, p_subn, p, + osm_port_get_guid(p_port), full); + if (status != IB_SUCCESS) + goto _err; + } + + _err: + return status; +} + +static const ib_gid_t osm_ipoib_mgid = { + { + 0xff, /* multicast field */ + 0x12, /* non-permanent bit, link local scope */ + 0x40, 0x1b, /* IPv4 signature */ + 0xff, 0xff, /* 16 bits of P_Key (to be filled in) */ + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 48 bits of zeros */ + 0xff, 0xff, 0xff, 0xff, /* 32 bit IPv4 broadcast address */ + }, +}; + +/* + * HACK: Until TS resolves their noncompliant join compmask, + * we have to pre-define the MGID + */ +static const ib_gid_t osm_ts_ipoib_mgid = { + { + 0xff, /* multicast field */ + 0x12, /* non-permanent bit, link local scope */ + 0x40, 0x1b, /* IPv4 signature */ + 0xff, 0xff, /* 16 bits of P_Key (to be filled in) */ + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 48 bits of zeros */ + 0x00, 0x00, 0x00, 0x01, /* 32 bit IPv4 broadcast address */ + }, +}; + +ib_api_status_t osm_prtn_add_mcgroup(osm_log_t *p_log, + osm_subn_t *p_subn, osm_prtn_t *p, + unsigned is_ipoib, uint8_t rate, + uint8_t mtu, uint8_t scope) +{ + ib_member_rec_t mc_rec; + ib_net64_t comp_mask; + ib_net16_t pkey; + osm_mgrp_t *p_mgrp = NULL; + osm_sa_t *p_sa = &p_subn->p_osm->sa; + ib_api_status_t status = IB_SUCCESS; + uint8_t ts_scope; + + pkey = p->pkey | cl_hton16(0x8000); + + memset(&mc_rec, 0, sizeof(mc_rec)); + + mc_rec.mgid = osm_ipoib_mgid; /* ipv4 broadcast group */ + memcpy(&mc_rec.mgid.raw[4], &pkey, sizeof(pkey)); + + mc_rec.qkey = CL_HTON32(0x0b1b); + mc_rec.mtu = (mtu ? mtu : OSM_DEFAULT_MGRP_MTU) | (2 << 6); /* 2048 Bytes */ + mc_rec.tclass = 0; + mc_rec.pkey = pkey; + mc_rec.rate = (rate ? rate : OSM_DEFAULT_MGRP_RATE) | (2 << 6); /* 10Gb/sec */ + mc_rec.pkt_life = OSM_DEFAULT_SUBNET_TIMEOUT; + mc_rec.sl_flow_hop = ib_member_set_sl_flow_hop(p->sl, 0, 0); + /* Scope in MCMemberRecord needs to be consistent with MGID */ + mc_rec.scope_state = ib_member_set_scope_state(scope ? scope : OSM_DEFAULT_MGRP_SCOPE, MC_FULL_MEMBER); + ib_mgid_set_scope(&mc_rec.mgid, scope ? scope : OSM_DEFAULT_MGRP_SCOPE); + + /* don't update rate, mtu, scope */ + comp_mask = IB_MCR_COMPMASK_MTU | IB_MCR_COMPMASK_MTU_SEL + | IB_MCR_COMPMASK_RATE | IB_MCR_COMPMASK_RATE_SEL + | IB_MCR_COMPMASK_SCOPE; + status = osm_mcmr_rcv_find_or_create_new_mgrp(&p_sa->mcmr_rcv, + comp_mask, &mc_rec, &p_mgrp); + if (!p_mgrp || status != IB_SUCCESS) + osm_log( p_log, OSM_LOG_ERROR, + "osm_prtn_add_mcgroup: " + "Failed to create MC group with pkey 0x%04x\n", + cl_ntoh16(pkey)); + if (p_mgrp) + p_mgrp->well_known = TRUE; + + /* workaround for TS */ + /* FIXME: remove this upon TS fixes */ + mc_rec.mgid = osm_ts_ipoib_mgid; + memcpy(&mc_rec.mgid.raw[4], &pkey, sizeof(pkey)); + /* Scope in MCMemberRecord needs to be consistent with MGID */ + ts_scope = ib_mgid_get_scope(&osm_ts_ipoib_mgid); /* get scope from MGID */ + mc_rec.scope_state = ib_member_set_scope_state(ts_scope, MC_FULL_MEMBER); + status = osm_mcmr_rcv_find_or_create_new_mgrp(&p_sa->mcmr_rcv, + comp_mask, &mc_rec, &p_mgrp); + if (p_mgrp) + p_mgrp->well_known = TRUE; + + return status; +} + +static uint16_t __generate_pkey(osm_subn_t *p_subn) +{ + uint16_t pkey; + + cl_qmap_t *m = &p_subn->prtn_pkey_tbl; + while (global_pkey_counter < cl_ntoh16(IB_DEFAULT_PARTIAL_PKEY) - 1) { + pkey = ++global_pkey_counter; + pkey = cl_hton16(pkey); + if (cl_qmap_get(m, pkey) == cl_qmap_end(m)) + return pkey; + } + return 0; +} + +static osm_prtn_t *find_prtn_by_name(osm_subn_t *p_subn, const char *name) +{ + cl_map_item_t *p_next; + osm_prtn_t *p; + + p_next = cl_qmap_head(&p_subn->prtn_pkey_tbl); + while (p_next != cl_qmap_end(&p_subn->prtn_pkey_tbl)) { + p = (osm_prtn_t *)p_next; + p_next = cl_qmap_next(&p->map_item); + if (!strncmp(p->name, name, sizeof(p->name))) + return p; + } + + return NULL; +} + +osm_prtn_t *osm_prtn_make_new(osm_log_t *p_log, osm_subn_t *p_subn, + const char *name, uint16_t pkey) +{ + osm_prtn_t *p = NULL, *p_check; + + pkey &= cl_hton16((uint16_t)~0x8000); + + if (!pkey) { + if (name && (p = find_prtn_by_name(p_subn, name))) + return p; + if(!(pkey = __generate_pkey(p_subn))) + return NULL; + } + + p = osm_prtn_new(name, pkey); + if (!p) { + osm_log(p_log, OSM_LOG_ERROR, + "osm_prtn_make_new: Unable to create" + " partition \'%s\' (0x%04x)\n", + name, cl_ntoh16(pkey)); + return NULL; + } + + p_check = (osm_prtn_t *)cl_qmap_insert(&p_subn->prtn_pkey_tbl, + p->pkey, &p->map_item); + if (p != p_check) { + osm_log(p_log, OSM_LOG_VERBOSE, + "osm_prtn_make_new: Duplicated partition" + " definition: \'%s\' (0x%04x) prev name \'%s\'" + ". Will use it\n", + name, cl_ntoh16(pkey), p_check->name); + osm_prtn_delete(&p); + p = p_check; + } + + return p; +} + +static ib_api_status_t osm_prtn_make_default(osm_log_t * const p_log, + osm_subn_t * const p_subn, + boolean_t no_config) +{ + ib_api_status_t status = IB_UNKNOWN_ERROR; + osm_prtn_t *p; + + p = osm_prtn_make_new(p_log, p_subn, "Default", IB_DEFAULT_PARTIAL_PKEY); + if (!p) + goto _err; + status = osm_prtn_add_all(p_log, p_subn, p, no_config); + if (status != IB_SUCCESS) + goto _err; + cl_map_remove(&p->part_guid_tbl, p_subn->sm_port_guid); + status = osm_prtn_add_port(p_log, p_subn, p, p_subn->sm_port_guid, TRUE); + + if (no_config) + osm_prtn_add_mcgroup(p_log, p_subn, p, 1, 0, 0, 0); + + _err: + return status; +} + +ib_api_status_t osm_prtn_make_partitions(osm_log_t * const p_log, + osm_subn_t * const p_subn) +{ + struct stat statbuf; + const char *file_name; + boolean_t is_config = TRUE; + ib_api_status_t status = IB_SUCCESS; + cl_map_item_t *p_next; + osm_prtn_t *p; + + file_name = p_subn->opt.partition_config_file ? + p_subn->opt.partition_config_file : + "/etc/osm-partitions.conf"; + if (stat(file_name, &statbuf)) + is_config = FALSE; + + /* clean up current port maps */ + p_next = cl_qmap_head(&p_subn->prtn_pkey_tbl); + while (p_next != cl_qmap_end(&p_subn->prtn_pkey_tbl)) { + p = (osm_prtn_t *)p_next; + p_next = cl_qmap_next(&p->map_item); + cl_map_remove_all(&p->part_guid_tbl); + cl_map_remove_all(&p->full_guid_tbl); + } + + global_pkey_counter = 0; + + status = osm_prtn_make_default(p_log, p_subn, !is_config); + if (status != IB_SUCCESS) + goto _err; + + if (is_config && osm_prtn_config_parse_file(p_log, p_subn, file_name)) { + osm_log(p_log, OSM_LOG_VERBOSE, + "osm_prtn_make_partitions: Partition configuration " + "was not fully processed\n"); + } + + /* and now clean up empty partitions */ + p_next = cl_qmap_head(&p_subn->prtn_pkey_tbl); + while (p_next != cl_qmap_end(&p_subn->prtn_pkey_tbl)) { + p = (osm_prtn_t *)p_next; + p_next = cl_qmap_next(&p->map_item); + if (cl_map_count(&p->part_guid_tbl) == 0 && + cl_map_count(&p->full_guid_tbl) == 0) { + cl_qmap_remove_item(&p_subn->prtn_pkey_tbl, + (cl_map_item_t *)p); + osm_prtn_delete(&p); + } + } + + _err: + return status; +} + diff --git a/trunk/ulp/opensm/user/opensm/osm_prtn_config.c b/trunk/ulp/opensm/user/opensm/osm_prtn_config.c new file mode 100644 index 00000000..3d4411b2 --- /dev/null +++ b/trunk/ulp/opensm/user/opensm/osm_prtn_config.c @@ -0,0 +1,447 @@ +/* + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. + * + * This software is available to you under the OpenIB.org BSD license + * below: + * + * Redistribution and use in source and binary forms, with or + * without modification, are permitted provided that the following + * conditions are met: + * + * - Redistributions of source code must retain the above + * copyright notice, this list of conditions and the following + * disclaimer. + * + * - Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials + * provided with the distribution. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS + * BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN + * ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN + * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + * + * $Id$ + */ + + +/* + * Abstract: + * Implementation of opensm partition management configuration + * + * Environment: + * Linux User Mode + * + * $Revision$ + */ + +#if HAVE_CONFIG_H +# include +#endif /* HAVE_CONFIG_H */ + +#include +#include +#include +#include +#include + +#include +#include +#include +#include +#include + +#if __WORDSIZE == 64 +#define STRTO_IB_NET64(str, end, base) strtoul(str, end, base) +#else +#define STRTO_IB_NET64(str, end, base) strtoull(str, end, base) +#endif + +/* + */ +struct part_conf { + osm_log_t *p_log; + osm_subn_t *p_subn; + osm_prtn_t *p_prtn; + unsigned is_ipoib, mtu, rate, sl, scope; +}; + +extern osm_prtn_t *osm_prtn_make_new(osm_log_t *p_log, osm_subn_t *p_subn, + const char *name, uint16_t pkey); +extern ib_api_status_t osm_prtn_add_all(osm_log_t *p_log, + osm_subn_t *p_subn, + osm_prtn_t *p, boolean_t full); +extern ib_api_status_t osm_prtn_add_port(osm_log_t *p_log, + osm_subn_t *p_subn, osm_prtn_t *p, + ib_net64_t guid, boolean_t full); +extern ib_api_status_t osm_prtn_add_mcgroup(osm_log_t *p_log, + osm_subn_t *p_subn, osm_prtn_t *p, + unsigned is_ipoib, uint8_t rate, + uint8_t mtu, uint8_t scope); + +static int partition_create(unsigned lineno, struct part_conf *conf, + char *name, char *id, char *flag, char *flag_val) +{ + uint16_t pkey; + + if (!id && name && isdigit(*name)) { + id = name; + name = NULL; + } + + if (id) { + char *end; + + pkey = (uint16_t)strtoul(id, &end, 0); + if (end == id || *end) + return -1; + } else + pkey = 0; + + conf->p_prtn = osm_prtn_make_new(conf->p_log, conf->p_subn, + name, cl_hton16(pkey)); + if (!conf->p_prtn) + return -1; + + if (conf->p_subn->opt.no_qos) { + if (conf->sl != OSM_DEFAULT_SL) { + osm_log(conf->p_log, OSM_LOG_ERROR, + "partition_create: Overriding SL %d to default SL %d on partition %s as QoS not enabled\n", + conf->sl, OSM_DEFAULT_SL, name); + conf->sl = OSM_DEFAULT_SL; + } + } + conf->p_prtn->sl = (uint8_t)conf->sl; + + if (conf->is_ipoib) + osm_prtn_add_mcgroup(conf->p_log, conf->p_subn, conf->p_prtn, + conf->is_ipoib, (uint8_t)conf->rate, + (uint8_t)conf->mtu, (uint8_t)conf->scope); + + return 0; +} + +static int partition_add_flag(unsigned lineno, struct part_conf *conf, + char *flag, char *val) +{ + int len = strlen(flag); + if (!strncmp(flag, "ipoib", len)) { + conf->is_ipoib = 1; + } else if (!strncmp(flag, "mtu", len)) { + if (!val || (conf->mtu = strtoul(val, NULL, 0)) == 0) + osm_log(conf->p_log, OSM_LOG_VERBOSE, + "PARSE WARN: line %d: " + "flag \'mtu\' requires valid value" + " - skipped\n", lineno); + } else if (!strncmp(flag, "rate", len)) { + if (!val || (conf->rate = strtoul(val, NULL, 0)) == 0) + osm_log(conf->p_log, OSM_LOG_VERBOSE, + "PARSE WARN: line %d: " + "flag \'rate\' requires valid value" + " - skipped\n", lineno); + } else if (!strncmp(flag, "scope", len)) { + if (!val || (conf->scope = strtoul(val, NULL, 0)) == 0) + osm_log(conf->p_log, OSM_LOG_VERBOSE, + "PARSE WARN: line %d: " + "flag \'scope\' requires valid value" + " - skipped\n", lineno); + } else if (!strncmp(flag, "sl", len)) { + unsigned sl; + char *end; + + if (!val || !*val || (sl = strtoul(val, &end, 0)) > 15 || + (*end && !isspace(*end))) + osm_log(conf->p_log, OSM_LOG_VERBOSE, + "PARSE WARN: line %d: " + "flag \'sl\' requires valid value" + " - skipped\n", lineno); + else + conf->sl = sl; + } else { + osm_log(conf->p_log, OSM_LOG_VERBOSE, + "PARSE WARN: line %d: " + "unrecognized partition flag \'%s\'" + " - ignored\n", lineno, flag); + } + return 0; +} + +static int partition_add_port(unsigned lineno, struct part_conf *conf, + char *name, char *flag) +{ + osm_prtn_t *p = conf->p_prtn; + ib_net64_t guid; + boolean_t full = FALSE; + + if (!name || !*name || !strncmp(name, "NONE", strlen(name))) + return 0; + + if (flag) { + if (!strncmp(flag, "full", strlen(flag))) + full = TRUE; + else if (strncmp(flag, "limited", strlen(flag))) { + osm_log(conf->p_log, OSM_LOG_VERBOSE, + "PARSE WARN: line %d: " + "unrecognized port flag \'%s\'." + " Assume \'limited\'\n", lineno, flag); + } + } + + if (!strncmp(name, "ALL", strlen(name))) { + return osm_prtn_add_all(conf->p_log, conf->p_subn, p, + full) == IB_SUCCESS ? 0 : -1; + } else if (!strncmp(name, "SELF", strlen(name))) { + guid = cl_ntoh64(conf->p_subn->sm_port_guid); + } else { + char *end; + guid = STRTO_IB_NET64(name, &end, 0); + if (!guid || *end) + return -1; + } + + if (osm_prtn_add_port(conf->p_log, conf->p_subn, p, + cl_hton64(guid), full) != IB_SUCCESS) + return -1; + + return 0; +} + +/* conf file parser */ + +#define STRIP_HEAD_SPACES(p) while (*(p) == ' ' || *(p) == '\t' || \ + *(p) == '\n') { (p)++; } +#define STRIP_TAIL_SPACES(p) { char *q = (p) + strlen(p); \ + while ( q != (p) && ( *q == '\0' || \ + *q == ' ' || *q == '\t' || \ + *q == '\n')) { *q-- = '\0'; }; } + +static int parse_name_token(char *str, char **name, char **val) +{ + int len = 0; + char *p, *q; + + *name = *val = NULL; + + p = str; + + while (*p == ' ' || *p == '\t' || *p == '\n') + p++; + + q = strchr(p, '='); + if (q) + *q++ = '\0'; + + len = strlen(str) + 1; + str = q; + + q = p + strlen(p); + while ( q != p && + ( *q == '\0' || *q == ' ' || *q == '\t' || *q == '\n')) + *q-- = '\0'; + + *name = p; + + p = str; + if (!p) + return len; + + while (*p == ' ' || *p == '\t' || *p == '\n') + p++; + + q = p + strlen(p); + len += (int)(q - str) + 1; + while ( q != p && + ( *q == '\0' || *q == ' ' || *q == '\t' || *q == '\n')) + *q-- = '\0'; + *val = p; + + return len; +} + +static struct part_conf *new_part_conf(osm_log_t *p_log, osm_subn_t *p_subn) +{ + static struct part_conf part; + struct part_conf *conf = ∂ + + memset(conf, 0, sizeof(*conf)); + conf->p_log = p_log; + conf->p_subn = p_subn; + conf->p_prtn = NULL; + conf->is_ipoib = 0; + conf->sl = OSM_DEFAULT_SL; + return conf; +} + +static int flush_part_conf(struct part_conf *conf) +{ + memset(conf, 0, sizeof(*conf)); + return 0; +} + +static int parse_part_conf(struct part_conf *conf, char *str, int lineno) +{ + int ret, len = 0; + char *name, *id, *flag, *flval; + char *q, *p; + + p = str; + if (*p == '\t' || *p == '\0' || *p == '\n') + p++; + + len += (int)(p - str); + str = p; + + if (conf->p_prtn) + goto skip_header; + + q = strchr(p, ':'); + if (!q) { + osm_log(conf->p_log, OSM_LOG_ERROR, + "PARSE ERROR: line %d: " + "no partition definition found\n", lineno); + fprintf(stderr, "\nPARSE ERROR: line %d: " + "no partition definition found\n", lineno); + return -1; + } + + *q++ = '\0'; + str = q; + + name = id = flag = flval = NULL; + + q = strchr(p, ','); + if (q) + *q = '\0'; + + ret = parse_name_token(p, &name, &id); + p += ret; + len += ret; + + while (q) { + flag = flval = NULL; + q = strchr(p, ','); + if (q) + *q++ = '\0'; + ret = parse_name_token(p, &flag, &flval); + if (!flag) { + osm_log(conf->p_log, OSM_LOG_ERROR, + "PARSE ERROR: line %d: " + "bad partition flags\n",lineno); + fprintf(stderr, "\nPARSE ERROR: line %d: " + "bad partition flags\n",lineno); + return -1; + } + p += ret; + len += ret; + partition_add_flag(lineno, conf, flag, flval); + } + + if (p != str || (partition_create(lineno, conf, + name, id, flag, flval) < 0)) { + osm_log(conf->p_log, OSM_LOG_ERROR, + "PARSE ERROR: line %d: " + "bad partition definition\n", lineno); + fprintf(stderr, "\nPARSE ERROR: line %d: " + "bad partition definition\n", lineno); + return -1; + } + + skip_header: + do { + name = flag = NULL; + q = strchr(p, ','); + if (q) + *q++ = '\0'; + ret = parse_name_token(p, &name, &flag); + if (partition_add_port(lineno, conf, name, flag) < 0) { + osm_log(conf->p_log, OSM_LOG_ERROR, + "PARSE ERROR: line %d: " + "bad PortGUID\n", lineno); + fprintf(stderr, "PARSE ERROR: line %d: " + "bad PortGUID\n", lineno); + return -1; + } + p += ret; + len += ret; + } while (q); + + return len; +} + +int osm_prtn_config_parse_file(osm_log_t *p_log, osm_subn_t *p_subn, + const char *file_name) +{ + char line[1024]; + struct part_conf *conf = NULL; + FILE *file; + int lineno; + + file = fopen(file_name, "r"); + if (!file) { + osm_log(p_log, OSM_LOG_VERBOSE, + "osm_prtn_config_parse_file: " + "Cannot open config file \'%s\': %s\n", + file_name, strerror(errno)); + return -1; + } + + lineno = 0; + + while (fgets(line, sizeof(line) - 1, file) != NULL) { + char *q, *p = line; + + lineno++; + + p = line; + + q = strchr(p, '#'); + if (q) + *q = '\0'; + + do { + int len; + while (*p == ' ' || *p == '\t' || *p == '\n') + p++; + if (*p == '\0') + break; + + if (!conf && + !(conf = new_part_conf(p_log, p_subn))) { + osm_log(conf->p_log, OSM_LOG_ERROR, + "PARSE ERROR: line %d: " + "internal: cannot create config\n", lineno); + fprintf(stderr, "PARSE ERROR: line %d: " + "internal: cannot create config\n", lineno); + break; + } + + q = strchr(p, ';'); + if (q) + *q = '\0'; + + len = parse_part_conf(conf, p, lineno); + if (len < 0) { + break; + } + + p += len; + + if (q) { + flush_part_conf(conf); + conf = NULL; + } + } while (q); + } + + fclose(file); + + return 0; +} + diff --git a/trunk/ulp/opensm/user/opensm/osm_qos.c b/trunk/ulp/opensm/user/opensm/osm_qos.c new file mode 100644 index 00000000..fe3b9534 --- /dev/null +++ b/trunk/ulp/opensm/user/opensm/osm_qos.c @@ -0,0 +1,451 @@ +/* + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. + * + * This software is available to you under the OpenIB.org BSD license + * below: + * + * Redistribution and use in source and binary forms, with or + * without modification, are permitted provided that the following + * conditions are met: + * + * - Redistributions of source code must retain the above + * copyright notice, this list of conditions and the following + * disclaimer. + * + * - Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials + * provided with the distribution. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS + * BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN + * ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN + * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + * + * $Id$ + */ + + +/* + * Abstract: + * Implementation of OpenSM QoS infrastructure primitives + * + * Environment: + * Linux User Mode + * + */ + +#if HAVE_CONFIG_H +# include +#endif /* HAVE_CONFIG_H */ + +#include +#include + +#include +#include +#include +#include +#include + +struct qos_config { + uint8_t max_vls; + uint8_t vl_high_limit; + ib_vl_arb_table_t vlarb_high[2]; + ib_vl_arb_table_t vlarb_low[2]; + ib_slvl_table_t sl2vl; +}; + +static void qos_build_config(struct qos_config * cfg, + osm_qos_options_t * opt, osm_qos_options_t * dflt); + +/* + * QoS primitives + */ +static ib_api_status_t vlarb_update_table_block(osm_req_t * p_req, + osm_physp_t * p, + uint8_t port_num, + const ib_vl_arb_table_t *table_block, + unsigned block_length, + unsigned block_num) +{ + ib_vl_arb_table_t block; + osm_madw_context_t context; + uint32_t attr_mod; + ib_port_info_t *p_pi; + unsigned vl_mask, i; + + if (!(p_pi = osm_physp_get_port_info_ptr(p))) + return IB_ERROR; + + vl_mask = (1 << (ib_port_info_get_op_vls(p_pi) - 1)) - 1; + + memset(&block, 0, sizeof(block)); + memcpy(&block, table_block, + block_length * sizeof(block.vl_entry[0])); + for (i = 0; i < block_length; i++) + block.vl_entry[i].vl &= vl_mask; + + if (!memcmp(&p->vl_arb[block_num], &block, + block_length * sizeof(block.vl_entry[0]))) + return IB_SUCCESS; + + context.vla_context.node_guid = + osm_node_get_node_guid(osm_physp_get_node_ptr(p)); + context.vla_context.port_guid = osm_physp_get_port_guid(p); + context.vla_context.set_method = TRUE; + attr_mod = ((block_num + 1) << 16) | port_num; + + return osm_req_set(p_req, osm_physp_get_dr_path_ptr(p), + (uint8_t *) & block, sizeof(block), + IB_MAD_ATTR_VL_ARBITRATION, + cl_hton32(attr_mod), CL_DISP_MSGID_NONE, &context); +} + +static ib_api_status_t vlarb_update(osm_req_t * p_req, + osm_physp_t * p, uint8_t port_num, + const struct qos_config *qcfg) +{ + ib_api_status_t status = IB_SUCCESS; + ib_port_info_t *p_pi; + unsigned len; + + if (!(p_pi = osm_physp_get_port_info_ptr(p))) + return IB_ERROR; + + if (p_pi->vl_arb_low_cap > 0) { + len = p_pi->vl_arb_low_cap < IB_NUM_VL_ARB_ELEMENTS_IN_BLOCK ? + p_pi->vl_arb_low_cap : IB_NUM_VL_ARB_ELEMENTS_IN_BLOCK; + if ((status = vlarb_update_table_block(p_req, p, port_num, + &qcfg->vlarb_low[0], + len, 0)) != IB_SUCCESS) + return status; + } + if (p_pi->vl_arb_low_cap > IB_NUM_VL_ARB_ELEMENTS_IN_BLOCK) { + len = p_pi->vl_arb_low_cap % IB_NUM_VL_ARB_ELEMENTS_IN_BLOCK; + if ((status = vlarb_update_table_block(p_req, p, port_num, + &qcfg->vlarb_low[1], + len, 1)) != IB_SUCCESS) + return status; + } + if (p_pi->vl_arb_high_cap > 0) { + len = p_pi->vl_arb_high_cap < IB_NUM_VL_ARB_ELEMENTS_IN_BLOCK ? + p_pi->vl_arb_high_cap : IB_NUM_VL_ARB_ELEMENTS_IN_BLOCK; + if ((status = vlarb_update_table_block(p_req, p, port_num, + &qcfg->vlarb_high[0], + len, 2)) != IB_SUCCESS) + return status; + } + if (p_pi->vl_arb_high_cap > IB_NUM_VL_ARB_ELEMENTS_IN_BLOCK) { + len = p_pi->vl_arb_high_cap % IB_NUM_VL_ARB_ELEMENTS_IN_BLOCK; + if ((status = vlarb_update_table_block(p_req, p, port_num, + &qcfg->vlarb_high[1], + len, 3)) != IB_SUCCESS) + return status; + } + + return status; +} + +static ib_api_status_t sl2vl_update_table(osm_req_t * p_req, + osm_physp_t * p, uint8_t in_port, + uint8_t out_port, + const ib_slvl_table_t * sl2vl_table) +{ + osm_madw_context_t context; + ib_slvl_table_t tbl, *p_tbl; + osm_node_t *p_node = osm_physp_get_node_ptr(p); + uint32_t attr_mod; + ib_port_info_t *p_pi; + unsigned vl_mask; + uint8_t vl1, vl2; + int i; + + if (!(p_pi = osm_physp_get_port_info_ptr(p))) + return IB_ERROR; + + vl_mask = (1 << (ib_port_info_get_op_vls(p_pi) - 1)) - 1; + + for (i = 0; i < IB_MAX_NUM_VLS / 2; i++) { + vl1 = sl2vl_table->raw_vl_by_sl[i] >> 4; + vl2 = sl2vl_table->raw_vl_by_sl[i] & 0xf; + if (vl1 != 15) + vl1 &= vl_mask; + if (vl2 != 15) + vl2 &= vl_mask; + tbl.raw_vl_by_sl[i] = (vl1 << 4 ) | vl2 ; + } + + p_tbl = osm_physp_get_slvl_tbl(p, in_port); + if (p_tbl && !memcmp(p_tbl, &tbl, sizeof(tbl))) + return IB_SUCCESS; + + context.slvl_context.node_guid = osm_node_get_node_guid(p_node); + context.slvl_context.port_guid = osm_physp_get_port_guid(p); + context.slvl_context.set_method = TRUE; + attr_mod = in_port << 8 | out_port; + return osm_req_set(p_req, osm_physp_get_dr_path_ptr(p), + (uint8_t *) & tbl, sizeof(tbl), + IB_MAD_ATTR_SLVL_TABLE, + cl_hton32(attr_mod), CL_DISP_MSGID_NONE, &context); +} + +static ib_api_status_t sl2vl_update(osm_req_t * p_req, osm_port_t * p_port, + osm_physp_t * p, uint8_t port_num, + const struct qos_config *qcfg) +{ + ib_api_status_t status; + uint8_t i, num_ports; + ib_port_info_t *p_pi = osm_physp_get_port_info_ptr(p); + osm_physp_t *p_physp; + + if (!p_pi) + return IB_ERROR; + + if (osm_node_get_type(osm_physp_get_node_ptr(p)) == IB_NODE_TYPE_SWITCH) { + if (ib_port_info_get_vl_cap(p_pi) == 1) { + /* Check port 0's capability mask */ + p_physp = osm_port_get_default_phys_ptr(p_port); + p_pi = osm_physp_get_port_info_ptr(p_physp); + if (!(p_pi->capability_mask & IB_PORT_CAP_HAS_SL_MAP)) + return IB_SUCCESS; + } + num_ports = osm_node_get_num_physp(osm_physp_get_node_ptr(p)); + } else { + if (!(p_pi->capability_mask & IB_PORT_CAP_HAS_SL_MAP)) + return IB_SUCCESS; + num_ports = 1; + } + + for (i = 0; i < num_ports; i++) { + status = + sl2vl_update_table(p_req, p, i, port_num, &qcfg->sl2vl); + if (status != IB_SUCCESS) + return status; + } + + return IB_SUCCESS; +} + +static ib_api_status_t vl_high_limit_update(osm_req_t * p_req, + osm_physp_t * p, + const struct qos_config *qcfg) +{ + uint8_t payload[IB_SMP_DATA_SIZE]; + osm_madw_context_t context; + ib_port_info_t *p_pi; + + if (!(p_pi = osm_physp_get_port_info_ptr(p))) + return IB_ERROR; + + if (p_pi->vl_high_limit == qcfg->vl_high_limit) + return IB_SUCCESS; + + memset(payload, 0, IB_SMP_DATA_SIZE); + memcpy(payload, p_pi, sizeof(ib_port_info_t)); + + p_pi = (ib_port_info_t *) payload; + ib_port_info_set_state_no_change(p_pi); + + p_pi->vl_high_limit = qcfg->vl_high_limit; + + context.pi_context.node_guid = + osm_node_get_node_guid(osm_physp_get_node_ptr(p)); + context.pi_context.port_guid = osm_physp_get_port_guid(p); + context.pi_context.set_method = TRUE; + context.pi_context.update_master_sm_base_lid = FALSE; + context.pi_context.ignore_errors = FALSE; + context.pi_context.light_sweep = FALSE; + context.pi_context.active_transition = FALSE; + + return osm_req_set(p_req, osm_physp_get_dr_path_ptr(p), + payload, sizeof(payload), IB_MAD_ATTR_PORT_INFO, + cl_hton32(osm_physp_get_port_num(p)), + CL_DISP_MSGID_NONE, &context); +} + +static ib_api_status_t qos_physp_setup(osm_log_t * p_log, osm_req_t * p_req, + osm_port_t * p_port, osm_physp_t * p, + uint8_t port_num, + const struct qos_config *qcfg) +{ + ib_api_status_t status; + + /* OpVLs should be ok at this moment - just use it */ + + /* setup VL high limit */ + status = vl_high_limit_update(p_req, p, qcfg); + if (status != IB_SUCCESS) { + osm_log(p_log, OSM_LOG_ERROR, + "qos_physp_setup: ERR 6201 : " + "failed to update VLHighLimit " + "for port %" PRIx64 " #%d\n", + cl_ntoh64(p->port_guid), port_num); + return status; + } + + /* setup VLArbitration */ + status = vlarb_update(p_req, p, port_num, qcfg); + if (status != IB_SUCCESS) { + osm_log(p_log, OSM_LOG_ERROR, + "qos_physp_setup: ERR 6202 : " + "failed to update VLArbitration tables " + "for port %" PRIx64 " #%d\n", + cl_ntoh64(p->port_guid), port_num); + return status; + } + + /* setup SL2VL tables */ + status = sl2vl_update(p_req, p_port, p, port_num, qcfg); + if (status != IB_SUCCESS) { + osm_log(p_log, OSM_LOG_ERROR, + "qos_physp_setup: ERR 6203 : " + "failed to update SL2VLMapping tables " + "for port %" PRIx64 " #%d\n", + cl_ntoh64(p->port_guid), port_num); + return status; + } + + return IB_SUCCESS; +} + +osm_signal_t osm_qos_setup(osm_opensm_t * p_osm) +{ + struct qos_config ca_config, sw0_config, swe_config, rtr_config; + struct qos_config *cfg; + cl_qmap_t *p_tbl; + cl_map_item_t *p_next; + osm_port_t *p_port; + uint32_t num_physp; + osm_physp_t *p_physp; + osm_node_t *p_node; + ib_api_status_t status; + uint8_t i; + + if (p_osm->subn.opt.no_qos) + return OSM_SIGNAL_DONE; + + OSM_LOG_ENTER(&p_osm->log, osm_qos_setup); + + qos_build_config(&ca_config, &p_osm->subn.opt.qos_ca_options, + &p_osm->subn.opt.qos_options); + qos_build_config(&sw0_config, &p_osm->subn.opt.qos_sw0_options, + &p_osm->subn.opt.qos_options); + qos_build_config(&swe_config, &p_osm->subn.opt.qos_swe_options, + &p_osm->subn.opt.qos_options); + qos_build_config(&rtr_config, &p_osm->subn.opt.qos_rtr_options, + &p_osm->subn.opt.qos_options); + + cl_plock_excl_acquire(&p_osm->lock); + + p_tbl = &p_osm->subn.port_guid_tbl; + p_next = cl_qmap_head(p_tbl); + while (p_next != cl_qmap_end(p_tbl)) { + p_port = (osm_port_t *) p_next; + p_next = cl_qmap_next(p_next); + + p_node = p_port->p_node; + if (p_node->sw) { + num_physp = osm_port_get_num_physp(p_port); + for (i = 1; i < num_physp; i++) { + p_physp = osm_port_get_phys_ptr(p_port, i); + if (!p_physp || !osm_physp_is_valid(p_physp)) + continue; + status = + qos_physp_setup(&p_osm->log, &p_osm->sm.req, + p_port, p_physp, i, &swe_config); + } + /* skip base port 0 */ + if (!ib_switch_info_is_enhanced_port0(&p_node->sw->switch_info)) + continue; + + cfg = &sw0_config; + } else if (osm_node_get_type(p_node) == IB_NODE_TYPE_ROUTER) + cfg = &rtr_config; + else + cfg = &ca_config; + + p_physp = osm_port_get_default_phys_ptr(p_port); + if (!osm_physp_is_valid(p_physp)) + continue; + + status = qos_physp_setup(&p_osm->log, &p_osm->sm.req, + p_port, p_physp, 0, cfg); + } + + cl_plock_release(&p_osm->lock); + OSM_LOG_EXIT(&p_osm->log); + + return OSM_SIGNAL_DONE; +} + +/* + * QoS config stuff + */ +static int parse_one_unsigned(char *str, char delim, unsigned *val) +{ + char *end; + *val = strtoul(str, &end, 0); + if (*end) + end++; + return (int)(end - str); +} + +static int parse_vlarb_entry(char *str, ib_vl_arb_element_t * e) +{ + unsigned val; + char *p = str; + p += parse_one_unsigned(p, ':', &val); + e->vl = val % 15; + p += parse_one_unsigned(p, ',', &val); + e->weight = (uint8_t)val; + return (int)(p - str); +} + +static int parse_sl2vl_entry(char *str, uint8_t * raw) +{ + unsigned val1, val2; + char *p = str; + p += parse_one_unsigned(p, ',', &val1); + p += parse_one_unsigned(p, ',', &val2); + *raw = (val1 << 4) | (val2 & 0xf); + return (int)(p - str); +} + +static void qos_build_config(struct qos_config *cfg, + osm_qos_options_t * opt, osm_qos_options_t * dflt) +{ + int i; + char *p; + + memset(cfg, 0, sizeof(*cfg)); + + cfg->max_vls = opt->max_vls > 0 ? opt->max_vls : dflt->max_vls; + cfg->vl_high_limit = (uint8_t)opt->high_limit; + + p = opt->vlarb_high ? opt->vlarb_high : dflt->vlarb_high; + for (i = 0; i < 2 * IB_NUM_VL_ARB_ELEMENTS_IN_BLOCK; i++) { + p += parse_vlarb_entry(p, + &cfg->vlarb_high[i/IB_NUM_VL_ARB_ELEMENTS_IN_BLOCK]. + vl_entry[i%IB_NUM_VL_ARB_ELEMENTS_IN_BLOCK]); + } + + p = opt->vlarb_low ? opt->vlarb_low : dflt->vlarb_low; + for (i = 0; i < 2 * IB_NUM_VL_ARB_ELEMENTS_IN_BLOCK; i++) { + p += parse_vlarb_entry(p, + &cfg->vlarb_low[i/IB_NUM_VL_ARB_ELEMENTS_IN_BLOCK]. + vl_entry[i%IB_NUM_VL_ARB_ELEMENTS_IN_BLOCK]); + } + + p = opt->sl2vl ? opt->sl2vl : dflt->sl2vl; + for (i = 0; i < IB_MAX_NUM_VLS / 2; i++) + p += parse_sl2vl_entry(p, &cfg->sl2vl.raw_vl_by_sl[i]); + +} + diff --git a/trunk/ulp/opensm/user/opensm/osm_remote_sm.c b/trunk/ulp/opensm/user/opensm/osm_remote_sm.c index 534b4394..4b0cefeb 100644 --- a/trunk/ulp/opensm/user/opensm/osm_remote_sm.c +++ b/trunk/ulp/opensm/user/opensm/osm_remote_sm.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Implementation of osm_sm_t. @@ -44,16 +45,12 @@ * $Revision: 1.5 $ */ -/* - Next available error code: 0x403 -*/ - #if HAVE_CONFIG_H # include #endif /* HAVE_CONFIG_H */ +#include #include -#include /********************************************************************** **********************************************************************/ @@ -61,7 +58,7 @@ void osm_remote_sm_construct( IN osm_remote_sm_t* const p_sm ) { - cl_memclr( p_sm, sizeof(*p_sm) ); + memset( p_sm, 0, sizeof(*p_sm) ); } /********************************************************************** @@ -70,12 +67,12 @@ void osm_remote_sm_destroy( IN osm_remote_sm_t* const p_sm ) { - cl_memclr( p_sm, sizeof(*p_sm) ); + memset( p_sm, 0, sizeof(*p_sm) ); } /********************************************************************** **********************************************************************/ -ib_api_status_t +void osm_remote_sm_init( IN osm_remote_sm_t* const p_sm, IN const osm_port_t* const p_port, @@ -88,5 +85,6 @@ osm_remote_sm_init( p_sm->p_port = p_port; p_sm->smi = *p_smi; - return( IB_SUCCESS ); + return; } + diff --git a/trunk/ulp/opensm/user/opensm/osm_req.c b/trunk/ulp/opensm/user/opensm/osm_req.c index 0a43f98e..f428315f 100644 --- a/trunk/ulp/opensm/user/opensm/osm_req.c +++ b/trunk/ulp/opensm/user/opensm/osm_req.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Implementation of osm_req_t. @@ -44,16 +45,12 @@ * $Revision: 1.6 $ */ -/* - Next available error code: 0x300 -*/ - #if HAVE_CONFIG_H # include #endif /* HAVE_CONFIG_H */ +#include #include -#include #include #include #include @@ -73,7 +70,7 @@ osm_req_construct( { CL_ASSERT( p_req ); - cl_memclr( p_req, sizeof(*p_req) ); + memset( p_req, 0, sizeof(*p_req) ); } /********************************************************************** @@ -136,7 +133,8 @@ osm_req_get( CL_ASSERT( attr_id ); /* do nothing if we are exiting ... */ - if (osm_exit_flag) goto Exit; + if (osm_exit_flag) + goto Exit; /* p_context may be NULL. */ @@ -161,7 +159,7 @@ osm_req_get( { osm_log( p_req->p_log, OSM_LOG_DEBUG, "osm_req_get: " - "Getting %s (0x%X), modifier = 0x%X, TID = 0x%" PRIx64 "\n", + "Getting %s (0x%X), modifier 0x%X, TID 0x%" PRIx64 "\n", ib_get_sm_attr_str( attr_id ), cl_ntoh16( attr_id ), cl_ntoh32( attr_mod ), @@ -228,7 +226,8 @@ osm_req_set( CL_ASSERT( p_payload ); /* do nothing if we are exiting ... */ - if (osm_exit_flag) goto Exit; + if (osm_exit_flag) + goto Exit; /* p_context may be NULL. */ @@ -253,7 +252,7 @@ osm_req_set( { osm_log( p_req->p_log, OSM_LOG_DEBUG, "osm_req_set: " - "Setting %s (0x%X), modifier = 0x%X, TID = 0x%" PRIx64 "\n", + "Setting %s (0x%X), modifier 0x%X, TID 0x%" PRIx64 "\n", ib_get_sm_attr_str( attr_id ), cl_ntoh16( attr_id ), cl_ntoh32( attr_mod ), @@ -286,8 +285,8 @@ osm_req_set( if( p_context ) p_madw->context = *p_context; - cl_memcpy( osm_madw_get_smp_ptr( p_madw )->data, - p_payload, payload_size ); + memcpy( osm_madw_get_smp_ptr( p_madw )->data, + p_payload, payload_size ); osm_vl15_post( p_req->p_vl15, p_madw ); @@ -296,3 +295,4 @@ osm_req_set( return( status ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_req_ctrl.c b/trunk/ulp/opensm/user/opensm/osm_req_ctrl.c index 42b9aee2..97274389 100644 --- a/trunk/ulp/opensm/user/opensm/osm_req_ctrl.c +++ b/trunk/ulp/opensm/user/opensm/osm_req_ctrl.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Implementation of osm_req_ctrl_t. @@ -44,15 +45,11 @@ * $Revision: 1.5 $ */ -/* - Next available error code: 0x102 -*/ - #if HAVE_CONFIG_H # include #endif /* HAVE_CONFIG_H */ -#include +#include #include #include #include @@ -83,7 +80,7 @@ void osm_req_ctrl_construct( IN osm_req_ctrl_t* const p_ctrl ) { - cl_memclr( p_ctrl, sizeof(*p_ctrl) ); + memset( p_ctrl, 0, sizeof(*p_ctrl) ); p_ctrl->h_disp = CL_DISP_INVALID_HANDLE; } @@ -136,3 +133,4 @@ osm_req_ctrl_init( return( status ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_resp.c b/trunk/ulp/opensm/user/opensm/osm_resp.c index ddf3a9cb..aff8198a 100644 --- a/trunk/ulp/opensm/user/opensm/osm_resp.c +++ b/trunk/ulp/opensm/user/opensm/osm_resp.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Implementation of osm_resp_t. @@ -48,8 +49,8 @@ # include #endif /* HAVE_CONFIG_H */ +#include #include -#include #include #include #include @@ -67,7 +68,7 @@ void osm_resp_construct( IN osm_resp_t* const p_resp ) { - cl_memclr( p_resp, sizeof(*p_resp) ); + memset( p_resp, 0, sizeof(*p_resp) ); } /********************************************************************** @@ -124,7 +125,7 @@ osm_resp_make_resp_smp( if (p_src_smp->method == IB_MAD_METHOD_GET || p_src_smp->method == IB_MAD_METHOD_SET ) { p_dest_smp->method = IB_MAD_METHOD_GET_RESP; - p_dest_smp->status = (ib_net16_t)(status | IB_SMP_DIRECTION); + p_dest_smp->status = status; } else if (p_src_smp->method == IB_MAD_METHOD_TRAP) { @@ -140,9 +141,12 @@ osm_resp_make_resp_smp( goto Exit; } + if (p_src_smp->mgmt_class == IB_MCLASS_SUBN_DIR) + p_dest_smp->status |= IB_SMP_DIRECTION; + p_dest_smp->dr_dlid = p_dest_smp->dr_slid; p_dest_smp->dr_slid = p_dest_smp->dr_dlid; - cl_memcpy( &p_dest_smp->data, p_payload, IB_SMP_DATA_SIZE ); + memcpy( &p_dest_smp->data, p_payload, IB_SMP_DATA_SIZE ); Exit: OSM_LOG_EXIT( p_resp->p_log ); @@ -158,7 +162,7 @@ osm_resp_send( IN const uint8_t* const p_payload ) { const ib_smp_t* p_req_smp; - ib_smp_t* p_smp; + ib_smp_t* p_smp; osm_madw_t* p_madw; ib_api_status_t status = IB_SUCCESS; @@ -168,7 +172,8 @@ osm_resp_send( CL_ASSERT( p_payload ); /* do nothing if we are exiting ... */ - if (osm_exit_flag) goto Exit; + if (osm_exit_flag) + goto Exit; p_madw = osm_mad_pool_get( p_resp->p_pool, @@ -206,7 +211,7 @@ osm_resp_send( osm_log( p_resp->p_log, OSM_LOG_DEBUG, "osm_resp_send: " "Responding to %s (0x%X)" - "\n\t\t\t\tattribute modifier = 0x%X, TID = 0x%" PRIx64 "\n", + "\n\t\t\t\tattribute modifier 0x%X, TID 0x%" PRIx64 "\n", ib_get_sm_attr_str( p_smp->attr_id ), cl_ntoh16( p_smp->attr_id ), cl_ntoh32( p_smp->attr_mod ), @@ -219,3 +224,4 @@ osm_resp_send( OSM_LOG_EXIT( p_resp->p_log ); return( status ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_router.c b/trunk/ulp/opensm/user/opensm/osm_router.c new file mode 100644 index 00000000..0f478b65 --- /dev/null +++ b/trunk/ulp/opensm/user/opensm/osm_router.c @@ -0,0 +1,124 @@ +/* + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. + * + * This software is available to you under the OpenIB.org BSD license + * below: + * + * Redistribution and use in source and binary forms, with or + * without modification, are permitted provided that the following + * conditions are met: + * + * - Redistributions of source code must retain the above + * copyright notice, this list of conditions and the following + * disclaimer. + * + * - Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials + * provided with the distribution. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS + * BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN + * ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN + * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + * + * $Id$ + */ + + +/* + * Abstract: + * Implementation of osm_router_t. + * This object represents an Infiniband router. + * This object is part of the opensm family of objects. + * + * Environment: + * Linux User Mode + * + */ + +#if HAVE_CONFIG_H +# include +#endif /* HAVE_CONFIG_H */ + +#include +#include +#include +#include +#include + +/********************************************************************** + **********************************************************************/ +void +osm_router_construct( + IN osm_router_t* const p_rtr ) +{ + CL_ASSERT( p_rtr ); + memset( p_rtr, 0, sizeof(*p_rtr) ); +} + +/********************************************************************** + **********************************************************************/ +ib_api_status_t +osm_router_init( + IN osm_router_t* const p_rtr, + IN osm_port_t* const p_port ) +{ + ib_api_status_t status = IB_SUCCESS; + + CL_ASSERT( p_rtr ); + CL_ASSERT( p_port ); + + osm_router_construct( p_rtr ); + + p_rtr->p_port = p_port; + + return( status ); +} + +/********************************************************************** + **********************************************************************/ +void +osm_router_destroy( + IN osm_router_t* const p_rtr ) +{ +} + +/********************************************************************** + **********************************************************************/ +void +osm_router_delete( + IN OUT osm_router_t** const pp_rtr ) +{ + osm_router_destroy( *pp_rtr ); + free( *pp_rtr ); + *pp_rtr = NULL; +} + +/********************************************************************** + **********************************************************************/ +osm_router_t* +osm_router_new( + IN osm_port_t* const p_port ) +{ + ib_api_status_t status; + osm_router_t *p_rtr; + + p_rtr = (osm_router_t*)malloc( sizeof(*p_rtr) ); + if( p_rtr ) + { + memset( p_rtr, 0, sizeof(*p_rtr) ); + status = osm_router_init( p_rtr, p_port ); + if( status != IB_SUCCESS ) + osm_router_delete( &p_rtr ); + } + + return( p_rtr ); +} + diff --git a/trunk/ulp/opensm/user/opensm/osm_sa.c b/trunk/ulp/opensm/user/opensm/osm_sa.c index d74301c8..3512cb27 100644 --- a/trunk/ulp/opensm/user/opensm/osm_sa.c +++ b/trunk/ulp/opensm/user/opensm/osm_sa.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -35,7 +35,7 @@ /* * Abstract: * Implementation of osm_sa_t. - * This object represents the Subnet Administrator object. + * This object represents the Subnet Administration object. * This object is part of the opensm family of objects. * * Environment: @@ -44,15 +44,15 @@ * $Revision: 1.14 $ */ -/* - Next available error code: 0x403 -*/ - #if HAVE_CONFIG_H # include #endif /* HAVE_CONFIG_H */ -#include +#include +#include +#include +#include +#include #include #include #include @@ -64,6 +64,10 @@ #include #include #include +#include +#include +#include +#include #define OSM_SA_INITIAL_TID_VALUE 0xabc @@ -73,7 +77,7 @@ void osm_sa_construct( IN osm_sa_t* const p_sa ) { - cl_memclr( p_sa, sizeof(*p_sa) ); + memset( p_sa, 0, sizeof(*p_sa) ); p_sa->state = OSM_SA_STATE_INIT; p_sa->sa_trans_id = OSM_SA_INITIAL_TID_VALUE; @@ -95,6 +99,11 @@ osm_sa_construct( osm_pr_rcv_construct( &p_sa->pr_rcv ); osm_pr_rcv_ctrl_construct( &p_sa->pr_rcv_ctrl ); +#if defined (VENDOR_RMPP_SUPPORT) && defined (DUAL_SIDED_RMPP) + osm_mpr_rcv_construct( &p_sa->mpr_rcv ); + osm_mpr_rcv_ctrl_construct( &p_sa->mpr_rcv_ctrl ); +#endif + osm_smir_rcv_construct( &p_sa->smir_rcv ); osm_smir_ctrl_construct( &p_sa->smir_ctrl ); @@ -118,6 +127,12 @@ osm_sa_construct( osm_lftr_rcv_construct( &p_sa->lftr_rcv ); osm_lftr_rcv_ctrl_construct( &p_sa->lftr_rcv_ctrl ); + + osm_sir_rcv_construct( &p_sa->sir_rcv ); + osm_sir_rcv_ctrl_construct( &p_sa->sir_rcv_ctrl ); + + osm_mftr_rcv_construct( &p_sa->mftr_rcv ); + osm_mftr_rcv_ctrl_construct( &p_sa->mftr_rcv_ctrl ); } /********************************************************************** @@ -138,6 +153,9 @@ osm_sa_shutdown( osm_gir_rcv_ctrl_destroy( &p_sa->gir_rcv_ctrl ); osm_lr_rcv_ctrl_destroy( &p_sa->lr_rcv_ctrl ); osm_pr_rcv_ctrl_destroy( &p_sa->pr_rcv_ctrl ); +#if defined (VENDOR_RMPP_SUPPORT) && defined (DUAL_SIDED_RMPP) + osm_mpr_rcv_ctrl_destroy( &p_sa->mpr_rcv_ctrl ); +#endif osm_smir_ctrl_destroy( &p_sa->smir_ctrl ); osm_mcmr_rcv_ctrl_destroy( &p_sa->mcmr_rcv_ctlr); osm_sr_rcv_ctrl_destroy( &p_sa->sr_rcv_ctrl ); @@ -146,6 +164,8 @@ osm_sa_shutdown( osm_slvl_rec_rcv_ctrl_destroy( &p_sa->slvl_rec_rcv_ctrl ); osm_pkey_rec_rcv_ctrl_destroy( &p_sa->pkey_rec_rcv_ctrl ); osm_lftr_rcv_ctrl_destroy( &p_sa->lftr_rcv_ctrl ); + osm_sir_rcv_ctrl_destroy( &p_sa->sir_rcv_ctrl ); + osm_mftr_rcv_ctrl_destroy( &p_sa->mftr_rcv_ctrl ); osm_sa_mad_ctrl_destroy( &p_sa->mad_ctrl ); OSM_LOG_EXIT( p_sa->p_log ); @@ -166,6 +186,9 @@ osm_sa_destroy( osm_gir_rcv_destroy( &p_sa->gir_rcv ); osm_lr_rcv_destroy( &p_sa->lr_rcv ); osm_pr_rcv_destroy( &p_sa->pr_rcv ); +#if defined (VENDOR_RMPP_SUPPORT) && defined (DUAL_SIDED_RMPP) + osm_mpr_rcv_destroy( &p_sa->mpr_rcv ); +#endif osm_smir_rcv_destroy( &p_sa->smir_rcv ); osm_mcmr_rcv_destroy(&p_sa->mcmr_rcv); osm_sr_rcv_destroy( &p_sa->sr_rcv ); @@ -174,6 +197,8 @@ osm_sa_destroy( osm_slvl_rec_rcv_destroy( &p_sa->slvl_rec_rcv ); osm_pkey_rec_rcv_destroy( &p_sa->pkey_rec_rcv ); osm_lftr_rcv_destroy( &p_sa->lftr_rcv ); + osm_sir_rcv_destroy( &p_sa->sir_rcv ); + osm_mftr_rcv_destroy( &p_sa->mftr_rcv ); osm_sa_resp_destroy( &p_sa->resp ); OSM_LOG_EXIT( p_sa->p_log ); @@ -332,6 +357,26 @@ osm_sa_init( if( status != IB_SUCCESS ) goto Exit; +#if defined (VENDOR_RMPP_SUPPORT) && defined (DUAL_SIDED_RMPP) + status = osm_mpr_rcv_init( + &p_sa->mpr_rcv, + &p_sa->resp, + p_sa->p_mad_pool, + p_subn, + p_log, + p_lock ); + if( status != IB_SUCCESS ) + goto Exit; + + status = osm_mpr_rcv_ctrl_init( + &p_sa->mpr_rcv_ctrl, + &p_sa->mpr_rcv, + p_log, + p_disp ); + if( status != IB_SUCCESS ) + goto Exit; +#endif + status = osm_smir_rcv_init( &p_sa->smir_rcv, &p_sa->resp, @@ -478,6 +523,42 @@ osm_sa_init( if( status != IB_SUCCESS ) goto Exit; + status = osm_sir_rcv_init( + &p_sa->sir_rcv, + &p_sa->resp, + p_sa->p_mad_pool, + p_subn, + p_log, + p_lock); + if( status != IB_SUCCESS ) + goto Exit; + + status = osm_sir_rcv_ctrl_init( + &p_sa->sir_rcv_ctrl, + &p_sa->sir_rcv, + p_log, + p_disp ); + if( status != IB_SUCCESS ) + goto Exit; + + status = osm_mftr_rcv_init( + &p_sa->mftr_rcv, + &p_sa->resp, + p_sa->p_mad_pool, + p_subn, + p_log, + p_lock); + if( status != IB_SUCCESS ) + goto Exit; + + status = osm_mftr_rcv_ctrl_init( + &p_sa->mftr_rcv_ctrl, + &p_sa->mftr_rcv, + p_log, + p_disp ); + if( status != IB_SUCCESS ) + goto Exit; + Exit: OSM_LOG_EXIT( p_log ); return( status ); @@ -503,107 +584,624 @@ osm_sa_bind( /********************************************************************** **********************************************************************/ +/* + * SA DB Dumper + * + */ -ib_gid_t osm_ipoib_mgid = { - { - 0xff, /* multicast field */ - 0x12, /* non-permanent bit,scope */ - 0x40, 0x1b, /* IPv4 signature */ - 0xff, 0xff, /* 16 bits of P_Key (to be filled in) */ - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 48 bits of zeros */ - 0xff, 0xff, 0xff, 0xff, /* 32 bit IPv4 broadcast address */ - }, +struct opensm_dump_context { + osm_opensm_t *p_osm; + FILE *file; }; +static int +opensm_dump_to_file(osm_opensm_t *p_osm, const char *file_name, + void (*dump_func)(osm_opensm_t *p_osm, FILE *file)) +{ + char path[1024]; + FILE *file; + + snprintf(path, sizeof(path), "%s/%s", + p_osm->subn.opt.dump_files_dir, file_name); + + file = fopen(path, "w"); + if (!file) { + osm_log(&p_osm->log, OSM_LOG_ERROR, + "opensm_dump_to_file: ERR 0000: " + "cannot open file \'%s\': %s\n", + file_name, strerror(errno)); + return -1; + } + + chmod(path, S_IRUSR|S_IWUSR); + + dump_func(p_osm, file); + + fclose(file); + return 0; +} + +static void +mcast_mgr_dump_one_port(cl_map_item_t *p_map_item, void *cxt) +{ + FILE *file = ((struct opensm_dump_context *)cxt)->file; + osm_mcm_port_t *p_mcm_port = (osm_mcm_port_t *)p_map_item; + + fprintf(file, "mcm_port: " + "port_gid=0x%016" PRIx64 ":0x%016" PRIx64 " " + "scope_state=0x%02x proxy_join=0x%x" "\n\n", + cl_ntoh64(p_mcm_port->port_gid.unicast.prefix), + cl_ntoh64(p_mcm_port->port_gid.unicast.interface_id), + p_mcm_port->scope_state, + p_mcm_port->proxy_join); +} + +static void +sa_dump_one_mgrp(cl_map_item_t *p_map_item, void *cxt) +{ + struct opensm_dump_context dump_context; + osm_opensm_t *p_osm = ((struct opensm_dump_context *)cxt)->p_osm; + FILE *file = ((struct opensm_dump_context *)cxt)->file; + osm_mgrp_t *p_mgrp = (osm_mgrp_t *)p_map_item; + + fprintf(file, "MC Group 0x%04x %s:" + " mgid=0x%016" PRIx64 ":0x%016" PRIx64 + " port_gid=0x%016" PRIx64 ":0x%016" PRIx64 + " qkey=0x%08x mlid=0x%04x mtu=0x%02x tclass=0x%02x" + " pkey=0x%04x rate=0x%02x pkt_life=0x%02x sl_flow_hop=0x%08x" + " scope_state=0x%02x proxy_join=0x%x" "\n\n", + cl_ntoh16(p_mgrp->mlid), + p_mgrp->well_known ? " (well known)" : "", + cl_ntoh64(p_mgrp->mcmember_rec.mgid.unicast.prefix), + cl_ntoh64(p_mgrp->mcmember_rec.mgid.unicast.interface_id), + cl_ntoh64(p_mgrp->mcmember_rec.port_gid.unicast.prefix), + cl_ntoh64(p_mgrp->mcmember_rec.port_gid.unicast.interface_id), + cl_ntoh32(p_mgrp->mcmember_rec.qkey), + cl_ntoh16(p_mgrp->mcmember_rec.mlid), + p_mgrp->mcmember_rec.mtu, + p_mgrp->mcmember_rec.tclass, + cl_ntoh16(p_mgrp->mcmember_rec.pkey), + p_mgrp->mcmember_rec.rate, + p_mgrp->mcmember_rec.pkt_life, + cl_ntoh32(p_mgrp->mcmember_rec.sl_flow_hop), + p_mgrp->mcmember_rec.scope_state, + p_mgrp->mcmember_rec.proxy_join + ); + + dump_context.p_osm = p_osm; + dump_context.file = file; + + cl_qmap_apply_func(&p_mgrp->mcm_port_tbl, + mcast_mgr_dump_one_port, &dump_context); +} + +static void +sa_dump_one_inform(cl_list_item_t *p_list_item, void *cxt) +{ + FILE *file = ((struct opensm_dump_context *)cxt)->file; + osm_infr_t *p_infr = (osm_infr_t *)p_list_item; + ib_inform_info_record_t *p_iir = &p_infr->inform_record; + + fprintf(file, "InformInfo Record:" + " subscriber_gid=0x%016" PRIx64 ":0x%016" PRIx64 + " subscriber_enum=0x%x" + " InformInfo:" + " gid=0x%016" PRIx64 ":0x%016" PRIx64 + " lid_range_begin=0x%x" + " lid_range_end=0x%x" + " is_generic=0x%x" + " subscribe=0x%x" + " trap_type=0x%x" + " trap_num=0x%x" + " qpn_resp_time_val=0x%x" + " node_type=0x%06x" + " rep_addr: lid=0x%04x path_bits=0x%02x static_rate=0x%02x" + " remote_qp=0x%08x remote_qkey=0x%08x pkey=0x%04x sl=0x%02x" + "\n\n", + cl_ntoh64(p_iir->subscriber_gid.unicast.prefix), + cl_ntoh64(p_iir->subscriber_gid.unicast.interface_id), + cl_ntoh16(p_iir->subscriber_enum), + cl_ntoh64(p_iir->inform_info.gid.unicast.prefix), + cl_ntoh64(p_iir->inform_info.gid.unicast.interface_id), + cl_ntoh16(p_iir->inform_info.lid_range_begin), + cl_ntoh16(p_iir->inform_info.lid_range_end), + p_iir->inform_info.is_generic, + p_iir->inform_info.subscribe, + cl_ntoh16(p_iir->inform_info.trap_type), + cl_ntoh16(p_iir->inform_info.g_or_v.generic.trap_num), + cl_ntoh32(p_iir->inform_info.g_or_v.generic.qpn_resp_time_val), + cl_ntoh32(ib_inform_info_get_node_type(&p_iir->inform_info)), + cl_ntoh16(p_infr->report_addr.dest_lid), + p_infr->report_addr.path_bits, + p_infr->report_addr.static_rate, + cl_ntoh32(p_infr->report_addr.addr_type.gsi.remote_qp), + cl_ntoh32(p_infr->report_addr.addr_type.gsi.remote_qkey), + cl_ntoh16(p_infr->report_addr.addr_type.gsi.pkey), + p_infr->report_addr.addr_type.gsi.service_level); +} + +static void +sa_dump_one_service(cl_list_item_t *p_list_item, void *cxt) +{ + FILE *file = ((struct opensm_dump_context *)cxt)->file; + osm_svcr_t *p_svcr = (osm_svcr_t *)p_list_item; + ib_service_record_t *p_sr = &p_svcr->service_record; + + fprintf(file, "Service Record: id=0x%016" PRIx64 + " gid=0x%016" PRIx64 ":0x%016" PRIx64 + " pkey=0x%x" + " lease=0x%x" + " key=0x%02x%02x%02x%02x%02x%02x%02x%02x" + ":0x%02x%02x%02x%02x%02x%02x%02x%02x" + " name=\'%s\'" + " data8=0x%02x%02x%02x%02x%02x%02x%02x%02x" + ":0x%02x%02x%02x%02x%02x%02x%02x%02x" + " data16=0x%04x%04x%04x%04x:0x%04x%04x%04x%04x" + " data32=0x%08x%08x:0x%08x%08x" + " data64=0x%016" PRIx64 ":0x%016" PRIx64 + " modified_time=0x%x lease_period=0x%x\n\n", + cl_ntoh64( p_sr->service_id ), + cl_ntoh64( p_sr->service_gid.unicast.prefix ), + cl_ntoh64( p_sr->service_gid.unicast.interface_id ), + cl_ntoh16( p_sr->service_pkey ), + cl_ntoh32( p_sr->service_lease ), + p_sr->service_key[0], p_sr->service_key[1], + p_sr->service_key[2], p_sr->service_key[3], + p_sr->service_key[4], p_sr->service_key[5], + p_sr->service_key[6], p_sr->service_key[7], + p_sr->service_key[8], p_sr->service_key[9], + p_sr->service_key[10], p_sr->service_key[11], + p_sr->service_key[12], p_sr->service_key[13], + p_sr->service_key[14], p_sr->service_key[15], + p_sr->service_name, + p_sr->service_data8[0], p_sr->service_data8[1], + p_sr->service_data8[2], p_sr->service_data8[3], + p_sr->service_data8[4], p_sr->service_data8[5], + p_sr->service_data8[6], p_sr->service_data8[7], + p_sr->service_data8[8], p_sr->service_data8[9], + p_sr->service_data8[10], p_sr->service_data8[11], + p_sr->service_data8[12], p_sr->service_data8[13], + p_sr->service_data8[14], p_sr->service_data8[15], + cl_ntoh16(p_sr->service_data16[0]), + cl_ntoh16(p_sr->service_data16[1]), + cl_ntoh16(p_sr->service_data16[2]), + cl_ntoh16(p_sr->service_data16[3]), + cl_ntoh16(p_sr->service_data16[4]), + cl_ntoh16(p_sr->service_data16[5]), + cl_ntoh16(p_sr->service_data16[6]), + cl_ntoh16(p_sr->service_data16[7]), + cl_ntoh32(p_sr->service_data32[0]), + cl_ntoh32(p_sr->service_data32[1]), + cl_ntoh32(p_sr->service_data32[2]), + cl_ntoh32(p_sr->service_data32[3]), + cl_ntoh64(p_sr->service_data64[0]), + cl_ntoh64(p_sr->service_data64[1]), + p_svcr->modified_time, p_svcr->lease_period); +} + +static void +sa_dump_all_sa(osm_opensm_t *p_osm, FILE *file) +{ + struct opensm_dump_context dump_context; + + dump_context.p_osm = p_osm; + dump_context.file = file; + osm_log(&p_osm->log, OSM_LOG_DEBUG, "sa_dump_all_sa: Dump multicast:\n"); + cl_plock_acquire(&p_osm->lock); + cl_qmap_apply_func(&p_osm->subn.mgrp_mlid_tbl, + sa_dump_one_mgrp, &dump_context); + osm_log(&p_osm->log, OSM_LOG_DEBUG, "sa_dump_all_sa: Dump inform:\n"); + cl_qlist_apply_func(&p_osm->subn.sa_infr_list, + sa_dump_one_inform, &dump_context); + osm_log(&p_osm->log, OSM_LOG_DEBUG, "sa_dump_all_sa: Dump services:\n"); + cl_qlist_apply_func(&p_osm->subn.sa_sr_list, + sa_dump_one_service, &dump_context); + cl_plock_release(&p_osm->lock); +} + +int osm_sa_db_file_dump(osm_opensm_t *p_osm) +{ + return opensm_dump_to_file(p_osm, "opensm-sa.dump", sa_dump_all_sa); +} + /* - * HACK: Until TS resolves their noncompliant join compmask - * we have to pre-define the MGID + * SA DB Loader + * */ -ib_gid_t osm_ts_ipoib_mgid = { - { - 0xff, /* multicast field */ - 0x12, /* non-permanent bit,scope */ - 0x40, 0x1b, /* IPv4 signature */ - 0xff, 0xff, /* 16 bits of P_Key (to be filled in) */ - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 48 bits of zeros */ - 0x00, 0x00, 0x00, 0x01, /* 32 bit IPv4 broadcast address */ - }, -}; -void -osm_sa_create_template_record_ipoib( - IN osm_sa_t* const p_sa, - IN const osm_subn_opt_t* const p_opt ) +osm_mgrp_t *load_mcgroup(osm_opensm_t *p_osm, ib_net16_t mlid, + ib_member_rec_t *p_mcm_rec, unsigned well_known) +{ + ib_net64_t comp_mask; + cl_map_item_t *p_next; + osm_mgrp_t *p_mgrp; + + cl_plock_excl_acquire(&p_osm->lock); + + if ((p_next = cl_qmap_get(&p_osm->subn.mgrp_mlid_tbl, mlid)) != + cl_qmap_end(&p_osm->subn.mgrp_mlid_tbl)) { + p_mgrp = (osm_mgrp_t *)p_next; + if (!memcmp(&p_mgrp->mcmember_rec.mgid, &p_mcm_rec->mgid, + sizeof(ib_gid_t))) { + osm_log(&p_osm->log, OSM_LOG_DEBUG, + "load_mcgroup: mgrp %04x is already here.", + cl_ntoh16(mlid)); + goto _out; + } + osm_log(&p_osm->log, OSM_LOG_VERBOSE, + "load_mcgroup: mlid %04x is already used by another " + "MC group. Will request clients reregistration.\n", + cl_ntoh16(mlid)); + p_mgrp = NULL; + goto _out; + } + + comp_mask = IB_MCR_COMPMASK_MTU | IB_MCR_COMPMASK_MTU_SEL + | IB_MCR_COMPMASK_RATE | IB_MCR_COMPMASK_RATE_SEL; + if (osm_mcmr_rcv_find_or_create_new_mgrp(&p_osm->sa.mcmr_rcv, + comp_mask, p_mcm_rec, + &p_mgrp) != IB_SUCCESS || + !p_mgrp || p_mgrp->mlid != mlid) { + osm_log(&p_osm->log, OSM_LOG_ERROR, + "load_mcgroup: cannot create MC group with mlid " + "0x%04x and mgid 0x%016" PRIx64 ":0x%016" PRIx64 "\n", + cl_ntoh16(mlid), + cl_ntoh64(p_mcm_rec->mgid.unicast.prefix), + cl_ntoh64(p_mcm_rec->mgid.unicast.interface_id)); + p_mgrp=NULL; + } + else if (well_known) + p_mgrp->well_known = TRUE; + + _out: + cl_plock_release(&p_osm->lock); + + return p_mgrp; +} + +static int load_svcr(osm_opensm_t *p_osm, ib_service_record_t *sr, + uint32_t modified_time, uint32_t lease_period) { - ib_member_rec_t mc_rec; - - osm_log( p_sa->p_log, OSM_LOG_FUNCS, - "osm_sa_create_template_record_ipoib: [\n" ); - - UNUSED_PARAM( p_opt ); - cl_memclr(&mc_rec, sizeof(mc_rec)); - - /* - * Fill in the default MC Member record - */ - mc_rec.mgid = osm_ipoib_mgid; - mc_rec.mtu = 4; /* 2048 Bytes */ - mc_rec.qkey = CL_HTON32(0x0b1b); /* This value is pushed into the mad, and thus needs - to be in network order */ - mc_rec.pkey = IB_DEFAULT_PKEY; - mc_rec.rate = 0x3; /* 10Gb/sec */ - mc_rec.pkt_life = OSM_DEFAULT_SUBNET_TIMEOUT; - mc_rec.sl_flow_hop = OSM_DEFAULT_SL << 28; - /* Note: scope needs to be consistent with MGID */ - mc_rec.scope_state = 0x21; - - osm_sa_add_well_known_mc_record(&p_sa->mcmr_rcv, &mc_rec); - - /* - * HACK: Until TS resolves their noncompliant join compmask - * we have to predefine the MGID - */ - mc_rec.mgid = osm_ts_ipoib_mgid; - osm_sa_add_well_known_mc_record(&p_sa->mcmr_rcv, &mc_rec); - - osm_log( p_sa->p_log, OSM_LOG_FUNCS, - "osm_sa_create_template_record_ipoib: ]\n" ); + osm_svcr_t *p_svcr; + int ret = 0; + + cl_plock_excl_acquire(&p_osm->lock); + if(osm_svcr_get_by_rid(&p_osm->subn, &p_osm->log, sr)) { + osm_log(&p_osm->log, OSM_LOG_VERBOSE, + "load_svcr ServiceRecord already exists.\n"); + goto _out; + } + + if (!(p_svcr = osm_svcr_new(sr))) { + osm_log(&p_osm->log, OSM_LOG_ERROR, + "load_svcr: cannot allocate new service struct\n"); + ret = -1; + goto _out; + } + + p_svcr->modified_time = modified_time; + p_svcr->lease_period = lease_period; + + osm_log(&p_osm->log, OSM_LOG_DEBUG, + "load_svcr: adding ServiceRecord...\n"); + + osm_svcr_insert_to_db(&p_osm->subn, &p_osm->log, p_svcr); + + if (lease_period != 0xffffffff) + cl_timer_trim(&p_osm->sa.sr_rcv.sr_timer, 1000); + + _out: + cl_plock_release(&p_osm->lock); + + return ret; } -/********************************************************************** - **********************************************************************/ -void -osm_sa_add_well_known_mc_record( - osm_mcmr_recv_t* const p_mcmr, - const ib_member_rec_t * const p_well_know_mc_rec) +static int load_infr(osm_opensm_t *p_osm, ib_inform_info_record_t *iir, + osm_mad_addr_t *addr) { + osm_infr_t infr, *p_infr; + int ret = 0; + + infr.h_bind = p_osm->sa.mad_ctrl.h_bind; + infr.p_infr_rcv = &p_osm->sa.infr_rcv; + /* other possible way to restore mad_addr partially is + to extract qpn from InformInfo and to find lid by gid */ + infr.report_addr = *addr; + infr.inform_record = *iir; + + cl_plock_excl_acquire(&p_osm->lock); + if (osm_infr_get_by_rec(&p_osm->subn, &p_osm->log, &infr)) { + osm_log(&p_osm->log, OSM_LOG_VERBOSE, + "load_infr: InformInfo Record already exists\n"); + goto _out; + } + + if (!(p_infr = osm_infr_new(&infr))) { + osm_log(&p_osm->log, OSM_LOG_ERROR, + "load_infr: cannot allocate new infr struct\n"); + ret = -1; + goto _out; + } + + osm_log(&p_osm->log, OSM_LOG_DEBUG, + "load_infr: adding InformInfo Record...\n"); + + osm_infr_insert_to_db(&p_osm->subn, &p_osm->log, p_infr); + + _out: + cl_plock_release(&p_osm->lock); + + return ret; +} - osm_mgrp_t * p_mgrp = NULL; - ib_api_status_t status; - ib_net64_t comp_mask; - - comp_mask = IB_MCR_COMPMASK_MTU | IB_MCR_COMPMASK_RATE; - status = osm_mcmr_rcv_create_new_mgrp( - p_mcmr, - comp_mask, - p_well_know_mc_rec, - NULL, - &p_mgrp); - if(p_mgrp) - { - p_mgrp->well_known = TRUE; - } - else - { - osm_log( p_mcmr->p_log, OSM_LOG_DEBUG, - "osm_sa_add_well_known_mc_record:" - "Failed to create a well known group\n"); - - } +#define UNPACK_FUNC(name,x) \ +int unpack_##name##x(char *p, uint##x##_t *val_ptr) \ +{ \ + char *q; \ + unsigned long long num; \ + num = strtoull(p, &q, 16); \ + if (num > ~((uint##x##_t)0x0) \ + || q == p || (!isspace(*q) && *q != ':')) { \ + *val_ptr = 0; \ + return -1; \ + } \ + *val_ptr = cl_hton##x((uint##x##_t)num); \ + return (int)(q - p); \ } -/********************************************************************** - **********************************************************************/ +#define cl_hton8(x) (x) + +UNPACK_FUNC(net,8); +UNPACK_FUNC(net,16); +UNPACK_FUNC(net,32); +UNPACK_FUNC(net,64); + +static int unpack_string(char *p, uint8_t *buf, unsigned len) +{ + char *q = p; + char delim = ' '; + + if (*q == '\'' || *q == '\"') + delim = *q++; + while (--len && *q && *q != delim) + *buf++ = *q++; + *buf = '\0'; + if (*q == delim && delim != ' ') + q++; + return (int)(q - p); +} + +static int unpack_string64(char *p, uint8_t *buf) +{ + return unpack_string(p, buf, 64); +} + +#define PARSE_AHEAD(p, x, name, val_ptr) { int _ret; \ + p = strstr(p, name); \ + if (!p) { \ + osm_log(&p_osm->log, OSM_LOG_ERROR, \ + "PARSE ERROR: %s:%u: cannot find \"%s\" string\n", \ + file_name, lineno, (name)); \ + ret = -2; \ + goto _error; \ + } \ + p += strlen(name); \ + _ret = unpack_##x(p, (val_ptr)); \ + if (_ret < 0) { \ + osm_log(&p_osm->log, OSM_LOG_ERROR, \ + "PARSE ERROR: %s:%u: cannot parse "#x" value " \ + "after \"%s\"\n", file_name, lineno, (name)); \ + ret = _ret; \ + goto _error; \ + } \ + p += _ret; \ +} + +int osm_sa_db_file_load(osm_opensm_t *p_osm) +{ + char line[1024]; + char *file_name; + FILE *file; + int ret = 0; + osm_mgrp_t *p_mgrp = NULL; + unsigned rereg_clients = 0; + unsigned lineno; + + file_name = p_osm->subn.opt.sa_db_file; + if (!file_name) { + osm_log(&p_osm->log, OSM_LOG_VERBOSE, + "osm_sa_db_file_load: sa db file name is not " + "specifed. Skip restore\n"); + return 0; + } + + file = fopen(file_name, "r"); + if (!file) { + osm_log(&p_osm->log, OSM_LOG_ERROR|OSM_LOG_SYS, + "osm_sa_db_file_load: ERR 0000: " + "cannot open sa db file \'%s\'. " + "Skip restoring\n", file_name); + return -1; + } + + lineno = 0; + + while (fgets(line, sizeof(line) - 1, file) != NULL) { + char *p; + uint8_t val; + + lineno++; + + p = line; + while (isspace(*p)) + p++; + + if (*p == '#') + continue; + + if (!strncmp(p, "MC Group", 8)) { + ib_member_rec_t mcm_rec; + ib_net16_t mlid; + unsigned well_known = 0; + + p_mgrp = NULL; + memset(&mcm_rec, 0, sizeof(mcm_rec)); + + PARSE_AHEAD(p, net16, " 0x", &mlid); + if(strstr(p, "well known")) + well_known = 1; + PARSE_AHEAD(p, net64, " mgid=0x", + &mcm_rec.mgid.unicast.prefix); + PARSE_AHEAD(p, net64, ":0x", + &mcm_rec.mgid.unicast.interface_id); + PARSE_AHEAD(p, net64, " port_gid=0x", + &mcm_rec.port_gid.unicast.prefix); + PARSE_AHEAD(p, net64, ":0x", + &mcm_rec.port_gid.unicast.interface_id); + PARSE_AHEAD(p, net32, " qkey=0x", &mcm_rec.qkey); + PARSE_AHEAD(p, net16, " mlid=0x", &mcm_rec.mlid); + PARSE_AHEAD(p, net8, " mtu=0x", &mcm_rec.mtu); + PARSE_AHEAD(p, net8, " tclass=0x", &mcm_rec.tclass); + PARSE_AHEAD(p, net16, " pkey=0x", &mcm_rec.pkey); + PARSE_AHEAD(p, net8, " rate=0x", &mcm_rec.rate); + PARSE_AHEAD(p, net8, " pkt_life=0x", &mcm_rec.pkt_life); + PARSE_AHEAD(p, net32, " sl_flow_hop=0x", + &mcm_rec.sl_flow_hop); + PARSE_AHEAD(p, net8, " scope_state=0x", + &mcm_rec.scope_state); + PARSE_AHEAD(p, net8, " proxy_join=0x", &val); + mcm_rec.proxy_join = val; + + p_mgrp = load_mcgroup(p_osm, mlid, &mcm_rec, + well_known); + if (!p_mgrp) + rereg_clients = 1; + } + else if (p_mgrp && !strncmp(p, "mcm_port", 8)) { + ib_gid_t port_gid; + ib_net64_t guid; + uint8_t scope_state; + boolean_t proxy_join; + + PARSE_AHEAD(p, net64, " port_gid=0x", + &port_gid.unicast.prefix); + PARSE_AHEAD(p, net64, ":0x", + &port_gid.unicast.interface_id); + PARSE_AHEAD(p, net8, " scope_state=0x", &scope_state); + PARSE_AHEAD(p, net8, " proxy_join=0x", &val); + proxy_join = val; + + guid = port_gid.unicast.interface_id; + if (cl_qmap_get(&p_mgrp->mcm_port_tbl, + port_gid.unicast.interface_id) == + cl_qmap_end(&p_mgrp->mcm_port_tbl)) + osm_mgrp_add_port(p_mgrp, &port_gid, + scope_state, proxy_join); + } + else if (!strncmp(p, "Service Record:", 15)) { + ib_service_record_t s_rec; + uint32_t modified_time, lease_period; + + p_mgrp = NULL; + memset(&s_rec, 0, sizeof(s_rec)); + + PARSE_AHEAD(p, net64, " id=0x", &s_rec.service_id); + PARSE_AHEAD(p, net64, " gid=0x", + &s_rec.service_gid.unicast.prefix); + PARSE_AHEAD(p, net64, ":0x", + &s_rec.service_gid.unicast.interface_id); + PARSE_AHEAD(p, net16, " pkey=0x", &s_rec.service_pkey); + PARSE_AHEAD(p, net32, " lease=0x", &s_rec.service_lease); + PARSE_AHEAD(p, net64, " key=0x", + (ib_net64_t *)(&s_rec.service_key[0])); + PARSE_AHEAD(p, net64, ":0x", + (ib_net64_t *)(&s_rec.service_key[8])); + PARSE_AHEAD(p, string64, " name=", s_rec.service_name); + PARSE_AHEAD(p, net64, " data8=0x", + (ib_net64_t *)(&s_rec.service_data8[0])); + PARSE_AHEAD(p, net64, ":0x", + (ib_net64_t *)(&s_rec.service_data8[8])); + PARSE_AHEAD(p, net64, " data16=0x", + (ib_net64_t *)(&s_rec.service_data16[0])); + PARSE_AHEAD(p, net64, ":0x", + (ib_net64_t *)(&s_rec.service_data16[4])); + PARSE_AHEAD(p, net64, " data32=0x", + (ib_net64_t *)(&s_rec.service_data32[0])); + PARSE_AHEAD(p, net64, ":0x", + (ib_net64_t *)(&s_rec.service_data32[2])); + PARSE_AHEAD(p, net64, " data64=0x", &s_rec.service_data64[0]); + PARSE_AHEAD(p, net64, ":0x", &s_rec.service_data64[1]); + PARSE_AHEAD(p, net32, " modified_time=0x", + &modified_time); + PARSE_AHEAD(p, net32, " lease_period=0x", + &lease_period); + + if (load_svcr(p_osm, &s_rec, cl_ntoh32(modified_time), + cl_ntoh32(lease_period))) + rereg_clients = 1; + } + else if (!strncmp(p, "InformInfo Record:", 18)) { + ib_inform_info_record_t i_rec; + osm_mad_addr_t rep_addr; + + p_mgrp = NULL; + memset(&i_rec, 0, sizeof(i_rec)); + memset(&rep_addr, 0, sizeof(rep_addr)); + + PARSE_AHEAD(p, net64, " subscriber_gid=0x", + &i_rec.subscriber_gid.unicast.prefix); + PARSE_AHEAD(p, net64, ":0x", + &i_rec.subscriber_gid.unicast.interface_id); + PARSE_AHEAD(p, net16, " subscriber_enum=0x", + &i_rec.subscriber_enum); + PARSE_AHEAD(p, net64, " gid=0x", + &i_rec.inform_info.gid.unicast.prefix); + PARSE_AHEAD(p, net64, ":0x", + &i_rec.inform_info.gid.unicast.interface_id); + PARSE_AHEAD(p, net16, " lid_range_begin=0x", + &i_rec.inform_info.lid_range_begin); + PARSE_AHEAD(p, net16, " lid_range_end=0x", + &i_rec.inform_info.lid_range_end); + PARSE_AHEAD(p, net8, " is_generic=0x", + &i_rec.inform_info.is_generic); + PARSE_AHEAD(p, net8, " subscribe=0x", + &i_rec.inform_info.subscribe); + PARSE_AHEAD(p, net16, " trap_type=0x", + &i_rec.inform_info.trap_type); + PARSE_AHEAD(p, net16, " trap_num=0x", + &i_rec.inform_info.g_or_v.generic.trap_num); + PARSE_AHEAD(p, net32, " qpn_resp_time_val=0x", + &i_rec.inform_info.g_or_v.generic.qpn_resp_time_val); + PARSE_AHEAD(p, net32, " node_type=0x", + (uint32_t *)&i_rec.inform_info.g_or_v.generic.reserved2); + + PARSE_AHEAD(p, net16, " rep_addr: lid=0x", + &rep_addr.dest_lid); + PARSE_AHEAD(p, net8, " path_bits=0x", + &rep_addr.path_bits); + PARSE_AHEAD(p, net8, " static_rate=0x", + &rep_addr.static_rate); + PARSE_AHEAD(p, net32, " remote_qp=0x", + &rep_addr.addr_type.gsi.remote_qp); + PARSE_AHEAD(p, net32, " remote_qkey=0x", + &rep_addr.addr_type.gsi.remote_qkey); + PARSE_AHEAD(p, net16, " pkey=0x", + &rep_addr.addr_type.gsi.pkey); + PARSE_AHEAD(p, net8, " sl=0x", + &rep_addr.addr_type.gsi.service_level); + + if (load_infr(p_osm, &i_rec, &rep_addr)) + rereg_clients = 1; + } + } + + if (!rereg_clients) + p_osm->subn.opt.no_clients_rereg = TRUE; + + _error: + fclose(file); + return ret; +} diff --git a/trunk/ulp/opensm/user/opensm/osm_sa_class_port_info.c b/trunk/ulp/opensm/user/opensm/osm_sa_class_port_info.c index 58d9dab7..493fd157 100644 --- a/trunk/ulp/opensm/user/opensm/osm_sa_class_port_info.c +++ b/trunk/ulp/opensm/user/opensm/osm_sa_class_port_info.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Implementation of osm_cpi_rcv_t. @@ -44,16 +45,12 @@ * $Revision: 1.8 $ */ -/* - Next available error code: 0x403 -*/ - #if HAVE_CONFIG_H # include #endif /* HAVE_CONFIG_H */ +#include #include -#include #include #include #include @@ -80,7 +77,7 @@ void osm_cpi_rcv_construct( IN osm_cpi_rcv_t* const p_rcv ) { - cl_memclr( p_rcv, sizeof(*p_rcv) ); + memset( p_rcv, 0, sizeof(*p_rcv) ); } /********************************************************************** @@ -125,19 +122,19 @@ osm_cpi_rcv_init( static void __osm_cpi_rcv_respond( IN osm_cpi_rcv_t* const p_rcv, - IN const osm_madw_t* const p_madw) + IN const osm_madw_t* const p_madw ) { osm_madw_t* p_resp_madw; - const ib_sa_mad_t* p_sa_mad; - ib_sa_mad_t* p_resp_sa_mad; + const ib_sa_mad_t* p_sa_mad; + ib_sa_mad_t* p_resp_sa_mad; ib_class_port_info_t *p_resp_cpi; - ib_api_status_t status; - ib_gid_t zero_gid; - uint8_t rtv; + ib_api_status_t status; + ib_gid_t zero_gid; + uint8_t rtv; OSM_LOG_ENTER( p_rcv->p_log, __osm_cpi_rcv_respond ); - cl_memclr(&zero_gid, sizeof(ib_gid_t)); + memset(&zero_gid, 0, sizeof(ib_gid_t)); /* Get a MAD to reply. Address of Mad is in the received mad_wrapper @@ -157,11 +154,10 @@ __osm_cpi_rcv_respond( p_sa_mad = osm_madw_get_sa_mad_ptr( p_madw ); p_resp_sa_mad = osm_madw_get_sa_mad_ptr( p_resp_madw ); - cl_memcpy( p_resp_sa_mad, p_sa_mad, IB_SA_MAD_HDR_SIZE ); + memcpy( p_resp_sa_mad, p_sa_mad, IB_SA_MAD_HDR_SIZE ); p_resp_sa_mad->method |= IB_MAD_METHOD_RESP_MASK; - /* C15-0.1.5 - always return SM_Key = 0 (table 151 p 782) */ + /* C15-0.1.5 - always return SM_Key = 0 (table 185 p 884) */ p_resp_sa_mad->sm_key = 0; - p_resp_sa_mad->paylen_newwin = 0; p_resp_cpi = (ib_class_port_info_t*)ib_sa_mad_get_payload_ptr( p_resp_sa_mad ); @@ -172,7 +168,8 @@ __osm_cpi_rcv_respond( /* transaction timeout is in msec */ if (p_rcv->p_subn->opt.transaction_timeout > __msecs_to_rtv_table[MAX_MSECS_TO_RTV]) rtv = MAX_MSECS_TO_RTV - 1; - else { + else + { for (rtv = 0; rtv < MAX_MSECS_TO_RTV; rtv++) { if (p_rcv->p_subn->opt.transaction_timeout <= __msecs_to_rtv_table[rtv]) break; @@ -194,30 +191,32 @@ __osm_cpi_rcv_respond( p_resp_cpi->trap_qkey = IB_QP1_WELL_KNOWN_Q_KEY; /* set specific capability mask bits */ - /* we do not support the optionals: + /* we do not support the following optional records: OSM_CAP_IS_SUBN_OPT_RECS_SUP : - SwitchInfoRecord, - LinearForwardingTableRecord, (we do support it under the table) RandomForwardingTableRecord, - MulticastForwardingTableRecord, - SMInfoRecord, (we do support it under the table) - InformInfoRecord, - LinkRecord, (we do support it under the table) ServiceAssociationRecord + other optional records supported "under the table" - OSM_CAP_IS_SUBN_OPT_MULTI_PATH_SUP: - MultiPathRecord, + OSM_CAP_IS_MULTIPATH_SUP: TraceRecord - OSM_CAP_IS_SUBN_OPT_REINIT_SUP: + OSM_CAP_IS_REINIT_SUP: For reinitialization functionality. - So not sending traps, but supporting Get(Notice) and Set(Notice): + So not sending traps, but supporting Get(Notice) and Set(Notice). */ - p_resp_cpi->cap_mask = 0x2; /* Note host notation replaced later */ + + /* Note host notation replaced later */ +#if defined (VENDOR_RMPP_SUPPORT) && defined (DUAL_SIDED_RMPP) + p_resp_cpi->cap_mask = OSM_CAP_IS_SUBN_GET_SET_NOTICE_SUP | + OSM_CAP_IS_PORT_INFO_CAPMASK_MATCH_SUPPORTED | + OSM_CAP_IS_MULTIPATH_SUP; +#else + p_resp_cpi->cap_mask = OSM_CAP_IS_SUBN_GET_SET_NOTICE_SUP | + OSM_CAP_IS_PORT_INFO_CAPMASK_MATCH_SUPPORTED; +#endif if (p_rcv->p_subn->opt.no_multicast_option != TRUE) p_resp_cpi->cap_mask |= OSM_CAP_IS_UD_MCAST_SUP; - p_resp_cpi->cap_mask = cl_hton16(p_resp_cpi->cap_mask); if( osm_log_is_active( p_rcv->p_log, OSM_LOG_FRAMES ) ) @@ -254,7 +253,7 @@ osm_cpi_rcv_process( p_sa_mad = osm_madw_get_sa_mad_ptr( p_madw ); - /* we only supports GET */ + /* we only support GET */ if (p_sa_mad->method != IB_MAD_METHOD_GET) { osm_log( p_rcv->p_log, OSM_LOG_ERROR, @@ -278,3 +277,4 @@ osm_cpi_rcv_process( Exit: OSM_LOG_EXIT( p_rcv->p_log ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_sa_class_port_info_ctrl.c b/trunk/ulp/opensm/user/opensm/osm_sa_class_port_info_ctrl.c index d67a78f0..dbd55dca 100644 --- a/trunk/ulp/opensm/user/opensm/osm_sa_class_port_info_ctrl.c +++ b/trunk/ulp/opensm/user/opensm/osm_sa_class_port_info_ctrl.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Implementation of osm_pr_rcv_ctrl_t. @@ -44,15 +45,11 @@ * $Revision: 1.3 $ */ -/* - Next available error code: 0x203 -*/ - #if HAVE_CONFIG_H # include #endif /* HAVE_CONFIG_H */ -#include +#include #include #include @@ -74,7 +71,7 @@ void osm_cpi_rcv_ctrl_construct( IN osm_cpi_rcv_ctrl_t* const p_ctrl ) { - cl_memclr( p_ctrl, sizeof(*p_ctrl) ); + memset( p_ctrl, 0, sizeof(*p_ctrl) ); p_ctrl->h_disp = CL_DISP_INVALID_HANDLE; } @@ -126,3 +123,4 @@ osm_cpi_rcv_ctrl_init( return( status ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_sa_guidinfo_record.c b/trunk/ulp/opensm/user/opensm/osm_sa_guidinfo_record.c index adba80e1..2c0bce9f 100644 --- a/trunk/ulp/opensm/user/opensm/osm_sa_guidinfo_record.c +++ b/trunk/ulp/opensm/user/opensm/osm_sa_guidinfo_record.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Implementation of osm_gir_rcv_t. @@ -43,16 +44,12 @@ * */ -/* - Next available error code: 0x403 -*/ - #if HAVE_CONFIG_H # include #endif /* HAVE_CONFIG_H */ +#include #include -#include #include #include #include @@ -71,7 +68,6 @@ typedef struct _osm_gir_item { cl_pool_item_t pool_item; ib_guidinfo_record_t rec; - } osm_gir_item_t; typedef struct _osm_gir_search_ctxt @@ -81,7 +77,6 @@ typedef struct _osm_gir_search_ctxt cl_qlist_t* p_list; osm_gir_rcv_t* p_rcv; const osm_physp_t* p_req_physp; - } osm_gir_search_ctxt_t; /********************************************************************** @@ -90,7 +85,7 @@ void osm_gir_rcv_construct( IN osm_gir_rcv_t* const p_rcv ) { - cl_memclr( p_rcv, sizeof(*p_rcv) ); + memset( p_rcv, 0, sizeof(*p_rcv) ); cl_qlock_pool_construct( &p_rcv->pool ); } @@ -168,13 +163,13 @@ __osm_gir_rcv_new_gir( if( osm_log_is_active( p_rcv->p_log, OSM_LOG_DEBUG ) ) { - osm_log( p_rcv->p_log, OSM_LOG_ERROR, + osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "__osm_gir_rcv_new_gir: " "New GUIDInfoRecord: lid 0x%X, block num %d\n", cl_ntoh16( match_lid ), block_num ); } - cl_memclr( &p_rec_item->rec, sizeof( p_rec_item->rec ) ); + memset( &p_rec_item->rec, 0, sizeof( p_rec_item->rec ) ); p_rec_item->rec.lid = match_lid; p_rec_item->rec.block_num = block_num; @@ -204,12 +199,10 @@ __osm_sa_gir_create_gir( uint8_t port_num; uint8_t num_ports; uint16_t match_lid_ho; - uint16_t lid_ho; ib_net16_t base_lid_ho; ib_net16_t max_lid_ho; uint8_t lmc; ib_net64_t port_guid; - ib_api_status_t status; const ib_port_info_t* p_pi; uint8_t block_num, start_block_num, end_block_num, num_blocks; @@ -217,7 +210,7 @@ __osm_sa_gir_create_gir( if( osm_log_is_active( p_rcv->p_log, OSM_LOG_DEBUG ) ) { - osm_log( p_rcv->p_log, OSM_LOG_ERROR, + osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "__osm_sa_gir_create_gir: " "Looking for GUIDRecord with LID: 0x%X GUID:0x%016" PRIx64 "\n", cl_ntoh16( match_lid ), @@ -252,70 +245,60 @@ __osm_sa_gir_create_gir( continue; p_pi = osm_physp_get_port_info_ptr( p_physp ); + + /* + Note: the following check is a temporary workaround + Since 1. GUIDCap should never be 0 on ports where this applies + and 2. GUIDCap should not be used on ports where it doesn't apply + So this should really be a check for whether the port is a + switch external port or not! + */ + if ( p_pi->guid_cap == 0 ) + continue; + num_blocks = p_pi->guid_cap / 8; if ( p_pi->guid_cap % 8 ) num_blocks++; - if (match_block_num == 255) + if ( match_block_num == 255 ) { start_block_num = 0; end_block_num = num_blocks - 1; } else { - if (match_block_num >= num_blocks) + if ( match_block_num >= num_blocks ) continue; end_block_num = start_block_num = match_block_num; } base_lid_ho = cl_ntoh16( osm_physp_get_base_lid( p_physp ) ); - lmc = osm_physp_get_lmc( p_physp ); - max_lid_ho = (uint16_t)( base_lid_ho + (1 << lmc) - 1 ); match_lid_ho = cl_ntoh16( match_lid ); - if( match_lid_ho ) { + lmc = osm_physp_get_lmc( p_physp ); + max_lid_ho = (uint16_t)( base_lid_ho + (1 << lmc) - 1 ); + /* We validate that the lid belongs to this node. */ if( osm_log_is_active( p_rcv->p_log, OSM_LOG_DEBUG ) ) { - osm_log( p_rcv->p_log, OSM_LOG_ERROR, + osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "__osm_sa_gir_create_gir: " "Comparing LID: 0x%X <= 0x%X <= 0x%X\n", - cl_ntoh16( base_lid_ho ), - cl_ntoh16( match_lid_ho ), - cl_ntoh16( max_lid_ho ) + base_lid_ho, match_lid_ho, max_lid_ho ); } - if( (match_lid_ho <= max_lid_ho) && (match_lid_ho >= base_lid_ho) ) - { - /* - Ignore return code for now. - */ - for (block_num = start_block_num; block_num <= end_block_num; block_num++) - __osm_gir_rcv_new_gir( p_rcv, p_node, p_list, - port_guid, match_lid, - p_physp, block_num ); - } - } - else - { - /* - For every lid value create the GUIDInfo record(s). - */ - for( lid_ho = base_lid_ho; lid_ho <= max_lid_ho; lid_ho++ ) - { - for (block_num = start_block_num; block_num <= end_block_num; block_num++) - { - status = __osm_gir_rcv_new_gir( p_rcv, p_node, p_list, - port_guid, cl_hton16( lid_ho ), - p_physp, block_num ); - if( status != IB_SUCCESS ) - break; - } - } + if ( match_lid_ho < base_lid_ho || match_lid_ho > max_lid_ho ) + continue; } + + for (block_num = start_block_num; block_num <= end_block_num; block_num++) + __osm_gir_rcv_new_gir( p_rcv, p_node, p_list, + port_guid, cl_ntoh16(base_lid_ho), + p_physp, block_num ); + } OSM_LOG_EXIT( p_rcv->p_log ); @@ -325,19 +308,19 @@ __osm_sa_gir_create_gir( **********************************************************************/ void __osm_sa_gir_by_comp_mask_cb( - IN cl_map_item_t* const p_map_item, - IN void* context ) + IN cl_map_item_t* const p_map_item, + IN void* context ) { const osm_gir_search_ctxt_t* const p_ctxt = (osm_gir_search_ctxt_t *)context; - const osm_node_t* const p_node = (osm_node_t*)p_map_item; - const ib_guidinfo_record_t* const p_rcvd_rec = p_ctxt->p_rcvd_rec; - const osm_physp_t* const p_req_physp = p_ctxt->p_req_physp; - osm_gir_rcv_t* const p_rcv = p_ctxt->p_rcv; - const ib_guid_info_t* p_comp_gi; - ib_net64_t const comp_mask = p_ctxt->comp_mask; - ib_net64_t match_port_guid = 0; - ib_net16_t match_lid = 0; - uint8_t match_block_num = 255; + const osm_node_t* const p_node = (osm_node_t*)p_map_item; + const ib_guidinfo_record_t* const p_rcvd_rec = p_ctxt->p_rcvd_rec; + const osm_physp_t* const p_req_physp = p_ctxt->p_req_physp; + osm_gir_rcv_t* const p_rcv = p_ctxt->p_rcv; + const ib_guid_info_t* p_comp_gi; + ib_net64_t const comp_mask = p_ctxt->comp_mask; + ib_net64_t match_port_guid = 0; + ib_net16_t match_lid = 0; + uint8_t match_block_num = 255; OSM_LOG_ENTER( p_ctxt->p_rcv->p_log, __osm_sa_gir_by_comp_mask_cb); @@ -418,13 +401,13 @@ osm_gir_rcv_process( const ib_guidinfo_record_t* p_rcvd_rec; cl_qlist_t rec_list; osm_madw_t* p_resp_madw; - ib_sa_mad_t* p_resp_sa_mad; + ib_sa_mad_t* p_resp_sa_mad; ib_guidinfo_record_t* p_resp_rec; - uint32_t num_rec, pre_trim_num_rec; + uint32_t num_rec, pre_trim_num_rec; #ifndef VENDOR_RMPP_SUPPORT - uint32_t trim_num_rec; + uint32_t trim_num_rec; #endif - uint32_t i; + uint32_t i; osm_gir_search_ctxt_t context; osm_gir_item_t* p_rec_item; ib_api_status_t status; @@ -441,6 +424,18 @@ osm_gir_rcv_process( CL_ASSERT( p_rcvd_mad->attr_id == IB_MAD_ATTR_GUIDINFO_RECORD ); + /* we only support SubnAdmGet and SubnAdmGetTable methods */ + if ( (p_rcvd_mad->method != IB_MAD_METHOD_GET) && + (p_rcvd_mad->method != IB_MAD_METHOD_GETTABLE) ) + { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "osm_gir_rcv_process: ERR 5105: " + "Unsupported Method (%s)\n", + ib_get_sa_method_str( p_rcvd_mad->method ) ); + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_MAD_STATUS_UNSUP_METHOD_ATTR ); + goto Exit; + } + /* update the requester physical port. */ p_req_physp = osm_get_physp_by_mad_addr(p_rcv->p_log, p_rcv->p_subn, @@ -453,17 +448,6 @@ osm_gir_rcv_process( goto Exit; } - if ( (p_rcvd_mad->method != IB_MAD_METHOD_GET) && - (p_rcvd_mad->method != IB_MAD_METHOD_GETTABLE) ) - { - osm_log( p_rcv->p_log, OSM_LOG_ERROR, - "osm_gir_rcv_process: ERR 5105: " - "Unsupported Method (%s)\n", - ib_get_sa_method_str( p_rcvd_mad->method ) ); - osm_sa_send_error( p_rcv->p_resp, p_madw, IB_SA_MAD_STATUS_REQ_INVALID); - goto Exit; - } - if ( osm_log_is_active( p_rcv->p_log, OSM_LOG_DEBUG ) ) osm_dump_guidinfo_record( p_rcv->p_log, p_rcvd_rec, OSM_LOG_DEBUG ); @@ -489,24 +473,32 @@ osm_gir_rcv_process( * C15-0.1.30: * If we do a SubnAdmGet and got more than one record it is an error ! */ - if ( (p_rcvd_mad->method == IB_MAD_METHOD_GET) && - (num_rec > 1)) { - osm_log( p_rcv->p_log, OSM_LOG_ERROR, - "osm_gir_rcv_process: " - "Got more than one record for SubnAdmGet (%u)\n", - num_rec ); - osm_sa_send_error( p_rcv->p_resp, p_madw, - IB_SA_MAD_STATUS_TOO_MANY_RECORDS); - - /* need to set the mem free ... */ - p_rec_item = (osm_gir_item_t*)cl_qlist_remove_head( &rec_list ); - while( p_rec_item != (osm_gir_item_t*)cl_qlist_end( &rec_list ) ) + if (p_rcvd_mad->method == IB_MAD_METHOD_GET) + { + if (num_rec == 0) { - cl_qlock_pool_put( &p_rcv->pool, &p_rec_item->pool_item ); - p_rec_item = (osm_gir_item_t*)cl_qlist_remove_head( &rec_list ); + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_SA_MAD_STATUS_NO_RECORDS ); + goto Exit; } + if (num_rec > 1) + { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "osm_gir_rcv_process: ERR 5103: " + "Got more than one record for SubnAdmGet (%u)\n", + num_rec ); + osm_sa_send_error( p_rcv->p_resp, p_madw, + IB_SA_MAD_STATUS_TOO_MANY_RECORDS ); + + /* need to set the mem free ... */ + p_rec_item = (osm_gir_item_t*)cl_qlist_remove_head( &rec_list ); + while( p_rec_item != (osm_gir_item_t*)cl_qlist_end( &rec_list ) ) + { + cl_qlock_pool_put( &p_rcv->pool, &p_rec_item->pool_item ); + p_rec_item = (osm_gir_item_t*)cl_qlist_remove_head( &rec_list ); + } - goto Exit; + goto Exit; + } } pre_trim_num_rec = num_rec; @@ -528,8 +520,7 @@ osm_gir_rcv_process( if ((p_rcvd_mad->method == IB_MAD_METHOD_GET) && (num_rec == 0)) { - osm_sa_send_error( p_rcv->p_resp, p_madw, - IB_SA_MAD_STATUS_NO_RECORDS ); + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_SA_MAD_STATUS_NO_RECORDS ); goto Exit; } @@ -553,9 +544,7 @@ osm_gir_rcv_process( cl_qlock_pool_put( &p_rcv->pool, &p_rec_item->pool_item ); } - osm_sa_send_error( p_rcv->p_resp, p_madw, - IB_SA_MAD_STATUS_NO_RESOURCES ); - + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_SA_MAD_STATUS_NO_RESOURCES ); goto Exit; } @@ -567,9 +556,9 @@ osm_gir_rcv_process( Then copy all records from the list into the response payload. */ - cl_memcpy( p_resp_sa_mad, p_rcvd_mad, IB_SA_MAD_HDR_SIZE ); - p_resp_sa_mad->method = (uint8_t)(p_resp_sa_mad->method | 0x80); - /* C15-0.1.5 - always return SM_Key = 0 (table 151 p 782) */ + memcpy( p_resp_sa_mad, p_rcvd_mad, IB_SA_MAD_HDR_SIZE ); + p_resp_sa_mad->method |= IB_MAD_METHOD_RESP_MASK; + /* C15-0.1.5 - always return SM_Key = 0 (table 185 p 884) */ p_resp_sa_mad->sm_key = 0; /* Fill in the offset (paylen will be done by the rmpp SAR) */ p_resp_sa_mad->attr_offset = @@ -607,11 +596,11 @@ osm_gir_rcv_process( CL_ASSERT( cl_is_qlist_empty( &rec_list ) ); status = osm_vendor_send( p_resp_madw->h_bind, p_resp_madw, FALSE); - if(status != IB_SUCCESS) + if (status != IB_SUCCESS) { osm_log(p_rcv->p_log, OSM_LOG_ERROR, "osm_gir_rcv_process: ERR 5107: " - "osm_vendor_send. status = %s\n", + "osm_vendor_send status = %s\n", ib_get_err_str(status)); goto Exit; } @@ -619,3 +608,4 @@ osm_gir_rcv_process( Exit: OSM_LOG_EXIT( p_rcv->p_log ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_sa_guidinfo_record_ctrl.c b/trunk/ulp/opensm/user/opensm/osm_sa_guidinfo_record_ctrl.c index 511bdd90..6e0b9e20 100644 --- a/trunk/ulp/opensm/user/opensm/osm_sa_guidinfo_record_ctrl.c +++ b/trunk/ulp/opensm/user/opensm/osm_sa_guidinfo_record_ctrl.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Implementation of osm_gir_rcv_ctrl_t. @@ -43,15 +44,11 @@ * */ -/* - Next available error code: 0x203 -*/ - #if HAVE_CONFIG_H # include #endif /* HAVE_CONFIG_H */ -#include +#include #include #include @@ -73,7 +70,7 @@ void osm_gir_rcv_ctrl_construct( IN osm_gir_rcv_ctrl_t* const p_ctrl ) { - cl_memclr( p_ctrl, sizeof(*p_ctrl) ); + memset( p_ctrl, 0, sizeof(*p_ctrl) ); p_ctrl->h_disp = CL_DISP_INVALID_HANDLE; } @@ -124,3 +121,4 @@ osm_gir_rcv_ctrl_init( OSM_LOG_EXIT( p_log ); return( status ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_sa_informinfo.c b/trunk/ulp/opensm/user/opensm/osm_sa_informinfo.c index 083e0d15..56619130 100644 --- a/trunk/ulp/opensm/user/opensm/osm_sa_informinfo.c +++ b/trunk/ulp/opensm/user/opensm/osm_sa_informinfo.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -48,8 +48,8 @@ # include #endif /* HAVE_CONFIG_H */ +#include #include -#include #include #include #include @@ -65,13 +65,34 @@ #include #include +#define OSM_IIR_RCV_POOL_MIN_SIZE 32 +#define OSM_IIR_RCV_POOL_GROW_SIZE 32 + +typedef struct _osm_iir_item +{ + cl_pool_item_t pool_item; + ib_inform_info_record_t rec; +} osm_iir_item_t; + +typedef struct _osm_iir_search_ctxt +{ + const ib_inform_info_record_t* p_rcvd_rec; + ib_net64_t comp_mask; + cl_qlist_t* p_list; + ib_gid_t subscriber_gid; + ib_net16_t subscriber_enum; + osm_infr_rcv_t* p_rcv; + osm_physp_t* p_req_physp; +} osm_iir_search_ctxt_t; + /********************************************************************** **********************************************************************/ void osm_infr_rcv_construct( IN osm_infr_rcv_t* const p_rcv ) { - cl_memclr( p_rcv, sizeof(*p_rcv) ); + memset( p_rcv, 0, sizeof(*p_rcv) ); + cl_qlock_pool_construct( &p_rcv->pool ); } /********************************************************************** @@ -80,7 +101,10 @@ void osm_infr_rcv_destroy( IN osm_infr_rcv_t* const p_rcv ) { + CL_ASSERT( p_rcv ); + OSM_LOG_ENTER( p_rcv->p_log, osm_infr_rcv_destroy ); + cl_qlock_pool_destroy( &p_rcv->pool ); OSM_LOG_EXIT( p_rcv->p_log ); } @@ -89,11 +113,11 @@ osm_infr_rcv_destroy( ib_api_status_t osm_infr_rcv_init( IN osm_infr_rcv_t* const p_rcv, - IN osm_sa_resp_t* const p_resp, + IN osm_sa_resp_t* const p_resp, IN osm_mad_pool_t* const p_mad_pool, - IN osm_subn_t* const p_subn, - IN osm_log_t* const p_log, - IN cl_plock_t* const p_lock ) + IN osm_subn_t* const p_subn, + IN osm_log_t* const p_log, + IN cl_plock_t* const p_lock ) { ib_api_status_t status = IB_ERROR; @@ -107,8 +131,13 @@ osm_infr_rcv_init( p_rcv->p_resp = p_resp; p_rcv->p_mad_pool = p_mad_pool; - status = IB_SUCCESS; - /* Exit: */ + status = cl_qlock_pool_init( &p_rcv->pool, + OSM_IIR_RCV_POOL_MIN_SIZE, + 0, + OSM_IIR_RCV_POOL_GROW_SIZE, + sizeof(osm_iir_item_t), + NULL, NULL, NULL ); + OSM_LOG_EXIT( p_rcv->p_log ); return( status ); } @@ -116,15 +145,15 @@ osm_infr_rcv_init( /********************************************************************** o13-14.1.1: Except for Set(InformInfo) requests with Inform- Info:LIDRangeBegin=0xFFFF, managers that support event forwarding -shall, upon receiving a Set(InformInfo), verify that the requester originating -the Set(InformInfo) and a Trap() source identified by Inform- -can acess each other - can use path record to verify that. +shall, upon receiving a Set(InformInfo), verify that the requester +originating the Set(InformInfo) and a Trap() source identified by Inform- +can access each other - can use path record to verify that. **********************************************************************/ static boolean_t __validate_ports_access_rights( IN osm_infr_rcv_t* const p_rcv, - IN osm_infr_t* p_infr_rec) + IN osm_infr_t* p_infr_rec ) { boolean_t valid = TRUE; osm_physp_t* p_requester_physp; @@ -134,18 +163,18 @@ __validate_ports_access_rights( ib_net16_t lid_range_begin; ib_net16_t lid_range_end; ib_net16_t lid; - const cl_ptr_vector_t* p_tbl; + const cl_ptr_vector_t* p_tbl; ib_gid_t zero_gid; OSM_LOG_ENTER( p_rcv->p_log, __validate_ports_access_rights ); /* get the requester physp from the request address */ - p_requester_physp = osm_get_physp_by_mad_addr(p_rcv->p_log, - p_rcv->p_subn, - &p_infr_rec->report_addr ); + p_requester_physp = osm_get_physp_by_mad_addr( p_rcv->p_log, + p_rcv->p_subn, + &p_infr_rec->report_addr ); - cl_memclr( &zero_gid, sizeof(zero_gid) ); - if ( cl_memcmp (&(p_infr_rec->inform_record.inform_info.gid), + memset( &zero_gid, 0, sizeof(zero_gid) ); + if ( memcmp (&(p_infr_rec->inform_record.inform_info.gid), &zero_gid, sizeof(ib_gid_t) ) ) { /* a gid is defined */ @@ -157,13 +186,13 @@ __validate_ports_access_rights( { osm_log( p_rcv->p_log, OSM_LOG_ERROR, "__validate_ports_access_rights: ERR 4301: " - "Invalid port guid: 0x%016\n", - portguid ); + "Invalid port guid: 0x%016" PRIx64 "\n", + cl_ntoh64(portguid) ); valid = FALSE; goto Exit; } - /* get the destination informInfo physical port */ + /* get the destination InformInfo physical port */ p_physp = osm_port_get_default_phys_ptr(p_port); /* make sure that the requester and destination port can access each other @@ -176,7 +205,9 @@ __validate_ports_access_rights( valid = FALSE; goto Exit; } - } else { + } + else + { /* gid is zero - check if LID range is defined */ lid_range_begin = cl_ntoh16(p_infr_rec->inform_record.inform_info.lid_range_begin); /* if lid is 0xFFFF - meaning all endports managed by the manager */ @@ -192,29 +223,29 @@ __validate_ports_access_rights( /* go over all defined lids within the range and make sure that the requester port can access them according to current partitioning. */ - for ( lid = lid_range_begin ; lid <= lid_range_end ; lid++ ) + for ( lid = lid_range_begin; lid <= lid_range_end; lid++ ) { p_tbl = &p_rcv->p_subn->port_lid_tbl; - if ( cl_ptr_vector_get_size(p_tbl) > lid ) + if ( cl_ptr_vector_get_size( p_tbl ) > lid ) { - p_port = cl_ptr_vector_get (p_tbl, lid ); + p_port = cl_ptr_vector_get( p_tbl, lid ); } else { /* lid requested is out of range */ osm_log( p_rcv->p_log, OSM_LOG_ERROR, "__validate_ports_access_rights: ERR 4302: " - "Given LID (%u) is out of range:%u\n", + "Given LID (0x%X) is out of range:0x%X\n", lid, cl_ptr_vector_get_size(p_tbl) ); valid = FALSE; goto Exit; } - if (p_port == NULL ) + if ( p_port == NULL ) continue; p_physp = osm_port_get_default_phys_ptr(p_port); - /* make sure that the requester and destination port can access each other - according to the current partitioning. */ + /* make sure that the requester and destination port can access + each other according to the current partitioning. */ if (! osm_physp_share_pkey( p_rcv->p_log, p_physp, p_requester_physp)) { osm_log( p_rcv->p_log, OSM_LOG_DEBUG, @@ -236,24 +267,22 @@ __validate_ports_access_rights( static boolean_t __validate_infr( - IN osm_infr_rcv_t* const p_rcv, - IN osm_infr_t* p_infr_rec ) + IN osm_infr_rcv_t* const p_rcv, + IN osm_infr_t* p_infr_rec ) { boolean_t valid = TRUE; OSM_LOG_ENTER( p_rcv->p_log, __validate_infr ); - valid = __validate_ports_access_rights( p_rcv, p_infr_rec); - if(!valid) + valid = __validate_ports_access_rights( p_rcv, p_infr_rec ); + if (!valid) { osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "__validate_infr: " - "Invalid Access for InformInfo\n"); + "Invalid Access for InformInfo\n" ); valid = FALSE; - goto Exit; } - Exit: OSM_LOG_EXIT( p_rcv->p_log ); return valid; } @@ -261,17 +290,17 @@ __validate_infr( /********************************************************************** o13-12.1.1: Confirm a valid request for event subscription by responding with an InformInfo attribute that is a copy of the data in the -Set(InformInfo) request, but with InformInfo:Subscribe set to 1. +Set(InformInfo) request. **********************************************************************/ static void __osm_infr_rcv_respond( IN osm_infr_rcv_t* const p_rcv, - IN const osm_madw_t* const p_madw) + IN const osm_madw_t* const p_madw ) { - osm_madw_t* p_resp_madw; + osm_madw_t* p_resp_madw; const ib_sa_mad_t* p_sa_mad; ib_sa_mad_t* p_resp_sa_mad; - ib_inform_info_t* p_resp_infr; + ib_inform_info_t* p_resp_infr; ib_api_status_t status; OSM_LOG_ENTER( p_rcv->p_log, __osm_infr_rcv_respond ); @@ -290,7 +319,7 @@ __osm_infr_rcv_respond( p_madw->h_bind, MAD_BLOCK_SIZE, &p_madw->mad_addr ); - if( !p_resp_madw ) + if ( !p_resp_madw ) { osm_log( p_rcv->p_log, OSM_LOG_ERROR, "__osm_infr_rcv_respond: ERR 4303: " @@ -302,26 +331,21 @@ __osm_infr_rcv_respond( p_resp_sa_mad = osm_madw_get_sa_mad_ptr( p_resp_madw ); /* copy the request InformInfo */ - cl_memcpy( p_resp_sa_mad, p_sa_mad, MAD_BLOCK_SIZE ); + memcpy( p_resp_sa_mad, p_sa_mad, MAD_BLOCK_SIZE ); p_resp_sa_mad->method = IB_MAD_METHOD_GET_RESP; - /* C15-0.1.5 - always return SM_Key = 0 (table 151 p 782) */ + /* C15-0.1.5 - always return SM_Key = 0 (table 185 p 884) */ p_resp_sa_mad->sm_key = 0; - p_resp_sa_mad->paylen_newwin = - cl_hton32( sizeof(ib_inform_info_record_t) ); p_resp_infr = (ib_inform_info_t*)ib_sa_mad_get_payload_ptr( p_resp_sa_mad ); - /* confirm success */ - p_resp_infr->subscribe = 1; - status = osm_vendor_send( p_resp_madw->h_bind, p_resp_madw, FALSE ); - if( status != IB_SUCCESS ) + if ( status != IB_SUCCESS ) { osm_log( p_rcv->p_log, OSM_LOG_ERROR, "__osm_infr_rcv_respond: ERR 4304: " "Unable to send MAD (%s)\n", ib_get_err_str( status ) ); - /* osm_mad_pool_put( p_rcv->p_mad_pool, p_resp_madw ); */ + /* osm_mad_pool_put( p_rcv->p_mad_pool, p_resp_madw ); */ goto Exit; } @@ -330,83 +354,406 @@ __osm_infr_rcv_respond( } /********************************************************************** -Received an Set(InformInfo) MAD + **********************************************************************/ +static void +__osm_sa_inform_info_rec_by_comp_mask( + IN osm_infr_rcv_t* const p_rcv, + IN const osm_infr_t* const p_infr, + osm_iir_search_ctxt_t* const p_ctxt ) +{ + const ib_inform_info_record_t* p_rcvd_rec = NULL; + ib_net64_t comp_mask; + ib_net64_t portguid; + osm_port_t * p_subscriber_port; + osm_physp_t * p_subscriber_physp; + const osm_physp_t* p_req_physp; + osm_iir_item_t* p_rec_item; + + OSM_LOG_ENTER( p_rcv->p_log, __osm_sa_inform_info_rec_by_comp_mask ); + + p_rcvd_rec = p_ctxt->p_rcvd_rec; + comp_mask = p_ctxt->comp_mask; + p_req_physp = p_ctxt->p_req_physp; + + if (comp_mask & IB_IIR_COMPMASK_SUBSCRIBERGID) + { + if (memcmp(&p_infr->inform_record.subscriber_gid, + &p_ctxt->subscriber_gid, + sizeof(p_infr->inform_record.subscriber_gid))) + goto Exit; + } + + if (comp_mask & IB_IIR_COMPMASK_ENUM) + { + if (p_infr->inform_record.subscriber_enum != p_ctxt->subscriber_enum) + goto Exit; + } + + /* Implement any other needed search cases */ + + /* Ensure pkey is shared before returning any records */ + portguid = p_infr->inform_record.subscriber_gid.unicast.interface_id; + p_subscriber_port = osm_get_port_by_guid( p_rcv->p_subn, portguid ); + if ( p_subscriber_port == NULL ) + { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "__osm_sa_inform_info_rec_by_comp_mask: ERR 430D: " + "Invalid subscriber port guid: 0x%016" PRIx64 "\n", + cl_ntoh64(portguid) ); + goto Exit; + } + + /* get the subscriber InformInfo physical port */ + p_subscriber_physp = osm_port_get_default_phys_ptr(p_subscriber_port); + /* make sure that the requester and subscriber port can access each other + according to the current partitioning. */ + if (! osm_physp_share_pkey( p_rcv->p_log, p_req_physp, p_subscriber_physp )) + { + osm_log( p_rcv->p_log, OSM_LOG_DEBUG, + "__osm_sa_inform_info_rec_by_comp_mask: " + "requester and subscriber ports don't share pkey\n" ); + goto Exit; + } + + p_rec_item = (osm_iir_item_t*)cl_qlock_pool_get( &p_rcv->pool ); + if( p_rec_item == NULL ) + { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "__osm_sa_inform_info_rec_by_comp_mask: ERR 430E: " + "cl_qlock_pool_get failed\n" ); + goto Exit; + } + + memcpy((void *)&p_rec_item->rec, (void *)&p_infr->inform_record, sizeof(ib_inform_info_record_t)); + cl_qlist_insert_tail( p_ctxt->p_list, (cl_list_item_t*)&p_rec_item->pool_item ); + +Exit: + OSM_LOG_EXIT( p_rcv->p_log ); +} + +/********************************************************************** + **********************************************************************/ +static void +__osm_sa_inform_info_rec_by_comp_mask_cb( + IN cl_list_item_t* const p_list_item, + IN void* context ) +{ + const osm_infr_t* const p_infr = (osm_infr_t *)p_list_item; + osm_iir_search_ctxt_t* const p_ctxt = (osm_iir_search_ctxt_t *)context; + + __osm_sa_inform_info_rec_by_comp_mask( p_ctxt->p_rcv, p_infr, p_ctxt ); +} + +/********************************************************************** +Received a Get(InformInfoRecord) or GetTable(InformInfoRecord) MAD **********************************************************************/ -static -void +static void +osm_infr_rcv_process_get_method( + IN osm_infr_rcv_t* const p_rcv, + IN const osm_madw_t* const p_madw ) +{ + ib_sa_mad_t* p_rcvd_mad; + const ib_inform_info_record_t* p_rcvd_rec; + ib_inform_info_record_t* p_resp_rec; + cl_qlist_t rec_list; + osm_madw_t* p_resp_madw; + ib_sa_mad_t* p_resp_sa_mad; + uint32_t num_rec, pre_trim_num_rec; +#ifndef VENDOR_RMPP_SUPPORT + uint32_t trim_num_rec; +#endif + uint32_t i, j; + osm_iir_search_ctxt_t context; + osm_iir_item_t* p_rec_item; + ib_api_status_t status = IB_SUCCESS; + osm_physp_t* p_req_physp; + + OSM_LOG_ENTER( p_rcv->p_log, osm_infr_rcv_process_get_method ); + + CL_ASSERT( p_madw ); + p_rcvd_mad = osm_madw_get_sa_mad_ptr( p_madw ); + p_rcvd_rec = + (ib_inform_info_record_t*)ib_sa_mad_get_payload_ptr( p_rcvd_mad ); + + /* update the requester physical port. */ + p_req_physp = osm_get_physp_by_mad_addr(p_rcv->p_log, + p_rcv->p_subn, + osm_madw_get_mad_addr_ptr(p_madw) ); + if (p_req_physp == NULL) + { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "osm_infr_rcv_process_get_method: ERR 4309: " + "Cannot find requester physical port\n" ); + goto Exit; + } + + if( osm_log_is_active( p_rcv->p_log, OSM_LOG_DEBUG ) ) + osm_dump_inform_info_record( p_rcv->p_log, p_rcvd_rec, OSM_LOG_DEBUG ); + + cl_qlist_init( &rec_list ); + + context.p_rcvd_rec = p_rcvd_rec; + context.p_list = &rec_list; + context.comp_mask = p_rcvd_mad->comp_mask; + context.subscriber_gid = p_rcvd_rec->subscriber_gid; + context.subscriber_enum = p_rcvd_rec->subscriber_enum; + context.p_rcv = p_rcv; + context.p_req_physp = p_req_physp; + + osm_log( p_rcv->p_log, OSM_LOG_DEBUG, + "osm_infr_rcv_process_get_method: " + "Query Subscriber GID:0x%016" PRIx64 " : 0x%016" PRIx64 "(%02X) Enum:0x%X(%02X)\n", + cl_ntoh64(p_rcvd_rec->subscriber_gid.unicast.prefix), + cl_ntoh64(p_rcvd_rec->subscriber_gid.unicast.interface_id), + (p_rcvd_mad->comp_mask & IB_IIR_COMPMASK_SUBSCRIBERGID) != 0, + cl_ntoh16(p_rcvd_rec->subscriber_enum), + (p_rcvd_mad->comp_mask & IB_IIR_COMPMASK_ENUM) != 0 ); + + cl_plock_acquire( p_rcv->p_lock ); + + cl_qlist_apply_func( &p_rcv->p_subn->sa_infr_list, + __osm_sa_inform_info_rec_by_comp_mask_cb, + &context ); + + cl_plock_release( p_rcv->p_lock ); + + num_rec = cl_qlist_count( &rec_list ); + + /* + * C15-0.1.30: + * If we do a SubnAdmGet and got more than one record it is an error ! + */ + if (p_rcvd_mad->method == IB_MAD_METHOD_GET) + { + if (num_rec == 0) + { + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_SA_MAD_STATUS_NO_RECORDS ); + goto Exit; + } + if (num_rec > 1) + { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "osm_infr_rcv_process_get_method: ERR 430A: " + "More than one record for SubnAdmGet (%u)\n", + num_rec ); + osm_sa_send_error( p_rcv->p_resp, p_madw, + IB_SA_MAD_STATUS_TOO_MANY_RECORDS); + + /* need to set the mem free ... */ + p_rec_item = (osm_iir_item_t*)cl_qlist_remove_head( &rec_list ); + while( p_rec_item != (osm_iir_item_t*)cl_qlist_end( &rec_list ) ) + { + cl_qlock_pool_put( &p_rcv->pool, &p_rec_item->pool_item ); + p_rec_item = (osm_iir_item_t*)cl_qlist_remove_head( &rec_list ); + } + + goto Exit; + } + } + + pre_trim_num_rec = num_rec; +#ifndef VENDOR_RMPP_SUPPORT + /* we limit the number of records to a single packet */ + trim_num_rec = (MAD_BLOCK_SIZE - IB_SA_MAD_HDR_SIZE) / sizeof(ib_inform_info_record_t); + if (trim_num_rec < num_rec) + { + osm_log( p_rcv->p_log, OSM_LOG_VERBOSE, + "osm_infr_rcv_process_get_method: " + "Number of records:%u trimmed to:%u to fit in one MAD\n", + num_rec, trim_num_rec ); + num_rec = trim_num_rec; + } +#endif + + osm_log( p_rcv->p_log, OSM_LOG_DEBUG, + "osm_infr_rcv_process_get_method: " + "Returning %u records\n", num_rec ); + + /* + * Get a MAD to reply. Address of Mad is in the received mad_wrapper + */ + p_resp_madw = osm_mad_pool_get( p_rcv->p_mad_pool, + p_madw->h_bind, + num_rec * sizeof(ib_inform_info_record_t) + IB_SA_MAD_HDR_SIZE, + &p_madw->mad_addr ); + + if( !p_resp_madw ) + { + osm_log(p_rcv->p_log, OSM_LOG_ERROR, + "osm_infr_rcv_process_get_method: ERR 430B: " + "osm_mad_pool_get failed\n" ); + + for( i = 0; i < num_rec; i++ ) + { + p_rec_item = (osm_iir_item_t*)cl_qlist_remove_head( &rec_list ); + cl_qlock_pool_put( &p_rcv->pool, &p_rec_item->pool_item ); + } + + osm_sa_send_error( p_rcv->p_resp, p_madw, + IB_SA_MAD_STATUS_NO_RESOURCES ); + + goto Exit; + } + + p_resp_sa_mad = osm_madw_get_sa_mad_ptr( p_resp_madw ); + + /* + Copy the MAD header back into the response mad. + Set the 'R' bit and the payload length, + Then copy all records from the list into the response payload. + */ + + memcpy( p_resp_sa_mad, p_rcvd_mad, IB_SA_MAD_HDR_SIZE ); + p_resp_sa_mad->method |= IB_MAD_METHOD_RESP_MASK; + /* C15-0.1.5 - always return SM_Key = 0 (table 185 p 884) */ + p_resp_sa_mad->sm_key = 0; + /* Fill in the offset (paylen will be done by the rmpp SAR) */ + p_resp_sa_mad->attr_offset = + ib_get_attr_offset( sizeof(ib_inform_info_record_t) ); + + p_resp_rec = (ib_inform_info_record_t*)ib_sa_mad_get_payload_ptr( p_resp_sa_mad ); + +#ifndef VENDOR_RMPP_SUPPORT + /* we support only one packet RMPP - so we will set the first and + last flags for gettable */ + if (p_resp_sa_mad->method == IB_MAD_METHOD_GETTABLE_RESP) + { + p_resp_sa_mad->rmpp_type = IB_RMPP_TYPE_DATA; + p_resp_sa_mad->rmpp_flags = IB_RMPP_FLAG_FIRST | IB_RMPP_FLAG_LAST | IB_RMPP_FLAG_ACTIVE; + } +#else + /* forcefully define the packet as RMPP one */ + if (p_resp_sa_mad->method == IB_MAD_METHOD_GETTABLE_RESP) + p_resp_sa_mad->rmpp_flags = IB_RMPP_FLAG_ACTIVE; +#endif + + for( i = 0; i < pre_trim_num_rec; i++ ) + { + p_rec_item = (osm_iir_item_t*)cl_qlist_remove_head( &rec_list ); + /* copy only if not trimmed */ + if (i < num_rec) + { + *p_resp_rec = p_rec_item->rec; + /* clear reserved and pad fields in InformInfoRecord */ + for (j = 0; j < 6; j++) + p_resp_rec->reserved[j] = 0; + for (j = 0; j < 4; j++) + p_resp_rec->pad[j] = 0; + } + cl_qlock_pool_put( &p_rcv->pool, &p_rec_item->pool_item ); + p_resp_rec++; + } + + CL_ASSERT( cl_is_qlist_empty( &rec_list ) ); + + status = osm_vendor_send( p_resp_madw->h_bind, p_resp_madw, FALSE ); + if (status != IB_SUCCESS) + { + osm_log(p_rcv->p_log, OSM_LOG_ERROR, + "osm_infr_rcv_process_get_method: ERR 430C: " + "osm_vendor_send status = %s\n", + ib_get_err_str(status)); + goto Exit; + } + + Exit: + OSM_LOG_EXIT( p_rcv->p_log ); +} + +/********************************************************************* +Received a Set(InformInfo) MAD +**********************************************************************/ +static void osm_infr_rcv_process_set_method( IN osm_infr_rcv_t* const p_rcv, - IN const osm_madw_t* const p_madw ) + IN const osm_madw_t* const p_madw ) { ib_sa_mad_t *p_sa_mad; - ib_inform_info_t* p_recvd_inform_info; - osm_infr_t inform_info_rec; /* actual inform record to be stored for reports */ + ib_inform_info_t *p_recvd_inform_info; + osm_infr_t inform_info_rec; /* actual inform record to be stored for reports */ osm_infr_t *p_infr; - uint8_t subscribe; ib_net32_t qpn; - uint8_t resp_time_val; + uint8_t resp_time_val; + ib_api_status_t res; OSM_LOG_ENTER( p_rcv->p_log, osm_infr_rcv_process_set_method ); CL_ASSERT( p_madw ); + p_sa_mad = osm_madw_get_sa_mad_ptr( p_madw ); p_recvd_inform_info = (ib_inform_info_t*)ib_sa_mad_get_payload_ptr( p_sa_mad ); - /* the dump routine is not defined yet - if( osm_log_is_active( p_rcv->p_log, OSM_LOG_DEBUG ) ) - { - osm_dump_inform_info_record( p_rcv->p_log, - p_recvd_service_rec, - OSM_LOG_DEBUG ); - } - */ +#if 0 + if( osm_log_is_active( p_rcv->p_log, OSM_LOG_DEBUG ) ) + osm_dump_inform_info( p_rcv->p_log, p_recvd_inform_info, OSM_LOG_DEBUG ); +#endif /* Grab the lock */ - cl_plock_excl_acquire(p_rcv->p_lock); + cl_plock_excl_acquire( p_rcv->p_lock ); /* define the inform record */ inform_info_rec.inform_record.inform_info = *p_recvd_inform_info; - /* following C13-32.1.2 Tbl 107 : we only copy the source address vector */ + /* following C13-32.1.2 Tbl 120: we only copy the source address vector */ inform_info_rec.report_addr = p_madw->mad_addr; /* we will need to know the mad srvc to send back through */ inform_info_rec.h_bind = p_madw->h_bind; inform_info_rec.p_infr_rcv = p_rcv; - /* HACK: enum is always 0 */ + /* update the subscriber GID according to mad address */ + res = osm_get_gid_by_mad_addr( + p_rcv->p_log, + p_rcv->p_subn, + &p_madw->mad_addr, + &inform_info_rec.inform_record.subscriber_gid ); + if ( res != IB_SUCCESS ) + { + cl_plock_release( p_rcv->p_lock ); + + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "osm_infr_rcv_process_set_method: ERR 4308 " + "Subscribe Request from unknown LID: 0x%04X\n", + cl_ntoh16(p_madw->mad_addr.dest_lid) + ); + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_SA_MAD_STATUS_REQ_INVALID ); + goto Exit; + } + + /* HACK: enum is always 0 (currently) */ inform_info_rec.inform_record.subscriber_enum = 0; - /* update the subscriber GID according to mad address */ - inform_info_rec.inform_record.subscriber_gid = - osm_get_gid_by_mad_addr( p_rcv->p_log, p_rcv->p_subn, &p_madw->mad_addr ); + /* Subscribe values above 1 are undefined */ + if ( p_recvd_inform_info->subscribe > 1 ) + { + cl_plock_release( p_rcv->p_lock ); + + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "osm_infr_rcv_process_set_method: ERR 4308 " + "Invalid subscribe: %d\n", + p_recvd_inform_info->subscribe + ); + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_SA_MAD_STATUS_REQ_INVALID ); + goto Exit; + } /* * MODIFICATIONS DONE ON INCOMING REQUEST: * * QPN: - * internally we keep the QPN field of the InformInfo updated - * so we can compare simply the entire record - when finding such. - * The Spec only require to fill the QPN field when an un-subscribe - * Set(InformInfo) is done. See table 106 p 654 QPN field - * - * SUBSCRIBE: - * For similar reasons we change the subscribe to 0 on the - * inserted/searched data + * Internally we keep the QPN field of the InformInfo updated + * so we can simply compare it in the record - when finding such. */ - - subscribe = p_recvd_inform_info->subscribe; - if (subscribe) + if ( p_recvd_inform_info->subscribe ) { - inform_info_rec.inform_record.inform_info.subscribe = 0; ib_inform_info_set_qpn( &inform_info_rec.inform_record.inform_info, - inform_info_rec.report_addr.addr_type.gsi.remote_qp); + inform_info_rec.report_addr.addr_type.gsi.remote_qp ); osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "osm_infr_rcv_process_set_method: " - "Got Subscribe Request with QPN: 0x%06X\n", + "Subscribe Request with QPN: 0x%06X\n", cl_ntoh32(inform_info_rec.report_addr.addr_type.gsi.remote_qp) ); } @@ -414,73 +761,58 @@ osm_infr_rcv_process_set_method( { ib_inform_info_get_qpn_resp_time( p_recvd_inform_info->g_or_v.generic.qpn_resp_time_val, - &qpn, &resp_time_val); + &qpn, &resp_time_val ); osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "osm_infr_rcv_process_set_method: " - "Got UnSubscribe Request with QPN: 0x%06X\n", + "UnSubscribe Request with QPN: 0x%06X\n", cl_ntoh32(qpn) ); } /* If record exists with matching InformInfo */ - p_infr = osm_infr_get_by_rec( - p_rcv->p_subn, - p_rcv->p_log, - &inform_info_rec); + p_infr = osm_infr_get_by_rec( p_rcv->p_subn, p_rcv->p_log, &inform_info_rec ); - /* check to see if the request was for subscribe = 1 */ - if (subscribe) + /* check to see if the request was for subscribe */ + if ( p_recvd_inform_info->subscribe ) { - /* validate the request for a new or update InformInfo */ - if (__validate_infr(p_rcv, &inform_info_rec) != TRUE) + if ( __validate_infr( p_rcv, &inform_info_rec ) != TRUE ) { - cl_plock_release(p_rcv->p_lock); + cl_plock_release( p_rcv->p_lock ); osm_log( p_rcv->p_log, OSM_LOG_ERROR, "osm_infr_rcv_process_set_method: ERR 4305: " "Failed to validate a new inform object\n"); - /* o13-13.1.1: we need to set the subscribe bit to 0 */ + /* o13-13.1.1: we need to set the subscribe bit to 0 */ p_recvd_inform_info->subscribe = 0; - osm_sa_send_error( - p_rcv->p_resp, - p_madw, - IB_SA_MAD_STATUS_REQ_INVALID); - + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_SA_MAD_STATUS_REQ_INVALID ); goto Exit; } /* ok - we can try and create a new entry */ - if(p_infr == NULL) + if (p_infr == NULL) { /* Create the instance of the osm_infr_t object */ - p_infr = osm_infr_new(&inform_info_rec); - if(p_infr == NULL) + p_infr = osm_infr_new( &inform_info_rec ); + if (p_infr == NULL) { - cl_plock_release(p_rcv->p_lock); + cl_plock_release( p_rcv->p_lock ); osm_log( p_rcv->p_log, OSM_LOG_ERROR, "osm_infr_rcv_process_set_method: ERR 4306: " "Failed to create a new inform object\n"); - /* o13-13.1.1: we need to set the subscribe bit to 0 */ + /* o13-13.1.1: we need to set the subscribe bit to 0 */ p_recvd_inform_info->subscribe = 0; - osm_sa_send_error( - p_rcv->p_resp, - p_madw, - IB_SA_MAD_STATUS_NO_RESOURCES); - + osm_sa_send_error( p_rcv->p_resp, p_madw, + IB_SA_MAD_STATUS_NO_RESOURCES ); goto Exit; } /* Add this new osm_infr_t object to subnet object */ - osm_infr_insert_to_db( - p_rcv->p_subn, - p_rcv->p_log, - p_infr); - + osm_infr_insert_to_db( p_rcv->p_subn, p_rcv->p_log, p_infr ); } else { @@ -490,72 +822,101 @@ osm_infr_rcv_process_set_method( } else { - /* We got an Un-Subscribe request */ - if(p_infr == NULL) + /* We got an UnSubscribe request */ + if (p_infr == NULL) { - cl_plock_release(p_rcv->p_lock); + cl_plock_release( p_rcv->p_lock ); /* No Such Item - So Error */ osm_log( p_rcv->p_log, OSM_LOG_ERROR, "osm_infr_rcv_process_set_method: ERR 4307: " - "Failed to UnSubscribe to non exiting inform object\n"); + "Failed to UnSubscribe to non existing inform object\n"); - /* o13-13.1.1: we need to set the subscribe bit to 0 */ + /* o13-13.1.1: we need to set the subscribe bit to 0 */ p_recvd_inform_info->subscribe = 0; - osm_sa_send_error( - p_rcv->p_resp, - p_madw, - IB_SA_MAD_STATUS_REQ_INVALID); + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_SA_MAD_STATUS_REQ_INVALID ); goto Exit; } else { /* Delete this object from the subnet list of informs */ - osm_infr_remove_from_db( - p_rcv->p_subn, - p_rcv->p_log, - p_infr); + osm_infr_remove_from_db( p_rcv->p_subn, p_rcv->p_log, p_infr ); } } - cl_plock_release(p_rcv->p_lock); + cl_plock_release( p_rcv->p_lock ); /* send the success response */ - __osm_infr_rcv_respond(p_rcv, p_madw); + __osm_infr_rcv_respond( p_rcv, p_madw ); Exit: OSM_LOG_EXIT( p_rcv->p_log ); - return; } +/********************************************************************* +**********************************************************************/ void osm_infr_rcv_process( IN osm_infr_rcv_t* const p_rcv, IN const osm_madw_t* const p_madw ) { ib_sa_mad_t *p_sa_mad; - ib_net16_t sa_status = IB_SA_MAD_STATUS_REQ_INVALID; OSM_LOG_ENTER( p_rcv->p_log, osm_infr_rcv_process ); CL_ASSERT( p_madw ); + p_sa_mad = osm_madw_get_sa_mad_ptr( p_madw ); - switch (p_sa_mad->method) + CL_ASSERT( p_sa_mad->attr_id == IB_MAD_ATTR_INFORM_INFO ); + + if (p_sa_mad->method != IB_MAD_METHOD_SET) { - case IB_MAD_METHOD_SET: - osm_infr_rcv_process_set_method(p_rcv, p_madw); - break; - default: osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "osm_infr_rcv_process: " - "Bad Method (%s)\n", ib_get_sa_method_str( p_sa_mad->method )); - osm_sa_send_error( p_rcv->p_resp, p_madw, sa_status); - break; + "Unsupported Method (%s)\n", + ib_get_sa_method_str( p_sa_mad->method ) ); + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_MAD_STATUS_UNSUP_METHOD_ATTR ); + goto Exit; } - /* Exit: */ + osm_infr_rcv_process_set_method( p_rcv, p_madw ); + + Exit: + OSM_LOG_EXIT( p_rcv->p_log ); +} + +/********************************************************************* +**********************************************************************/ +void +osm_infir_rcv_process( + IN osm_infr_rcv_t* const p_rcv, + IN const osm_madw_t* const p_madw ) +{ + ib_sa_mad_t *p_sa_mad; + + OSM_LOG_ENTER( p_rcv->p_log, osm_infr_rcv_process ); + + CL_ASSERT( p_madw ); + + p_sa_mad = osm_madw_get_sa_mad_ptr( p_madw ); + + CL_ASSERT( p_sa_mad->attr_id == IB_MAD_ATTR_INFORM_INFO_RECORD ); + + if ( (p_sa_mad->method != IB_MAD_METHOD_GET) && + (p_sa_mad->method != IB_MAD_METHOD_GETTABLE) ) + { + osm_log( p_rcv->p_log, OSM_LOG_DEBUG, + "osm_infir_rcv_process: " + "Unsupported Method (%s)\n", + ib_get_sa_method_str( p_sa_mad->method ) ); + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_MAD_STATUS_UNSUP_METHOD_ATTR ); + goto Exit; + } + + osm_infr_rcv_process_get_method( p_rcv, p_madw ); + + Exit: OSM_LOG_EXIT( p_rcv->p_log ); - return; } diff --git a/trunk/ulp/opensm/user/opensm/osm_sa_informinfo_ctrl.c b/trunk/ulp/opensm/user/opensm/osm_sa_informinfo_ctrl.c index 0178559a..94760b6e 100644 --- a/trunk/ulp/opensm/user/opensm/osm_sa_informinfo_ctrl.c +++ b/trunk/ulp/opensm/user/opensm/osm_sa_informinfo_ctrl.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -44,21 +44,17 @@ * $Revision: 1.4 $ */ -/* - Next available error code: 0x203 -*/ - #if HAVE_CONFIG_H # include #endif /* HAVE_CONFIG_H */ -#include +#include #include #include /********************************************************************** **********************************************************************/ -void +static void __osm_infr_rcv_ctrl_disp_callback( IN void *context, IN void *p_data ) @@ -68,14 +64,27 @@ __osm_infr_rcv_ctrl_disp_callback( (osm_madw_t*)p_data ); } +/********************************************************************** + **********************************************************************/ +static void +__osm_infir_rcv_ctrl_disp_callback( + IN void *context, + IN void *p_data ) +{ + /* ignore return status when invoked via the dispatcher */ + osm_infir_rcv_process( ((osm_infr_rcv_ctrl_t*)context)->p_rcv, + (osm_madw_t*)p_data ); +} + /********************************************************************** **********************************************************************/ void osm_infr_rcv_ctrl_construct( IN osm_infr_rcv_ctrl_t* const p_ctrl ) { - cl_memclr( p_ctrl, sizeof(*p_ctrl) ); + memset( p_ctrl, 0, sizeof(*p_ctrl) ); p_ctrl->h_disp = CL_DISP_INVALID_HANDLE; + p_ctrl->h_disp2 = CL_DISP_INVALID_HANDLE; } /********************************************************************** @@ -85,6 +94,7 @@ osm_infr_rcv_ctrl_destroy( IN osm_infr_rcv_ctrl_t* const p_ctrl ) { CL_ASSERT( p_ctrl ); + cl_disp_unregister( p_ctrl->h_disp2 ); cl_disp_unregister( p_ctrl->h_disp ); } @@ -121,6 +131,22 @@ osm_infr_rcv_ctrl_init( goto Exit; } + p_ctrl->h_disp2 = cl_disp_register( + p_disp, + OSM_MSG_MAD_INFORM_INFO_RECORD, + __osm_infir_rcv_ctrl_disp_callback, + p_ctrl ); + + if( p_ctrl->h_disp2 == CL_DISP_INVALID_HANDLE ) + { + osm_log( p_log, OSM_LOG_ERROR, + "osm_infr_rcv_ctrl_init: ERR 1702: " + "Dispatcher registration failed\n" ); + cl_disp_unregister( p_ctrl->h_disp ); + status = IB_INSUFFICIENT_RESOURCES; + goto Exit; + } + Exit: OSM_LOG_EXIT( p_log ); return( status ); diff --git a/trunk/ulp/opensm/user/opensm/osm_sa_lft_record.c b/trunk/ulp/opensm/user/opensm/osm_sa_lft_record.c index 933eea73..8034febe 100644 --- a/trunk/ulp/opensm/user/opensm/osm_sa_lft_record.c +++ b/trunk/ulp/opensm/user/opensm/osm_sa_lft_record.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -44,14 +44,11 @@ * $Revision: 1.5 $ */ -/* - Next available error code: 0x403 -*/ - #if HAVE_CONFIG_H # include #endif /* HAVE_CONFIG_H */ +#include #include #include #include @@ -62,13 +59,12 @@ #include #define OSM_LFTR_RCV_POOL_MIN_SIZE 32 -#define OSM_LFTR_RCV_POOL_GROW_SIZE 32 +#define OSM_LFTR_RCV_POOL_GROW_SIZE 32 typedef struct _osm_lftr_item { cl_pool_item_t pool_item; ib_lft_record_t rec; - } osm_lftr_item_t; typedef struct _osm_lftr_search_ctxt @@ -86,7 +82,7 @@ void osm_lftr_rcv_construct( IN osm_lftr_rcv_t* const p_rcv ) { - cl_memclr( p_rcv, sizeof(*p_rcv) ); + memset( p_rcv, 0, sizeof(*p_rcv) ); cl_qlock_pool_construct( &p_rcv->pool ); } @@ -165,13 +161,13 @@ __osm_lftr_rcv_new_lftr( osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "__osm_lftr_rcv_new_lftr: " "New LinearForwardingTable: sw 0x%016" PRIx64 - "\n\t\t\t\tblock 0x%02X lid 0x%02X.\n", + "\n\t\t\t\tblock 0x%02X lid 0x%02X\n", cl_ntoh64( osm_node_get_node_guid( p_sw->p_node ) ), cl_ntoh16( block ), cl_ntoh16( lid ) ); } - cl_memclr( &p_rec_item->rec, sizeof(ib_lft_record_t) ); + memset( &p_rec_item->rec, 0, sizeof(ib_lft_record_t) ); p_rec_item->rec.lid = lid; p_rec_item->rec.block_num = block; @@ -188,39 +184,36 @@ __osm_lftr_rcv_new_lftr( /********************************************************************** **********************************************************************/ -static -osm_port_t* +static osm_port_t* __osm_lftr_get_port_by_guid( IN osm_lftr_rcv_t* const p_rcv, - IN uint64_t port_guid) + IN uint64_t port_guid ) { + osm_port_t* p_port; - osm_port_t* p_port; CL_PLOCK_ACQUIRE(p_rcv->p_lock); p_port = (osm_port_t *)cl_qmap_get(&p_rcv->p_subn->port_guid_tbl, port_guid); - - if(p_port == (osm_port_t *)cl_qmap_end(&p_rcv->p_subn->port_guid_tbl)) + if (p_port == (osm_port_t *)cl_qmap_end(&p_rcv->p_subn->port_guid_tbl)) { osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "__osm_lftr_get_port_by_guid ERR 4404: " - "Invalid port_guid 0x%016" PRIx64 "\n", - port_guid); - CL_PLOCK_RELEASE(p_rcv->p_lock); - return NULL; + "Invalid port GUID 0x%016" PRIx64 "\n", + port_guid ); + p_port = NULL; } + CL_PLOCK_RELEASE(p_rcv->p_lock); return p_port; } /********************************************************************** **********************************************************************/ -static -void +static void __osm_lftr_rcv_by_comp_mask( IN cl_map_item_t* const p_map_item, - IN void* context ) + IN void* context ) { const osm_lftr_search_ctxt_t* const p_ctxt = (osm_lftr_search_ctxt_t *)context; @@ -232,12 +225,11 @@ __osm_lftr_rcv_by_comp_mask( osm_port_t* p_port; uint16_t min_lid_ho, max_lid_ho; uint16_t min_block, max_block, block; - uint16_t sw_max_lid_ho, lids_per_block; const osm_physp_t* p_physp; /* In switches, the port guid is the node guid. */ p_port = - __osm_lftr_get_port_by_guid( p_rcv, p_sw->p_node->node_info.port_guid); + __osm_lftr_get_port_by_guid( p_rcv, p_sw->p_node->node_info.port_guid ); if (! p_port) { osm_log( p_rcv->p_log, OSM_LOG_ERROR, @@ -249,9 +241,6 @@ __osm_lftr_rcv_by_comp_mask( return; } - /* get the port 0 of the switch */ - osm_port_get_lid_range_ho( p_port, &min_lid_ho, &max_lid_ho ); - /* check that the requester physp and the current physp are under the same partition. */ p_physp = osm_port_get_default_phys_ptr( p_port ); @@ -268,6 +257,9 @@ __osm_lftr_rcv_by_comp_mask( if (! osm_physp_share_pkey( p_rcv->p_log, p_req_physp, p_physp )) return; + /* get the port 0 of the switch */ + osm_port_get_lid_range_ho( p_port, &min_lid_ho, &max_lid_ho ); + /* compare the lids - if required */ if( comp_mask & IB_LFTR_COMPMASK_LID ) { @@ -277,8 +269,8 @@ __osm_lftr_rcv_by_comp_mask( cl_ntoh16( p_rcvd_rec->lid ), min_lid_ho, max_lid_ho ); /* ok we are ready for range check */ - if ((min_lid_ho > cl_ntoh16(p_rcvd_rec->lid)) || - (max_lid_ho < cl_ntoh16(p_rcvd_rec->lid))) + if (min_lid_ho > cl_ntoh16(p_rcvd_rec->lid) || + max_lid_ho < cl_ntoh16(p_rcvd_rec->lid)) return; } @@ -289,11 +281,9 @@ __osm_lftr_rcv_by_comp_mask( } else { - /* use as many blocks as possible */ + /* use as many blocks as "in use" */ min_block = 0; - sw_max_lid_ho = osm_switch_get_max_lid_ho( p_sw ); - lids_per_block = osm_fwd_tbl_get_lids_per_block( osm_switch_get_fwd_tbl_ptr( p_sw ) ); - max_block = (max_lid_ho + lids_per_block - 1)/lids_per_block; + max_block = osm_switch_get_max_block_id_in_use(p_sw); } /* so we can add these blocks one by one ... */ @@ -307,8 +297,8 @@ __osm_lftr_rcv_by_comp_mask( **********************************************************************/ void osm_lftr_rcv_process( - IN osm_lftr_rcv_t* const p_rcv, - IN const osm_madw_t* const p_madw ) + IN osm_lftr_rcv_t* const p_rcv, + IN const osm_madw_t* const p_madw ) { const ib_sa_mad_t* p_rcvd_mad; const ib_lft_record_t* p_rcvd_rec; @@ -323,7 +313,7 @@ osm_lftr_rcv_process( uint32_t i; osm_lftr_search_ctxt_t context; osm_lftr_item_t* p_rec_item; - ib_api_status_t status; + ib_api_status_t status = IB_SUCCESS; osm_physp_t* p_req_physp; CL_ASSERT( p_rcv ); @@ -337,6 +327,17 @@ osm_lftr_rcv_process( CL_ASSERT( p_rcvd_mad->attr_id == IB_MAD_ATTR_LFT_RECORD ); + /* we only support SubnAdmGet and SubnAdmGetTable methods */ + if ( (p_rcvd_mad->method != IB_MAD_METHOD_GET) && + (p_rcvd_mad->method != IB_MAD_METHOD_GETTABLE) ) { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "osm_lftr_rcv_process: ERR 4408: " + "Unsupported Method (%s)\n", + ib_get_sa_method_str( p_rcvd_mad->method ) ); + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_MAD_STATUS_UNSUP_METHOD_ATTR ); + goto Exit; + } + /* update the requester physical port. */ p_req_physp = osm_get_physp_by_mad_addr(p_rcv->p_log, p_rcv->p_subn, @@ -349,16 +350,6 @@ osm_lftr_rcv_process( goto Exit; } - if ( (p_rcvd_mad->method != IB_MAD_METHOD_GET) && - (p_rcvd_mad->method != IB_MAD_METHOD_GETTABLE) ) { - osm_log( p_rcv->p_log, OSM_LOG_ERROR, - "osm_lftr_rcv_process: ERR 4408: " - "Unsupported Method (%s)\n", - ib_get_sa_method_str( p_rcvd_mad->method ) ); - osm_sa_send_error( p_rcv->p_resp, p_madw, IB_SA_MAD_STATUS_REQ_INVALID); - goto Exit; - } - cl_qlist_init( &rec_list ); context.p_rcvd_rec = p_rcvd_rec; @@ -382,24 +373,32 @@ osm_lftr_rcv_process( * C15-0.1.30: * If we do a SubnAdmGet and got more than one record it is an error ! */ - if ( (p_rcvd_mad->method == IB_MAD_METHOD_GET) && - (num_rec > 1)) { - osm_log( p_rcv->p_log, OSM_LOG_ERROR, - "osm_lftr_rcv_process: ERR 4409: " - "Got more than one record for SubnAdmGet (%u)\n", - num_rec ); - osm_sa_send_error( p_rcv->p_resp, p_madw, - IB_SA_MAD_STATUS_TOO_MANY_RECORDS); - - /* need to set the mem free ... */ - p_rec_item = (osm_lftr_item_t*)cl_qlist_remove_head( &rec_list ); - while( p_rec_item != (osm_lftr_item_t*)cl_qlist_end( &rec_list ) ) + if (p_rcvd_mad->method == IB_MAD_METHOD_GET) + { + if (num_rec == 0) { - cl_qlock_pool_put( &p_rcv->pool, &p_rec_item->pool_item ); - p_rec_item = (osm_lftr_item_t*)cl_qlist_remove_head( &rec_list ); + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_SA_MAD_STATUS_NO_RECORDS ); + goto Exit; } + if (num_rec > 1) + { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "osm_lftr_rcv_process: ERR 4409: " + "Got more than one record for SubnAdmGet (%u)\n", + num_rec ); + osm_sa_send_error( p_rcv->p_resp, p_madw, + IB_SA_MAD_STATUS_TOO_MANY_RECORDS); + + /* need to set the mem free ... */ + p_rec_item = (osm_lftr_item_t*)cl_qlist_remove_head( &rec_list ); + while( p_rec_item != (osm_lftr_item_t*)cl_qlist_end( &rec_list ) ) + { + cl_qlock_pool_put( &p_rcv->pool, &p_rec_item->pool_item ); + p_rec_item = (osm_lftr_item_t*)cl_qlist_remove_head( &rec_list ); + } - goto Exit; + goto Exit; + } } pre_trim_num_rec = num_rec; @@ -462,9 +461,9 @@ osm_lftr_rcv_process( Then copy all records from the list into the response payload. */ - cl_memcpy( p_resp_sa_mad, p_rcvd_mad, IB_SA_MAD_HDR_SIZE ); - p_resp_sa_mad->method = (uint8_t)(p_resp_sa_mad->method | 0x80); - /* C15-0.1.5 - always return SM_Key = 0 (table 151 p 782) */ + memcpy( p_resp_sa_mad, p_rcvd_mad, IB_SA_MAD_HDR_SIZE ); + p_resp_sa_mad->method |= IB_MAD_METHOD_RESP_MASK; + /* C15-0.1.5 - always return SM_Key = 0 (table 185 p 884) */ p_resp_sa_mad->sm_key = 0; /* Fill in the offset (paylen will be done by the rmpp SAR) */ p_resp_sa_mad->attr_offset = @@ -501,12 +500,11 @@ osm_lftr_rcv_process( CL_ASSERT( cl_is_qlist_empty( &rec_list ) ); status = osm_vendor_send( p_resp_madw->h_bind, p_resp_madw, FALSE ); - - if(status != IB_SUCCESS) + if (status != IB_SUCCESS) { osm_log(p_rcv->p_log, OSM_LOG_ERROR, "osm_lftr_rcv_process: ERR 4411: " - "osm_vendor_send. status = %s\n", + "osm_vendor_send status = %s\n", ib_get_err_str(status)); goto Exit; } diff --git a/trunk/ulp/opensm/user/opensm/osm_sa_lft_record_ctrl.c b/trunk/ulp/opensm/user/opensm/osm_sa_lft_record_ctrl.c index dbeee1d4..c39efe2d 100644 --- a/trunk/ulp/opensm/user/opensm/osm_sa_lft_record_ctrl.c +++ b/trunk/ulp/opensm/user/opensm/osm_sa_lft_record_ctrl.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -44,15 +44,11 @@ * $Revision: 1.4 $ */ -/* - Next available error code: 0x203 -*/ - #if HAVE_CONFIG_H # include #endif /* HAVE_CONFIG_H */ -#include +#include #include #include @@ -74,7 +70,7 @@ void osm_lftr_rcv_ctrl_construct( IN osm_lftr_rcv_ctrl_t* const p_ctrl ) { - cl_memclr( p_ctrl, sizeof(*p_ctrl) ); + memset( p_ctrl, 0, sizeof(*p_ctrl) ); p_ctrl->h_disp = CL_DISP_INVALID_HANDLE; } @@ -125,3 +121,4 @@ osm_lftr_rcv_ctrl_init( OSM_LOG_EXIT( p_log ); return( status ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_sa_link_record.c b/trunk/ulp/opensm/user/opensm/osm_sa_link_record.c index f7b1a308..8e242b08 100644 --- a/trunk/ulp/opensm/user/opensm/osm_sa_link_record.c +++ b/trunk/ulp/opensm/user/opensm/osm_sa_link_record.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Implementation of osm_lr_rcv_t. @@ -44,16 +45,12 @@ * $Revision: 1.8 $ */ -/* - Next available error code: 0x403 -*/ - #if HAVE_CONFIG_H # include #endif /* HAVE_CONFIG_H */ +#include #include -#include #include #include #include @@ -70,7 +67,6 @@ typedef struct _osm_lr_item { cl_pool_item_t pool_item; ib_link_record_t link_rec; - } osm_lr_item_t; /********************************************************************** @@ -79,7 +75,7 @@ void osm_lr_rcv_construct( IN osm_lr_rcv_t* const p_rcv ) { - cl_memclr( p_rcv, sizeof(*p_rcv) ); + memset( p_rcv, 0, sizeof(*p_rcv) ); cl_qlock_pool_construct( &p_rcv->lr_pool ); } @@ -98,14 +94,14 @@ osm_lr_rcv_destroy( **********************************************************************/ ib_api_status_t osm_lr_rcv_init( - IN osm_lr_rcv_t* const p_rcv, - IN osm_sa_resp_t* const p_resp, + IN osm_lr_rcv_t* const p_rcv, + IN osm_sa_resp_t* const p_resp, IN osm_mad_pool_t* const p_mad_pool, - IN osm_subn_t* const p_subn, - IN osm_log_t* const p_log, - IN cl_plock_t* const p_lock ) + IN osm_subn_t* const p_subn, + IN osm_log_t* const p_log, + IN cl_plock_t* const p_lock ) { - ib_api_status_t status = IB_SUCCESS; + ib_api_status_t status = IB_SUCCESS; OSM_LOG_ENTER( p_log, osm_lr_rcv_init ); @@ -130,12 +126,11 @@ osm_lr_rcv_init( /********************************************************************** **********************************************************************/ - static void __osm_lr_rcv_build_physp_link( IN osm_lr_rcv_t* const p_rcv, - IN const ib_net16_t from_lid, - IN const ib_net16_t to_lid, + IN const ib_net16_t from_lid, + IN const ib_net16_t to_lid, IN const uint8_t from_port, IN const uint8_t to_port, IN cl_qlist_t* p_list ) @@ -148,13 +143,13 @@ __osm_lr_rcv_build_physp_link( osm_log( p_rcv->p_log, OSM_LOG_ERROR, "__osm_lr_rcv_build_physp_link: ERR 1801: " "Unable to acquire link record\n" - "\t\t\t\tFrom port 0x%\n" - "\t\t\t\tTo port 0x%\n" - "\t\t\t\tFrom lid 0x%\n" - "\t\t\t\tTo lid 0x%\n", + "\t\t\t\tFrom port 0x%u\n" + "\t\t\t\tTo port 0x%u\n" + "\t\t\t\tFrom lid 0x%X\n" + "\t\t\t\tTo lid 0x%X\n", from_port, to_port, cl_ntoh16(from_lid), - cl_ntoh16(to_lid)); + cl_ntoh16(to_lid) ); return; } @@ -169,13 +164,10 @@ __osm_lr_rcv_build_physp_link( /********************************************************************** **********************************************************************/ static void -__get_lid_range( - IN const osm_physp_t* p_physp, - OUT uint16_t *p_base_lid, - OUT uint16_t *p_max_lid) +__get_base_lid( + IN const osm_physp_t* p_physp, + OUT uint16_t * p_base_lid ) { - uint8_t lmc; - if(p_physp->p_node->node_info.node_type == IB_NODE_TYPE_SWITCH) { *p_base_lid = @@ -183,14 +175,11 @@ __get_lid_range( osm_physp_get_base_lid( osm_node_get_physp_ptr(p_physp->p_node, 0)) ); - *p_max_lid = *p_base_lid; } else { *p_base_lid = cl_ntoh16(osm_physp_get_base_lid(p_physp)); - lmc = osm_physp_get_lmc( p_physp ); - *p_max_lid = (uint16_t)(*p_base_lid + (1<p_log, __osm_lr_rcv_get_physp_link ); @@ -245,9 +231,7 @@ __osm_lr_rcv_get_physp_link( if( !osm_physp_is_valid( p_dest_physp ) ) goto Exit; - } - } else { @@ -283,14 +267,14 @@ __osm_lr_rcv_get_physp_link( { osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "__osm_lr_rcv_get_physp_link: " - "Source and Requestor PhysPorts do not share PKey\n"); + "Source and Requester PhysPorts do not share PKey\n"); goto Exit; } if (! osm_physp_share_pkey(p_rcv->p_log, p_req_physp, p_dest_physp) ) { osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "__osm_lr_rcv_get_physp_link: " - "Requestor and Dest PhysPorts do not share PKey\n"); + "Requester and Dest PhysPorts do not share PKey\n"); goto Exit; } @@ -309,7 +293,7 @@ __osm_lr_rcv_get_physp_link( { osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "__osm_lr_rcv_get_physp_link: " - "Acquiring link record.\n" + "Acquiring link record\n" "\t\t\t\tsrc port 0x%" PRIx64 " (port 0x%X)" ", dest port 0x%" PRIx64 " (port 0x%X)\n", cl_ntoh64( osm_physp_get_port_guid( p_src_physp ) ), @@ -318,32 +302,12 @@ __osm_lr_rcv_get_physp_link( dest_port_num ); } - if( comp_mask & IB_LR_COMPMASK_FROM_LID ) - { - from_max_lid_ho = from_base_lid_ho = - cl_ntoh16(p_lr->from_lid); - }else - { - __get_lid_range(p_src_physp, &from_base_lid_ho, - &from_max_lid_ho); - } - - if( comp_mask & IB_LR_COMPMASK_TO_LID ) - { - to_max_lid_ho = to_base_lid_ho = - cl_ntoh16(p_lr->to_lid); - }else - { - __get_lid_range(p_dest_physp, &to_base_lid_ho, - &to_max_lid_ho); - } + __get_base_lid(p_src_physp, &from_base_lid_ho); + __get_base_lid(p_dest_physp, &to_base_lid_ho); - for(i=from_base_lid_ho; i<= from_max_lid_ho; i++) - { - for(j=to_base_lid_ho; j<= to_max_lid_ho; j++) - __osm_lr_rcv_build_physp_link(p_rcv, cl_ntoh16(i), cl_ntoh16(j), - src_port_num, dest_port_num, p_list); - } + __osm_lr_rcv_build_physp_link(p_rcv, cl_ntoh16(from_base_lid_ho), + cl_ntoh16(to_base_lid_ho), + src_port_num, dest_port_num, p_list); Exit: OSM_LOG_EXIT( p_rcv->p_log ); @@ -353,21 +317,21 @@ __osm_lr_rcv_get_physp_link( **********************************************************************/ static void __osm_lr_rcv_get_port_links( - IN osm_lr_rcv_t* const p_rcv, + IN osm_lr_rcv_t* const p_rcv, IN const ib_link_record_t* const p_lr, - IN const osm_port_t* p_src_port, - IN const osm_port_t* p_dest_port, + IN const osm_port_t* p_src_port, + IN const osm_port_t* p_dest_port, IN const ib_net64_t comp_mask, - IN cl_qlist_t* const p_list, - IN const osm_physp_t* p_req_physp ) + IN cl_qlist_t* const p_list, + IN const osm_physp_t* p_req_physp ) { - const osm_physp_t* p_src_physp; - const osm_physp_t* p_dest_physp; - const cl_qmap_t* p_port_tbl; - uint8_t port_num; - uint8_t num_ports; - uint8_t dest_num_ports; - uint8_t dest_port_num; + const osm_physp_t* p_src_physp; + const osm_physp_t* p_dest_physp; + const cl_qmap_t* p_port_tbl; + uint8_t port_num; + uint8_t num_ports; + uint8_t dest_num_ports; + uint8_t dest_port_num; OSM_LOG_ENTER( p_rcv->p_log, __osm_lr_rcv_get_port_links ); @@ -492,16 +456,16 @@ __osm_lr_rcv_get_port_links( } /********************************************************************** - Returns the SA status to return to the client. -**********************************************************************/ + Returns the SA status to return to the client. + **********************************************************************/ static ib_net16_t __osm_lr_rcv_get_end_points( IN osm_lr_rcv_t* const p_rcv, IN const osm_madw_t* const p_madw, - OUT const osm_port_t** const pp_src_port, - OUT const osm_port_t** const pp_dest_port ) + OUT const osm_port_t** const pp_src_port, + OUT const osm_port_t** const pp_dest_port ) { - const ib_link_record_t* p_lr; + const ib_link_record_t* p_lr; const ib_sa_mad_t* p_sa_mad; ib_net64_t comp_mask; ib_api_status_t status; @@ -522,12 +486,11 @@ __osm_lr_rcv_get_end_points( if( p_sa_mad->comp_mask & IB_LR_COMPMASK_FROM_LID ) { - status = cl_ptr_vector_at( &p_rcv->p_subn->port_lid_tbl, - cl_ntoh16(p_lr->from_lid), - (void**)pp_src_port ); + status = osm_get_port_by_base_lid( p_rcv->p_subn, + p_lr->from_lid, + pp_src_port ); - if( ( (status != CL_SUCCESS) || (*pp_src_port == NULL) ) && - (p_sa_mad->method == IB_MAD_METHOD_GET) ) + if( (status != IB_SUCCESS) || (*pp_src_port == NULL) ) { /* This 'error' is the client's fault (bad lid) so @@ -546,12 +509,11 @@ __osm_lr_rcv_get_end_points( if( p_sa_mad->comp_mask & IB_LR_COMPMASK_TO_LID ) { - status = cl_ptr_vector_at( &p_rcv->p_subn->port_lid_tbl, - cl_ntoh16(p_lr->to_lid), - (void**)pp_dest_port ); + status = osm_get_port_by_base_lid( p_rcv->p_subn, + p_lr->to_lid, + pp_dest_port ); - if( ( (status != CL_SUCCESS) || (*pp_dest_port == NULL) ) && - (p_sa_mad->method == IB_MAD_METHOD_GET) ) + if( (status != IB_SUCCESS) || (*pp_dest_port == NULL) ) { /* This 'error' is the client's fault (bad lid) so @@ -577,19 +539,19 @@ __osm_lr_rcv_get_end_points( **********************************************************************/ static void __osm_lr_rcv_respond( - IN osm_lr_rcv_t* const p_rcv, - IN const osm_madw_t* const p_madw, - IN cl_qlist_t* const p_list ) + IN osm_lr_rcv_t* const p_rcv, + IN const osm_madw_t* const p_madw, + IN cl_qlist_t* const p_list ) { - osm_madw_t* p_resp_madw; - const ib_sa_mad_t* p_sa_mad; + osm_madw_t* p_resp_madw; + const ib_sa_mad_t* p_sa_mad; ib_sa_mad_t* p_resp_sa_mad; size_t num_rec, num_copied; #ifndef VENDOR_RMPP_SUPPORT size_t trim_num_rec; #endif - ib_link_record_t* p_resp_lr; - ib_api_status_t status; + ib_link_record_t* p_resp_lr; + ib_api_status_t status; osm_lr_item_t* p_lr_item; const ib_sa_mad_t* p_rcvd_mad = osm_madw_get_sa_mad_ptr( p_madw ); @@ -603,11 +565,11 @@ __osm_lr_rcv_respond( if ( (p_rcvd_mad->method == IB_MAD_METHOD_GET) && (num_rec > 1)) { osm_log( p_rcv->p_log, OSM_LOG_ERROR, - "__osm_lr_rcv_respond: " - "Got more than one record for SubnAdmGet (%u)\n", + "__osm_lr_rcv_respond: ERR 1806: " + "Got more than one record for SubnAdmGet (%zu)\n", num_rec ); osm_sa_send_error( p_rcv->p_resp, p_madw, - IB_SA_MAD_STATUS_TOO_MANY_RECORDS); + IB_SA_MAD_STATUS_TOO_MANY_RECORDS ); /* need to set the mem free ... */ p_lr_item = (osm_lr_item_t*)cl_qlist_remove_head( p_list ); @@ -636,7 +598,7 @@ __osm_lr_rcv_respond( { osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "__osm_lr_rcv_respond: " - "Generating response with %u records", num_rec ); + "Generating response with %zu records", num_rec ); } /* @@ -666,11 +628,11 @@ __osm_lr_rcv_respond( p_resp_sa_mad = osm_madw_get_sa_mad_ptr( p_resp_madw ); /* Copy the header from the request to response */ - cl_memcpy( p_resp_sa_mad, p_sa_mad, IB_SA_MAD_HDR_SIZE ); + memcpy( p_resp_sa_mad, p_sa_mad, IB_SA_MAD_HDR_SIZE ); p_resp_sa_mad->method |= IB_MAD_METHOD_RESP_MASK; p_resp_sa_mad->attr_offset = ib_get_attr_offset( sizeof(ib_link_record_t) ); - /* C15-0.1.5 - always return SM_Key = 0 (table 151 p 782) */ + /* C15-0.1.5 - always return SM_Key = 0 (table table 185 p 884) */ p_resp_sa_mad->sm_key = 0; #ifndef VENDOR_RMPP_SUPPORT @@ -692,7 +654,7 @@ __osm_lr_rcv_respond( if ((p_rcvd_mad->method == IB_MAD_METHOD_GET) && (num_rec == 0)) { p_resp_sa_mad->status = IB_SA_MAD_STATUS_NO_RECORDS; - cl_memclr( p_resp_lr, sizeof(*p_resp_lr) ); + memset( p_resp_lr, 0, sizeof(*p_resp_lr) ); } else { @@ -717,8 +679,7 @@ __osm_lr_rcv_respond( } status = osm_vendor_send( p_resp_madw->h_bind, p_resp_madw, FALSE ); - - if( status != IB_SUCCESS ) + if (status != IB_SUCCESS) { osm_log( p_rcv->p_log, OSM_LOG_ERROR, "__osm_lr_rcv_respond: ERR 1803: " @@ -738,10 +699,10 @@ osm_lr_rcv_process( IN osm_lr_rcv_t* const p_rcv, IN const osm_madw_t* const p_madw ) { - const ib_link_record_t* p_lr; + const ib_link_record_t* p_lr; const ib_sa_mad_t* p_sa_mad; - const osm_port_t* p_src_port = NULL; - const osm_port_t* p_dest_port = NULL; + const osm_port_t* p_src_port; + const osm_port_t* p_dest_port; cl_qlist_t lr_list; ib_net16_t sa_status; osm_physp_t* p_req_physp; @@ -753,19 +714,19 @@ osm_lr_rcv_process( p_sa_mad = osm_madw_get_sa_mad_ptr( p_madw ); p_lr = (ib_link_record_t*)ib_sa_mad_get_payload_ptr( p_sa_mad ); - /* we only support SubnAdmGet and SubnAdmGetTable Methods */ + CL_ASSERT( p_sa_mad->attr_id == IB_MAD_ATTR_LINK_RECORD ); + + /* we only support SubnAdmGet and SubnAdmGetTable methods */ if ( (p_sa_mad->method != IB_MAD_METHOD_GET) && (p_sa_mad->method != IB_MAD_METHOD_GETTABLE)) { osm_log( p_rcv->p_log, OSM_LOG_ERROR, "osm_lr_rcv_process: ERR 1804: " "Unsupported Method (%s)\n", ib_get_sa_method_str( p_sa_mad->method ) ); - osm_sa_send_error( p_rcv->p_resp, p_madw, IB_SA_MAD_STATUS_REQ_INVALID); + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_MAD_STATUS_UNSUP_METHOD_ATTR ); goto Exit; } - CL_ASSERT( p_sa_mad->attr_id == IB_MAD_ATTR_LINK_RECORD ); - /* update the requester physical port. */ p_req_physp = osm_get_physp_by_mad_addr(p_rcv->p_log, p_rcv->p_subn, @@ -792,23 +753,18 @@ osm_lr_rcv_process( sa_status = __osm_lr_rcv_get_end_points( p_rcv, p_madw, &p_src_port, &p_dest_port ); - if( sa_status != IB_SA_MAD_STATUS_SUCCESS ) + if( sa_status == IB_SA_MAD_STATUS_SUCCESS ) { - cl_plock_release( p_rcv->p_lock ); - osm_sa_send_error( p_rcv->p_resp, p_madw, sa_status ); - goto Exit; + __osm_lr_rcv_get_port_links( p_rcv, p_lr, p_src_port, p_dest_port, + p_sa_mad->comp_mask, &lr_list, p_req_physp ); } - __osm_lr_rcv_get_port_links( p_rcv, p_lr, p_src_port, p_dest_port, - p_sa_mad->comp_mask, &lr_list, p_req_physp ); - cl_plock_release( p_rcv->p_lock ); if( (cl_qlist_count( &lr_list ) == 0) && (p_sa_mad->method == IB_MAD_METHOD_GET) ) { - osm_sa_send_error( p_rcv->p_resp, p_madw, - IB_SA_MAD_STATUS_NO_RECORDS ); + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_SA_MAD_STATUS_NO_RECORDS ); goto Exit; } @@ -818,3 +774,4 @@ osm_lr_rcv_process( OSM_LOG_EXIT( p_rcv->p_log ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_sa_link_record_ctrl.c b/trunk/ulp/opensm/user/opensm/osm_sa_link_record_ctrl.c index 05706a60..ee517abf 100644 --- a/trunk/ulp/opensm/user/opensm/osm_sa_link_record_ctrl.c +++ b/trunk/ulp/opensm/user/opensm/osm_sa_link_record_ctrl.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Implementation of osm_lr_rcv_ctrl_t. @@ -48,7 +49,7 @@ # include #endif /* HAVE_CONFIG_H */ -#include +#include #include #include @@ -70,7 +71,7 @@ void osm_lr_rcv_ctrl_construct( IN osm_lr_rcv_ctrl_t* const p_ctrl ) { - cl_memclr( p_ctrl, sizeof(*p_ctrl) ); + memset( p_ctrl, 0, sizeof(*p_ctrl) ); p_ctrl->h_disp = CL_DISP_INVALID_HANDLE; } @@ -113,7 +114,7 @@ osm_lr_rcv_ctrl_init( { osm_log( p_log, OSM_LOG_ERROR, "osm_lr_rcv_ctrl_init: ERR 1901: " - "Dispatcher registration failed.\n" ); + "Dispatcher registration failed\n" ); status = IB_INSUFFICIENT_RESOURCES; goto Exit; } @@ -124,3 +125,4 @@ osm_lr_rcv_ctrl_init( } + diff --git a/trunk/ulp/opensm/user/opensm/osm_sa_mad_ctrl.c b/trunk/ulp/opensm/user/opensm/osm_sa_mad_ctrl.c index 94eecfb9..55c10f8e 100644 --- a/trunk/ulp/opensm/user/opensm/osm_sa_mad_ctrl.c +++ b/trunk/ulp/opensm/user/opensm/osm_sa_mad_ctrl.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Implementation of osm_sa_mad_ctrl_t. @@ -47,7 +48,7 @@ # include #endif /* HAVE_CONFIG_H */ -#include +#include #include #include #include @@ -83,11 +84,11 @@ __osm_sa_mad_ctrl_disp_done_callback( osm_mad_pool_put( p_ctrl->p_mad_pool, p_madw ); OSM_LOG_EXIT( p_ctrl->p_log ); } - /************/ -/****f* opensm: SA/__osm_sa_mad_ctrl_process_get + +/****f* opensm: SA/__osm_sa_mad_ctrl_process * NAME - * __osm_sa_mad_ctrl_process_get + * __osm_sa_mad_ctrl_process * * DESCRIPTION * This function handles known methods for received MADs. @@ -129,17 +130,17 @@ __osm_sa_mad_ctrl_process( "__osm_sa_mad_ctrl_process: " /* "Responding BUSY status since the dispatcher is already"*/ "Dropping MAD since the dispatcher is already" - " overloaded with %u messages and queue time of:%u[msec]\n", - num_messages, last_dispatched_msg_queue_time_msec); + " overloaded with %u messages and queue time of:" + "%" PRIu64 "[msec]\n", + num_messages, last_dispatched_msg_queue_time_msec ); /* send a busy response */ - /* osm_sa_send_error( p_ctrl->p_resp, p_madw, IB_RESOURCE_BUSY); */ + /* osm_sa_send_error( p_ctrl->p_resp, p_madw, IB_RESOURCE_BUSY ); */ /* return the request to the pool */ osm_mad_pool_put( p_ctrl->p_mad_pool, p_madw ); goto Exit; - } p_sa_mad = osm_madw_get_sa_mad_ptr( p_madw ); @@ -206,6 +207,24 @@ __osm_sa_mad_ctrl_process( msg_id = OSM_MSG_MAD_GUIDINFO_RECORD; break; + case IB_MAD_ATTR_INFORM_INFO_RECORD: + msg_id = OSM_MSG_MAD_INFORM_INFO_RECORD; + break; + + case IB_MAD_ATTR_SWITCH_INFO_RECORD: + msg_id = OSM_MSG_MAD_SWITCH_INFO_RECORD; + break; + + case IB_MAD_ATTR_MFT_RECORD: + msg_id = OSM_MSG_MAD_MFT_RECORD; + break; + +#if defined (VENDOR_RMPP_SUPPORT) && defined (DUAL_SIDED_RMPP) + case IB_MAD_ATTR_MULTIPATH_RECORD: + msg_id = OSM_MSG_MAD_MULTIPATH_RECORD; + break; +#endif + default: osm_log( p_ctrl->p_log, OSM_LOG_ERROR, "__osm_sa_mad_ctrl_process: ERR 1A01: " @@ -247,7 +266,7 @@ __osm_sa_mad_ctrl_process( else { /* - There is a known MAD attribute type for which there is + There is an unknown MAD attribute type for which there is no recipient. Simply retire the MAD here. */ osm_mad_pool_put( p_ctrl->p_mad_pool, p_madw ); @@ -256,7 +275,6 @@ __osm_sa_mad_ctrl_process( Exit: OSM_LOG_EXIT( p_ctrl->p_log ); } - /* * PARAMETERS * @@ -333,7 +351,7 @@ __osm_sa_mad_ctrl_rcv_callback( osm_dump_sa_mad( p_ctrl->p_log, p_sa_mad, OSM_LOG_FRAMES ); /* - * C15-0.1.5 - Table 151: SA Header - p782 + * C15-0.1.5 - Table 185: SA Header - p884 * SM_key should be either 0 or match the current SM_Key * otherwise discard the MAD. */ @@ -367,6 +385,9 @@ __osm_sa_mad_ctrl_rcv_callback( case IB_MAD_METHOD_GET: case IB_MAD_METHOD_GETTABLE: +#if defined (VENDOR_RMPP_SUPPORT) && defined (DUAL_SIDED_RMPP) + case IB_MAD_METHOD_GETMULTI: +#endif case IB_MAD_METHOD_SET: case IB_MAD_METHOD_DELETE: __osm_sa_mad_ctrl_process( p_ctrl, p_madw ); @@ -375,8 +396,8 @@ __osm_sa_mad_ctrl_rcv_callback( default: osm_log( p_ctrl->p_log, OSM_LOG_ERROR, "__osm_sa_mad_ctrl_rcv_callback: ERR 1A05: " - "Not yet implemented Method=<0x%X> Attribute=<0x%X>\n", - p_sa_mad->method,p_sa_mad->attr_id); + "Unsupported method = 0x%X\n", + p_sa_mad->method ); osm_mad_pool_put( p_ctrl->p_mad_pool, p_madw ); goto Exit; } @@ -384,7 +405,6 @@ __osm_sa_mad_ctrl_rcv_callback( Exit: OSM_LOG_EXIT( p_ctrl->p_log ); } - /* * PARAMETERS * @@ -469,7 +489,6 @@ __osm_sa_mad_ctrl_send_err_callback( OSM_LOG_EXIT( p_ctrl->p_log ); } - /* * PARAMETERS * @@ -487,7 +506,7 @@ osm_sa_mad_ctrl_construct( IN osm_sa_mad_ctrl_t* const p_ctrl ) { CL_ASSERT( p_ctrl ); - cl_memclr( p_ctrl, sizeof(*p_ctrl) ); + memset( p_ctrl, 0, sizeof(*p_ctrl) ); p_ctrl->h_disp = CL_DISP_INVALID_HANDLE; } @@ -628,5 +647,5 @@ osm_sa_mad_ctrl_unbind( Exit: OSM_LOG_EXIT( p_ctrl->p_log ); return( status ); - } + diff --git a/trunk/ulp/opensm/user/opensm/osm_sa_mcmember_record.c b/trunk/ulp/opensm/user/opensm/osm_sa_mcmember_record.c index 7f9befef..e5875d12 100644 --- a/trunk/ulp/opensm/user/opensm/osm_sa_mcmember_record.c +++ b/trunk/ulp/opensm/user/opensm/osm_sa_mcmember_record.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -44,16 +44,13 @@ * $Revision: 1.15 $ */ -/* - Next available error code: 0x403 -*/ - #if HAVE_CONFIG_H # include #endif /* HAVE_CONFIG_H */ +#include +#include #include -#include #include #include #include @@ -76,9 +73,8 @@ typedef struct _osm_mcmr_item { - cl_pool_item_t pool_item; + cl_pool_item_t pool_item; ib_member_rec_t rec; - } osm_mcmr_item_t; typedef struct osm_sa_mcmr_search_ctxt { @@ -97,7 +93,7 @@ void osm_mcmr_rcv_construct( IN osm_mcmr_recv_t* const p_rcv ) { - cl_memclr( p_rcv, sizeof(*p_rcv) ); + memset( p_rcv, 0, sizeof(*p_rcv) ); cl_qlock_pool_construct( &p_rcv->pool ); } @@ -129,6 +125,7 @@ osm_mcmr_rcv_init( IN cl_plock_t* const p_lock ) { ib_api_status_t status = IB_SUCCESS; + OSM_LOG_ENTER( p_log, osm_mcmr_rcv_init ); osm_mcmr_rcv_construct( p_rcv ); @@ -151,8 +148,8 @@ osm_mcmr_rcv_init( { osm_log( p_rcv->p_log, OSM_LOG_ERROR, "osm_mcmr_rcv_init: ERR 1B02: " - "Error Init of qlock pool (%d)\n", - status ); + "qlock pool init failed (%d)\n", + status ); } OSM_LOG_EXIT( p_rcv->p_log ); return( status ); @@ -168,15 +165,14 @@ osm_mcmr_rcv_init( context - points to the osm_sa_mcmr_search_ctxt_t including the mgid looked for and the result p_mgrp **********************************************************************/ -static -void +static void __search_mgrp_by_mgid( IN cl_map_item_t* const p_map_item, IN void* context ) { osm_mgrp_t* p_mgrp = (osm_mgrp_t*)p_map_item; osm_sa_mcmr_search_ctxt_t *p_ctxt = (osm_sa_mcmr_search_ctxt_t *) context; - const ib_member_rec_t *p_recvd_mcmember_rec; + const ib_member_rec_t *p_recvd_mcmember_rec; osm_mcmr_recv_t *p_rcv; p_recvd_mcmember_rec = p_ctxt->p_mcmember_rec; @@ -188,18 +184,19 @@ __search_mgrp_by_mgid( /* compare entire MGID so different scope will not sneak in for the same MGID */ - if (cl_memcmp(&p_mgrp->mcmember_rec.mgid, - &p_recvd_mcmember_rec->mgid, - sizeof(ib_gid_t))) + if (memcmp(&p_mgrp->mcmember_rec.mgid, + &p_recvd_mcmember_rec->mgid, + sizeof(ib_gid_t))) return; - if(p_ctxt->p_mgrp) + if (p_ctxt->p_mgrp) { osm_log( p_rcv->p_log, OSM_LOG_ERROR, "__search_mgrp_by_mgid: ERR 1B03: " "Multiple MC groups for same MGID\n" ); return; } + p_ctxt->p_mgrp = p_mgrp; } @@ -207,17 +204,15 @@ __search_mgrp_by_mgid( /********************************************************************** Look for a MGRP in the mgrp_mlid_tbl by mlid **********************************************************************/ -static -osm_mgrp_t * +static osm_mgrp_t * __get_mgrp_by_mlid( IN osm_mcmr_recv_t* const p_rcv, IN ib_net16_t const mlid) { cl_map_item_t *map_item; - map_item = cl_qmap_get(&p_rcv->p_subn->mgrp_mlid_tbl, - mlid); - if(map_item == cl_qmap_end(&p_rcv->p_subn->mgrp_mlid_tbl)) + map_item = cl_qmap_get(&p_rcv->p_subn->mgrp_mlid_tbl, mlid); + if (map_item == cl_qmap_end(&p_rcv->p_subn->mgrp_mlid_tbl)) { return NULL; } @@ -244,7 +239,7 @@ __get_mgrp_by_mgid( __search_mgrp_by_mgid, &mcmr_search_context); - if(mcmr_search_context.p_mgrp == NULL) + if (mcmr_search_context.p_mgrp == NULL) { return IB_NOT_FOUND; } @@ -254,7 +249,7 @@ __get_mgrp_by_mgid( } /********************************************************************* -copy certain fields between two mcmember records +Copy certain fields between two mcmember records used during the process of join request to copy data from the mgrp to the port record. **********************************************************************/ @@ -294,7 +289,8 @@ available mlids. **********************************************************************/ static ib_net16_t __get_new_mlid( - IN osm_mcmr_recv_t* const p_rcv) + IN osm_mcmr_recv_t* const p_rcv, + IN ib_net16_t requested_mlid) { osm_subn_t *p_subn = p_rcv->p_subn; osm_mgrp_t *p_mgrp; @@ -304,8 +300,16 @@ __get_new_mlid( uint16_t max_num_mlids; OSM_LOG_ENTER(p_rcv->p_log, __get_new_mlid); - - /* If empty MCGroups table - at first return the min mlid */ + + if (requested_mlid && cl_ntoh16(requested_mlid) >= IB_LID_MCAST_START_HO && + cl_ntoh16(requested_mlid) < p_subn->max_multicast_lid_ho && + cl_qmap_get(&p_subn->mgrp_mlid_tbl, requested_mlid) == + cl_qmap_end(&p_subn->mgrp_mlid_tbl) ) { + mlid = cl_ntoh16(requested_mlid); + goto Exit; + } + + /* If MCGroups table empty, first return the min mlid */ p_mgrp = (osm_mgrp_t*)cl_qmap_head( &p_subn->mgrp_mlid_tbl ); if (p_mgrp == (osm_mgrp_t*)cl_qmap_end( &p_subn->mgrp_mlid_tbl )) { @@ -322,7 +326,11 @@ __get_new_mlid( /* track all used mlids in the array (by mlid index) */ used_mlids_array = - (uint8_t *)cl_zalloc(sizeof(uint8_t)*max_num_mlids); + (uint8_t *)malloc(sizeof(uint8_t)*max_num_mlids); + if (used_mlids_array) + memset(used_mlids_array, 0, sizeof(uint8_t)*max_num_mlids); + if (!used_mlids_array) + return 0; /* scan all available multicast groups in the DB and fill in the table */ while( p_mgrp != (osm_mgrp_t*)cl_qmap_end( &p_subn->mgrp_mlid_tbl ) ) @@ -345,7 +353,7 @@ __get_new_mlid( "__get_new_mlid: ERR 1B27: " "Found mgrp with mlid:0x%04X > max allowed mlid:0x%04X\n", cl_ntoh16(p_mgrp->mlid), - max_num_mlids + IB_LID_MCAST_START_HO); + max_num_mlids + IB_LID_MCAST_START_HO ); } else { @@ -367,18 +375,18 @@ __get_new_mlid( osm_log( p_rcv->p_log, OSM_LOG_VERBOSE, "__get_new_mlid: " "Found available mlid:0x%04X at idx:%u\n", - mlid, idx); + mlid, idx ); } else { osm_log( p_rcv->p_log, OSM_LOG_ERROR, "__get_new_mlid: ERR 1B23: " "All available:%u mlids are taken\n", - max_num_mlids); + max_num_mlids ); mlid = 0; } - cl_free(used_mlids_array); + free(used_mlids_array); Exit: OSM_LOG_EXIT(p_rcv->p_log); @@ -386,7 +394,7 @@ __get_new_mlid( } /********************************************************************* -This procedure is only invoked to cleanup INTERMEDIATE mgrp. +This procedure is only invoked to cleanup an INTERMEDIATE mgrp. If there is only one port on the mgrp it means that the current request was the only member and the group is not really needed. So we silently drop it. Since it was an intermediate group no need to @@ -419,31 +427,39 @@ __cleanup_mgrp( Add a port to the group. Calculating its PROXY_JOIN by the Port and requester gids. **********************************************************************/ -static -ib_api_status_t +static ib_api_status_t __add_new_mgrp_port( - IN osm_mcmr_recv_t * p_rcv, - IN osm_mgrp_t *p_mgrp, + IN osm_mcmr_recv_t *p_rcv, + IN osm_mgrp_t *p_mgrp, IN ib_member_rec_t *p_recvd_mcmember_rec, - IN osm_mad_addr_t *p_mad_addr, + IN osm_mad_addr_t *p_mad_addr, OUT osm_mcm_port_t **pp_mcmr_port) { boolean_t proxy_join; ib_gid_t requester_gid; + ib_api_status_t res; /* set the proxy_join if the requester gid is not identical to the joined gid */ - requester_gid = osm_get_gid_by_mad_addr( p_rcv->p_log, - p_rcv->p_subn, - p_mad_addr ); + res = osm_get_gid_by_mad_addr( p_rcv->p_log, + p_rcv->p_subn, + p_mad_addr, &requester_gid ); + if ( res != IB_SUCCESS ) + { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "__add_new_mgrp_port: ERR 1B29: " + "Could not find GID for requester\n" ); + + return IB_INVALID_PARAMETER; + } - if (! cl_memcmp(&p_recvd_mcmember_rec->port_gid, &requester_gid, - sizeof(ib_gid_t))) + if (!memcmp(&p_recvd_mcmember_rec->port_gid, &requester_gid, + sizeof(ib_gid_t))) { proxy_join = FALSE; osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "__add_new_mgrp_port: " - "create new port with proxy_join FALSE\n"); + "Create new port with proxy_join FALSE\n" ); } else { @@ -453,18 +469,18 @@ __add_new_mgrp_port( proxy_join = TRUE; osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "__add_new_mgrp_port: " - "create new port with proxy_join TRUE\n"); + "Create new port with proxy_join TRUE\n" ); } - *pp_mcmr_port = osm_mgrp_add_port(p_mgrp, - &p_recvd_mcmember_rec->port_gid, - p_recvd_mcmember_rec->scope_state, - proxy_join ); + *pp_mcmr_port = osm_mgrp_add_port( p_mgrp, + &p_recvd_mcmember_rec->port_gid, + p_recvd_mcmember_rec->scope_state, + proxy_join ); if(*pp_mcmr_port == NULL) { osm_log( p_rcv->p_log, OSM_LOG_ERROR, "__add_new_mgrp_port: ERR 1B06: " - "osm_mgrp_add_port failed\n"); + "osm_mgrp_add_port failed\n" ); return IB_INSUFFICIENT_MEMORY; } @@ -477,7 +493,7 @@ __add_new_mgrp_port( static inline boolean_t __check_join_comp_mask(ib_net64_t comp_mask) { - return( (comp_mask & JOIN_MC_COMP_MASK) == JOIN_MC_COMP_MASK); + return( (comp_mask & JOIN_MC_COMP_MASK) == JOIN_MC_COMP_MASK ); } /********************************************************************** @@ -506,6 +522,7 @@ __osm_mcmr_rcv_respond( ib_api_status_t status; OSM_LOG_ENTER( p_rcv->p_log, __osm_mcmr_rcv_respond ); + /* * Get a MAD to reply. Address of Mad is in the received mad_wrapper */ @@ -513,7 +530,7 @@ __osm_mcmr_rcv_respond( p_madw->h_bind, sizeof(ib_member_rec_t)+IB_SA_MAD_HDR_SIZE, osm_madw_get_mad_addr_ptr(p_madw) ); - if ( !p_resp_madw) + if ( !p_resp_madw ) { goto Exit; } @@ -521,20 +538,21 @@ __osm_mcmr_rcv_respond( p_resp_sa_mad = (ib_sa_mad_t*)p_resp_madw->p_mad; p_sa_mad = (ib_sa_mad_t*)p_madw->p_mad; /* Copy the MAD header back into the response mad */ - cl_memcpy(p_resp_sa_mad, p_sa_mad, IB_SA_MAD_HDR_SIZE); + memcpy(p_resp_sa_mad, p_sa_mad, IB_SA_MAD_HDR_SIZE); /* based on the current method decide about the response: */ if ((p_resp_sa_mad->method == IB_MAD_METHOD_GET) || (p_resp_sa_mad->method == IB_MAD_METHOD_SET)) { p_resp_sa_mad->method = IB_MAD_METHOD_GET_RESP; - } else if (p_resp_sa_mad->method == IB_MAD_METHOD_DELETE) { - p_resp_sa_mad->method = (uint8_t)(p_resp_sa_mad->method | 0x80); + } + else if (p_resp_sa_mad->method == IB_MAD_METHOD_DELETE) { + p_resp_sa_mad->method |= IB_MAD_METHOD_RESP_MASK; } else { CL_ASSERT( p_resp_sa_mad->method == 0); } - /* C15-0.1.5 - always return SM_Key = 0 (table 151 p 782) */ + /* C15-0.1.5 - always return SM_Key = 0 (table 185 p 884) */ p_resp_sa_mad->sm_key = 0; /* Fill in the offset (paylen will be done by the rmpp SAR) */ @@ -545,20 +563,22 @@ __osm_mcmr_rcv_respond( *p_resp_mcmember_rec = *p_mcmember_rec; /* Fill in the mtu, rate, and packet lifetime selectors */ + p_resp_mcmember_rec->mtu &= 0x3f; p_resp_mcmember_rec->mtu |= 2<<6; /* exactly */ + p_resp_mcmember_rec->rate &= 0x3f; p_resp_mcmember_rec->rate |= 2<<6; /* exactly */ + p_resp_mcmember_rec->pkt_life &= 0x3f; p_resp_mcmember_rec->pkt_life |= 2<<6; /* exactly */ - status = osm_vendor_send( - p_resp_madw->h_bind, - p_resp_madw, - FALSE); + status = osm_vendor_send( p_resp_madw->h_bind, p_resp_madw, FALSE ); if(status != IB_SUCCESS) { osm_log( p_rcv->p_log, OSM_LOG_ERROR, - "__osm_mcmr_rcv_respond: ERR 1B07: \n" - "for TID = <0x%"PRIx64">\n", p_resp_sa_mad->trans_id); + "__osm_mcmr_rcv_respond: ERR 1B07: " + "Unable to send MAD (%s) for TID <0x%"PRIx64">\n", + ib_get_err_str( status ), + p_resp_sa_mad->trans_id ); } Exit: @@ -599,7 +619,7 @@ __validate_more_comp_fields( osm_log( p_log, OSM_LOG_DEBUG, "__validate_more_comp_fields: " "Requested MTU %x is not greater than %x\n", - mtu_mgrp, mtu_required); + mtu_mgrp, mtu_required ); return FALSE; } break; @@ -609,7 +629,7 @@ __validate_more_comp_fields( osm_log( p_log, OSM_LOG_DEBUG, "__validate_more_comp_fields: " "Requested MTU %x is not less than %x\n", - mtu_mgrp, mtu_required); + mtu_mgrp, mtu_required ); return FALSE; } break; @@ -619,7 +639,7 @@ __validate_more_comp_fields( osm_log( p_log, OSM_LOG_DEBUG, "__validate_more_comp_fields: " "Requested MTU %x is not equal to %x\n", - mtu_mgrp, mtu_required); + mtu_mgrp, mtu_required ); return FALSE; } break; @@ -643,7 +663,7 @@ __validate_more_comp_fields( osm_log( p_log, OSM_LOG_DEBUG, "__validate_more_comp_fields: " "Requested RATE %x is not greater than %x\n", - rate_mgrp, rate_required); + rate_mgrp, rate_required ); return FALSE; } break; @@ -653,7 +673,7 @@ __validate_more_comp_fields( osm_log( p_log, OSM_LOG_DEBUG, "__validate_more_comp_fields: " "Requested RATE %x is not less than %x\n", - rate_mgrp, rate_required); + rate_mgrp, rate_required ); return FALSE; } break; @@ -663,7 +683,7 @@ __validate_more_comp_fields( osm_log( p_log, OSM_LOG_DEBUG, "__validate_more_comp_fields: " "Requested RATE %x is not equal to %x\n", - rate_mgrp, rate_required); + rate_mgrp, rate_required ); return FALSE; } break; @@ -695,9 +715,9 @@ __validate_port_caps( if (!p_pi) { osm_log( p_log, OSM_LOG_DEBUG, - "__validate_port_caps: " - "Cannot get Port's 0x%016" PRIx64 " PortInfo\n", - osm_physp_get_port_guid(p_physp)); + "__validate_port_caps: " + "Cannot get Port's 0x%016" PRIx64 " PortInfo\n", + cl_ntoh64( osm_physp_get_port_guid(p_physp) ) ); return FALSE; } @@ -706,9 +726,9 @@ __validate_port_caps( if (mtu_required < mtu_mgrp) { osm_log( p_log, OSM_LOG_DEBUG, - "__validate_port_caps: " - "Port's MTU %x is less than %x\n", - mtu_required, mtu_mgrp); + "__validate_port_caps: " + "Port's MTU %x is less than %x\n", + mtu_required, mtu_mgrp ); return FALSE; } @@ -717,9 +737,9 @@ __validate_port_caps( if (rate_required < rate_mgrp) { osm_log( p_log, OSM_LOG_DEBUG, - "__validate_port_caps: " - "Port's RATE %x is less than %x\n", - rate_required, rate_mgrp); + "__validate_port_caps: " + "Port's RATE %x is less than %x\n", + rate_required, rate_mgrp ); return FALSE; } @@ -742,21 +762,23 @@ __validate_modify(IN osm_mcmr_recv_t* const p_rcv, IN osm_mgrp_t* p_mgrp, IN osm_mad_addr_t* p_mad_addr, IN ib_member_rec_t* p_recvd_mcmember_rec, - OUT osm_mcm_port_t **pp_mcm_port) { + OUT osm_mcm_port_t **pp_mcm_port) +{ ib_net64_t portguid; ib_gid_t request_gid; osm_physp_t* p_request_physp; + ib_api_status_t res; portguid = p_recvd_mcmember_rec->port_gid.unicast.interface_id; *pp_mcm_port = NULL; /* o15-0.2.1: If this is a new port being added - nothing to check */ - if (! osm_mgrp_is_port_present(p_mgrp, portguid, pp_mcm_port)) + if (!osm_mgrp_is_port_present(p_mgrp, portguid, pp_mcm_port)) { osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "__validate_modify: " - "This is a new port in the MC group\n"); + "This is a new port in the MC group\n" ); return TRUE; } @@ -766,11 +788,21 @@ __validate_modify(IN osm_mcmr_recv_t* const p_rcv, { /* The proxy_join is not set. Modifying can by done only if the requester GID == PortGID */ - request_gid = osm_get_gid_by_mad_addr(p_rcv->p_log, - p_rcv->p_subn, - p_mad_addr ); + res = osm_get_gid_by_mad_addr(p_rcv->p_log, + p_rcv->p_subn, + p_mad_addr, + &request_gid); - if (cl_memcmp(&((*pp_mcm_port)->port_gid), &request_gid, sizeof(ib_gid_t))) + if ( res != IB_SUCCESS ) + { + osm_log( p_rcv->p_log, OSM_LOG_DEBUG, + "__validate_modify: " + "Could not find port for requested address\n" + ); + return FALSE; + } + + if (memcmp(&((*pp_mcm_port)->port_gid), &request_gid, sizeof(ib_gid_t))) { osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "__validate_modify: " @@ -788,13 +820,12 @@ __validate_modify(IN osm_mcmr_recv_t* const p_rcv, requester is part of the partition for this MCMemberRecord */ p_request_physp = osm_get_physp_by_mad_addr(p_rcv->p_log, p_rcv->p_subn, - p_mad_addr ); + p_mad_addr); if (p_request_physp == NULL) return FALSE; - - if ( ! osm_physp_has_pkey(p_rcv->p_log, p_mgrp->mcmember_rec.pkey, - p_request_physp )) + if (!osm_physp_has_pkey(p_rcv->p_log, p_mgrp->mcmember_rec.pkey, + p_request_physp)) { /* the request port is not part of the partition for this mgrp */ osm_log( p_rcv->p_log, OSM_LOG_DEBUG, @@ -837,28 +868,30 @@ __validate_delete(IN osm_mcmr_recv_t* const p_rcv, IN osm_mgrp_t *p_mgrp, IN osm_mad_addr_t* p_mad_addr, IN ib_member_rec_t* p_recvd_mcmember_rec, - OUT osm_mcm_port_t **pp_mcm_port) { + OUT osm_mcm_port_t **pp_mcm_port) +{ ib_net64_t portguid; + portguid = p_recvd_mcmember_rec->port_gid.unicast.interface_id; *pp_mcm_port = NULL; /* 1 */ - if (! osm_mgrp_is_port_present(p_mgrp, portguid, pp_mcm_port)) + if (!osm_mgrp_is_port_present(p_mgrp, portguid, pp_mcm_port)) { osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "__validate_delete: " - "Failed to find the port in the MC group\n"); + "Failed to find the port in the MC group\n" ); return FALSE; } /* 2 */ - if (! (p_recvd_mcmember_rec->scope_state & 0x0F & - (*pp_mcm_port)->scope_state)) + if (!(p_recvd_mcmember_rec->scope_state & 0x0F & + (*pp_mcm_port)->scope_state)) { osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "__validate_delete: " - "Could not find any matching bits in the stored and requested JoinState\n"); + "Could not find any matching bits in the stored and requested JoinStates\n" ); return FALSE; } @@ -893,12 +926,12 @@ __validate_delete(IN osm_mcmr_recv_t* const p_rcv, **********************************************************************/ /* * Check legality of the requested MGID (note this does not hold for SA - * created MGIDs + * created MGIDs) * - * Implementing o16.0.1.6: + * Implementing o15-0.1.5: * A multicast GID is considered to be invalid if: * 1. It does not comply with the rules as specified in 4.1.1 "GID Usage and - * Properties" on page 133: + * Properties" on page 145: * * 14) The multicast GID format is (bytes are comma sep): * 0xff,,,,

,

,

,

,

,

,

,

,,,, @@ -933,8 +966,8 @@ __validate_delete(IN osm_mcmr_recv_t* const p_rcv, */ ib_api_status_t __validate_requested_mgid(IN osm_mcmr_recv_t* const p_rcv, - IN const ib_member_rec_t* p_mcm_rec) { - + IN const ib_member_rec_t* p_mcm_rec) +{ uint16_t signature; boolean_t valid = TRUE; @@ -953,7 +986,7 @@ __validate_requested_mgid(IN osm_mcmr_recv_t* const p_rcv, } /* the MGID signature can mark IPoIB or SA assigned MGIDs */ - cl_memcpy(&signature, &(p_mcm_rec->mgid.multicast.raw_group_id), sizeof(signature)); + memcpy(&signature, &(p_mcm_rec->mgid.multicast.raw_group_id), sizeof(signature)); signature = cl_ntoh16(signature); osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "__validate_requested_mgid: " @@ -1005,15 +1038,16 @@ __validate_requested_mgid(IN osm_mcmr_recv_t* const p_rcv, /* 2 - now what if the link local format 0xA01B is used - the scope should not be link local */ if ( ( signature == 0xA01B ) && - ((p_mcm_rec->mgid.multicast.header[1] & 0x0F) == 0x02) ) { + ((p_mcm_rec->mgid.multicast.header[1] & 0x0F) == MC_SCOPE_LINK_LOCAL) ) { osm_log( p_rcv->p_log, OSM_LOG_ERROR, "__validate_requested_mgid: ERR 1B24: " - "MGID Uses 0xA01B signature but with link-local scope\n"); + "MGID uses 0xA01B signature but with link-local scope\n" ); valid = FALSE; goto Exit; } /* + * For SA assigned MGIDs (signature 0xA01B): * There is no real way to make sure the Unique MGID Prefix is really unique. * If we could enforce using the Subnet Prefix for that purpose it would * have been nice. But the spec does not require it. @@ -1035,20 +1069,20 @@ __mgrp_request_is_realizable( IN ib_member_rec_t * p_mcm_rec, IN const osm_physp_t* const p_physp) { - uint8_t mtu_sel; - uint8_t mtu_required; - uint8_t rate_sel; - uint8_t rate_required; + uint8_t mtu_sel = 2; /* exactly */ + uint8_t mtu_required, mtu, port_mtu; + uint8_t rate_sel = 2; /* exactly */ + uint8_t rate_required, rate, port_rate; osm_log_t *p_log = p_rcv->p_log; ib_port_info_t *p_pi = NULL; - OSM_LOG_ENTER( p_rcv->p_log, __mgrp_request_is_realizable;) + OSM_LOG_ENTER( p_rcv->p_log, __mgrp_request_is_realizable ); - if (p_physp != NULL) - p_pi = osm_physp_get_port_info_ptr(p_physp); + if (p_physp != NULL) + p_pi = osm_physp_get_port_info_ptr(p_physp); /* - * End of o15-0.1.6 specifies: + * End of o15-0.2.3 specifies: * .... * The entity may also supply the other components such as HopLimit, MTU, * etc. during group creation time. If these components are not provided @@ -1057,158 +1091,112 @@ __mgrp_request_is_realizable( * * so we might also need to assign RATE/MTU if they are not comp masked in. */ - if (! (comp_mask & IB_MCR_COMPMASK_MTU)) - { - p_mcm_rec->mtu = p_rcv->p_subn->min_ca_mtu; - } + + port_mtu = p_pi ? ib_port_info_get_mtu_cap(p_pi) : 0; + if (!(comp_mask & IB_MCR_COMPMASK_MTU) || + !(comp_mask & IB_MCR_COMPMASK_MTU_SEL) || + (mtu_sel = (p_mcm_rec->mtu >> 6)) == 3) + mtu = port_mtu ? port_mtu : p_rcv->p_subn->min_ca_mtu; else { - /* we need to select an MTU based on the requested MTU and selector */ - if ( comp_mask & IB_MCR_COMPMASK_MTU_SEL) - { - mtu_sel = (uint8_t)(p_mcm_rec->mtu >> 6); - } - else - { - /* by default we assume an exact mtu is requested */ - mtu_sel = 2; - } - - /* Clearing last 2 bits */ mtu_required = (uint8_t)(p_mcm_rec->mtu & 0x3F); - + mtu = mtu_required; switch (mtu_sel) { case 0: /* Greater than MTU specified */ - /* we provide the largest MTU possible if we can */ - if (mtu_required < p_rcv->p_subn->min_ca_mtu) - { - p_mcm_rec->mtu = p_rcv->p_subn->min_ca_mtu; - } - else + if (port_mtu && mtu_required >= port_mtu) { osm_log( p_log, OSM_LOG_DEBUG, "__mgrp_request_is_realizable: " - "Requested MTU %x >= the maximal possible:%x\n", - mtu_required, p_rcv->p_subn->min_ca_mtu); + "Requested MTU %x >= the port\'s mtu:%x\n", + mtu_required, port_mtu ); return FALSE; } + /* we provide the largest MTU possible if we can */ + if (port_mtu) + mtu = port_mtu; + else if (mtu_required < p_rcv->p_subn->min_ca_mtu) + mtu = p_rcv->p_subn->min_ca_mtu; + else + mtu++; break; case 1: /* Less than MTU specified */ - /* if the requested MTU is not already the minimal, then we will - use the smaller of the two: + /* use the smaller of the two: a. one lower then the required - b. the mtu of the requesting port - If the p_pi is NULL, this means there is no requester port and - just use mtu one lower than the required. */ - if ( mtu_required > 1 ) - { - if (p_pi && ib_port_info_get_mtu_cap(p_pi) < (mtu_required - 1)) - p_mcm_rec->mtu = (mtu_sel<<6) | ib_port_info_get_mtu_cap(p_pi); - else - p_mcm_rec->mtu--; - } + b. the mtu of the requesting port (if exists) */ + if (port_mtu && mtu_required > port_mtu) + mtu = port_mtu; else - { - osm_log( p_log, OSM_LOG_DEBUG, - "__mgrp_request_is_realizable: " - "Can not obtain a lower MTU then the given one:%x\n", - mtu_required); - return FALSE; - } + mtu--; break; case 2: /* Exactly MTU specified */ - /* make sure it is in the range */ - if (mtu_required < IB_MIN_MTU || mtu_required > IB_MAX_MTU) - { - osm_log( p_log, OSM_LOG_DEBUG, - "__mgrp_request_is_realizable: " - "Requested MTU %x is out of range\n", - mtu_required); - return FALSE; - } - break; default: break; } + /* make sure it still be in the range */ + if (mtu < IB_MIN_MTU || mtu > IB_MAX_MTU) + { + osm_log( p_log, OSM_LOG_DEBUG, + "__mgrp_request_is_realizable: " + "Calculated MTU %x is out of range\n", + mtu ); + return FALSE; + } } + p_mcm_rec->mtu = (mtu_sel<<6) | mtu; - if (! (comp_mask & IB_MCR_COMPMASK_RATE)) - { - p_mcm_rec->rate = p_rcv->p_subn->min_ca_rate; - } + port_rate = p_pi ? ib_port_info_compute_rate(p_pi) : 0; + if (!(comp_mask & IB_MCR_COMPMASK_RATE) || + !(comp_mask & IB_MCR_COMPMASK_RATE_SEL) || + (rate_sel = (p_mcm_rec->rate >> 6)) == 3) + rate = port_rate ? port_rate : p_rcv->p_subn->min_ca_rate; else { - /* we need to select an RATE based on the requested RATE and selector */ - if ( comp_mask & IB_MCR_COMPMASK_RATE_SEL) - { - rate_sel = (uint8_t)(p_mcm_rec->rate >> 6); - } - else - { - /* by default we assume an exact rate is requested */ - rate_sel = 2; - } - - /* Clearing last 2 bits */ rate_required = (uint8_t)(p_mcm_rec->rate & 0x3F); - + rate = rate_required; switch (rate_sel) { case 0: /* Greater than RATE specified */ - /* we provide the largest RATE possible if we can */ - if (rate_required < p_rcv->p_subn->min_ca_rate) - { - p_mcm_rec->rate = p_rcv->p_subn->min_ca_rate; - } - else + if (port_rate && rate_required >= port_rate) { osm_log( p_log, OSM_LOG_DEBUG, "__mgrp_request_is_realizable: " - "Requested RATE %x >= the maximal possible:%x\n", - rate_required, p_rcv->p_subn->min_ca_rate); + "Requested RATE %x >= the port\'s rate:%x\n", + rate_required, port_rate ); return FALSE; } + /* we provide the largest RATE possible if we can */ + if (port_rate) + rate = port_rate; + else if (rate_required < p_rcv->p_subn->min_ca_rate) + rate = p_rcv->p_subn->min_ca_rate; + else + rate++; break; case 1: /* Less than RATE specified */ - /* if the requested RATE is not already the minimal, then we will - use the smaller of the two: + /* use the smaller of the two: a. one lower then the required - b. the rate of the requesting port - If the p_pi is NULL, this means there is no requester port and - just use rate one lower than the required. */ - - if ( rate_required > 2 ) - { - if (p_pi && ib_port_info_compute_rate(p_pi) < (rate_required - 1)) - p_mcm_rec->rate = (rate_sel<<6) | ib_port_info_compute_rate(p_pi); - else - p_mcm_rec->rate--; - } + b. the rate of the requesting port (if exists) */ + if (port_rate && rate_required > port_rate) + rate = port_rate; else - { - osm_log( p_log, OSM_LOG_DEBUG, - "__mgrp_request_is_realizable: " - "Can not obtain a lower RATE then the given one:%x\n", - rate_required); - return FALSE; - } + rate--; break; case 2: /* Exactly RATE specified */ - /* make sure it is in the range */ - if (rate_required < IB_MIN_RATE || rate_required > IB_MAX_RATE) - { - osm_log( p_log, OSM_LOG_DEBUG, - "__mgrp_request_is_realizable: " - "Requested RATE %x is out of range\n", - rate_required); - return FALSE; - } - break; default: break; } + /* make sure it still is in the range */ + if (rate < IB_MIN_RATE || rate > IB_MAX_RATE) + { + osm_log( p_log, OSM_LOG_DEBUG, + "__mgrp_request_is_realizable: " + "Calculated RATE %x is out of range\n", + rate ); + return FALSE; + } } + p_mcm_rec->rate = (rate_sel<<6) | rate; OSM_LOG_EXIT( p_rcv->p_log ); return TRUE; @@ -1225,6 +1213,7 @@ osm_mcmr_rcv_find_or_create_new_mgrp( OUT osm_mgrp_t **pp_mgrp) { ib_api_status_t status; + status = __get_mgrp_by_mgid(p_rcv, p_recvd_mcmember_rec, pp_mgrp); if (status == IB_SUCCESS) return status; @@ -1249,9 +1238,7 @@ osm_mcmr_rcv_create_new_mgrp( ib_gid_t *p_mgid; osm_mgrp_t *p_prev_mgrp; ib_api_status_t status = IB_SUCCESS; - - /* copy for modifications */ - ib_member_rec_t mcm_rec = *p_recvd_mcmember_rec; + ib_member_rec_t mcm_rec = *p_recvd_mcmember_rec; /* copy for modifications */ OSM_LOG_ENTER( p_rcv->p_log, osm_mcmr_rcv_create_new_mgrp ); @@ -1270,19 +1257,19 @@ osm_mcmr_rcv_create_new_mgrp( we allocate a new mlid number before we might use it for MGID ... */ - mlid = __get_new_mlid(p_rcv); + mlid = __get_new_mlid(p_rcv, mcm_rec.mlid); if ( mlid == 0 ) { osm_log( p_rcv->p_log, OSM_LOG_ERROR, "osm_mcmr_rcv_create_new_mgrp: ERR 1B19: " - "__get_new_mlid failed\n"); + "__get_new_mlid failed\n" ); status = IB_SA_MAD_STATUS_NO_RESOURCES; goto Exit; } osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "osm_mcmr_rcv_create_new_mgrp: " - "Getting new mlid 0x%x\n", cl_ntoh16(mlid)); + "Obtained new mlid 0x%X\n", cl_ntoh16(mlid) ); /* we need to create the new MGID if it was not defined */ if (zero_mgid) @@ -1298,7 +1285,7 @@ osm_mcmr_rcv_create_new_mgrp( else { /* to guarantee no collision with other subnets use local scope! */ - scope = 0x02; /* link-local scope */ + scope = MC_SCOPE_LINK_LOCAL; } p_mgid = &(mcm_rec.mgid); @@ -1307,13 +1294,13 @@ osm_mcmr_rcv_create_new_mgrp( p_mgid->raw[2] = 0xA0; p_mgid->raw[3] = 0x1B; - /* HACK: I will be using the SA port gid for making it globally unique */ - cl_memcpy((&p_mgid->raw[4]), - &p_rcv->p_subn->opt.subnet_prefix, sizeof(uint64_t)); + /* HACK: use the SA port gid to make it globally unique */ + memcpy((&p_mgid->raw[4]), + &p_rcv->p_subn->opt.subnet_prefix, sizeof(uint64_t)); - /* HACK how do we get a unique number - use the mlid twice */ - cl_memcpy(&p_mgid->raw[10], &mlid, sizeof(uint16_t)); - cl_memcpy(&p_mgid->raw[12], &mlid, sizeof(uint16_t)); + /* HACK: how do we get a unique number - use the mlid twice */ + memcpy(&p_mgid->raw[10], &mlid, sizeof(uint16_t)); + memcpy(&p_mgid->raw[12], &mlid, sizeof(uint16_t)); osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "osm_mcmr_rcv_create_new_mgrp: " "Allocated new MGID:0x%016" PRIx64 " : " @@ -1323,14 +1310,13 @@ osm_mcmr_rcv_create_new_mgrp( } else { - /* a specific MGID was requested so validate the resulting MGID */ valid = __validate_requested_mgid(p_rcv, &mcm_rec); - if (! valid) + if (!valid) { osm_log( p_rcv->p_log, OSM_LOG_ERROR, "osm_mcmr_rcv_create_new_mgrp: ERR 1B22: " - "Invalid requested MGID\n"); + "Invalid requested MGID\n" ); __free_mlid(p_rcv, mlid); status = IB_SA_MAD_STATUS_REQ_INVALID; goto Exit; @@ -1342,7 +1328,7 @@ osm_mcmr_rcv_create_new_mgrp( { osm_log( p_rcv->p_log, OSM_LOG_ERROR, "osm_mcmr_rcv_create_new_mgrp: ERR 1B26: " - "Requested MGRP parameters are not realizable\n"); + "Requested MGRP parameters are not realizable\n" ); __free_mlid(p_rcv, mlid); status = IB_SA_MAD_STATUS_REQ_INVALID; goto Exit; @@ -1354,25 +1340,28 @@ osm_mcmr_rcv_create_new_mgrp( { osm_log( p_rcv->p_log, OSM_LOG_ERROR, "osm_mcmr_rcv_create_new_mgrp: ERR 1B08: " - "osm_mgrp_new failed\n"); + "osm_mgrp_new failed\n" ); __free_mlid(p_rcv, mlid); status = IB_SA_MAD_STATUS_NO_RESOURCES; goto Exit; } - /* the mcmember_record should have mtu_sel, rate_sel and pkt_lifetime_sel = 2 */ - (*pp_mgrp)->mcmember_rec.mtu |= 2<<6; /* exactly */ - (*pp_mgrp)->mcmember_rec.rate |= 2<<6; /* exactly */ - (*pp_mgrp)->mcmember_rec.pkt_life |= 2<<6; /* exactly */ - /* Initialize the mgrp */ (*pp_mgrp)->mcmember_rec = mcm_rec; (*pp_mgrp)->mcmember_rec.mlid = mlid; + /* the mcmember_record should have mtu_sel, rate_sel, and pkt_lifetime_sel = 2 */ + (*pp_mgrp)->mcmember_rec.mtu &= 0x3f; + (*pp_mgrp)->mcmember_rec.mtu |= 2<<6; /* exactly */ + (*pp_mgrp)->mcmember_rec.rate &= 0x3f; + (*pp_mgrp)->mcmember_rec.rate |= 2<<6; /* exactly */ + (*pp_mgrp)->mcmember_rec.pkt_life &= 0x3f; + (*pp_mgrp)->mcmember_rec.pkt_life |= 2<<6; /* exactly */ + /* Insert the new group in the data base */ /* since we might have an old group by that mlid - one that its deletion was delayed for an idle time + one whose deletion was delayed for an idle time we need to deallocate it first */ p_prev_mgrp = (osm_mgrp_t *)cl_qmap_get(&p_rcv->p_subn->mgrp_mlid_tbl, mlid); if (p_prev_mgrp != (osm_mgrp_t *)cl_qmap_end(&p_rcv->p_subn->mgrp_mlid_tbl)) @@ -1380,7 +1369,7 @@ osm_mcmr_rcv_create_new_mgrp( osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "osm_mcmr_rcv_create_new_mgrp: " "Found previous group for mlid:0x%04x - Need to destroy it\n", - cl_ntoh16(mlid)); + cl_ntoh16(mlid) ); cl_qmap_remove_item(&p_rcv->p_subn->mgrp_mlid_tbl, (cl_map_item_t *)p_prev_mgrp ); osm_mgrp_destroy( p_prev_mgrp ); @@ -1404,7 +1393,7 @@ osm_mcmr_rcv_create_new_mgrp( Process a request for leaving the group **********************************************************************/ static void -osm_mcmr_rcv_leave_mgrp( +__osm_mcmr_rcv_leave_mgrp( IN osm_mcmr_recv_t* const p_rcv, IN const osm_madw_t* const p_madw ) { @@ -1421,7 +1410,7 @@ osm_mcmr_rcv_leave_mgrp( uint8_t port_join_state; uint8_t new_join_state; - OSM_LOG_ENTER( p_rcv->p_log, osm_mcmr_rcv_leave_mgrp ); + OSM_LOG_ENTER( p_rcv->p_log, __osm_mcmr_rcv_leave_mgrp ); p_mgrp = NULL; p_sa_mad = osm_madw_get_sa_mad_ptr( p_madw ); @@ -1430,12 +1419,15 @@ osm_mcmr_rcv_leave_mgrp( mcmember_rec = *p_recvd_mcmember_rec; - if ( osm_log_is_active( p_rcv->p_log, OSM_LOG_DEBUG ) ) + if ( osm_log_is_active( p_rcv->p_log, OSM_LOG_DEBUG ) ) { + osm_log( p_rcv->p_log, OSM_LOG_DEBUG, + "__osm_mcmr_rcv_leave_mgrp: Dump of record\n" ); osm_dump_mc_record( p_rcv->p_log, &mcmember_rec, OSM_LOG_DEBUG ); + } CL_PLOCK_EXCL_ACQUIRE(p_rcv->p_lock); status = __get_mgrp_by_mgid(p_rcv,p_recvd_mcmember_rec, &p_mgrp); - if(status == IB_SUCCESS) + if (status == IB_SUCCESS) { mlid = p_mgrp->mlid; portguid = p_recvd_mcmember_rec->port_gid.unicast.interface_id; @@ -1449,7 +1441,6 @@ osm_mcmr_rcv_leave_mgrp( if (valid) { - /* * according to the same o15-0.1.14 we get the stored JoinState and the * request JoinState and they must be opposite to leave - @@ -1460,17 +1451,20 @@ osm_mcmr_rcv_leave_mgrp( port_join_state & ~(p_recvd_mcmember_rec->scope_state & 0x0F); if (new_join_state) { - osm_log( p_rcv->p_log, OSM_LOG_DEBUG, - "osm_mcmr_rcv_leave_mgrp: " - "After update JoinState != 0. Updating from 0x%X to 0x%X\n", - port_join_state, - new_join_state - ); /* Just update the result JoinState */ p_mcm_port->scope_state = new_join_state | (p_mcm_port->scope_state & 0xf0); mcmember_rec.scope_state = p_mcm_port->scope_state; + + CL_PLOCK_RELEASE( p_rcv->p_lock ); + + osm_log( p_rcv->p_log, OSM_LOG_DEBUG, + "__osm_mcmr_rcv_leave_mgrp: " + "After update JoinState != 0. Updating from 0x%X to 0x%X\n", + port_join_state, + new_join_state + ); } else { @@ -1478,29 +1472,23 @@ osm_mcmr_rcv_leave_mgrp( mcmember_rec.scope_state = p_mcm_port->scope_state; /* OK we can leave */ - CL_PLOCK_RELEASE( p_rcv->p_lock ); + /* note: osm_sm_mcgrp_leave() will release p_rcv->p_lock */ - status = osm_sm_mcgrp_leave(p_rcv->p_sm, - mlid, - portguid); + status = osm_sm_mcgrp_leave(p_rcv->p_sm, mlid, portguid); if(status != IB_SUCCESS) { osm_log( p_rcv->p_log, OSM_LOG_ERROR, - "osm_mcmr_rcv_leave_mgrp: ERR 1B09: " - "osm_sm_mcgrp_leave failed\n"); + "__osm_mcmr_rcv_leave_mgrp: ERR 1B09: " + "osm_sm_mcgrp_leave failed\n" ); } - - CL_PLOCK_EXCL_ACQUIRE(p_rcv->p_lock); - /* Note: The deletion of the mgrp itself will be done in the callback - for the multicast tree updating (osm_mcast_mgr_process_mgrp_cb) */ } } else { CL_PLOCK_RELEASE( p_rcv->p_lock ); osm_log( p_rcv->p_log, OSM_LOG_ERROR, - "osm_mcmr_rcv_leave_mgrp: ERR 1B25: " - "Received an invalid delete request on " + "__osm_mcmr_rcv_leave_mgrp: ERR 1B25: " + "Received an invalid delete request for " "MGID: 0x%016" PRIx64 " : " "0x%016" PRIx64 " for " "PortGID: 0x%016" PRIx64 " : " @@ -1510,28 +1498,23 @@ osm_mcmr_rcv_leave_mgrp( cl_ntoh64( p_recvd_mcmember_rec->port_gid.unicast.prefix ), cl_ntoh64( p_recvd_mcmember_rec->port_gid.unicast.interface_id ) ); sa_status = IB_SA_MAD_STATUS_REQ_INVALID; - osm_sa_send_error( p_rcv->p_resp, p_madw, sa_status); + osm_sa_send_error( p_rcv->p_resp, p_madw, sa_status ); goto Exit; } - } else { CL_PLOCK_RELEASE( p_rcv->p_lock ); osm_log( p_rcv->p_log, OSM_LOG_DEBUG, - "osm_mcmr_rcv_leave_mgrp: " - "Multicast group not present failed\n"); + "__osm_mcmr_rcv_leave_mgrp: " + "Failed since multicast group not present\n" ); sa_status = IB_SA_MAD_STATUS_REQ_INVALID; - osm_sa_send_error( p_rcv->p_resp, p_madw, sa_status); + osm_sa_send_error( p_rcv->p_resp, p_madw, sa_status ); goto Exit; } - CL_PLOCK_RELEASE( p_rcv->p_lock ); - - /* Send an SA RESPONSE */ - __osm_mcmr_rcv_respond( p_rcv, - p_madw, - &mcmember_rec ); + /* Send an SA response */ + __osm_mcmr_rcv_respond( p_rcv, p_madw, &mcmember_rec ); Exit: OSM_LOG_EXIT( p_rcv->p_log ); @@ -1541,12 +1524,10 @@ osm_mcmr_rcv_leave_mgrp( /********************************************************************** Handle a join (or create) request **********************************************************************/ -static -void -osm_mcmr_rcv_join_mgrp( +static void +__osm_mcmr_rcv_join_mgrp( IN osm_mcmr_recv_t* const p_rcv, - IN const osm_madw_t* const p_madw - ) + IN const osm_madw_t* const p_madw ) { boolean_t valid; osm_mgrp_t *p_mgrp = NULL; @@ -1565,7 +1546,7 @@ osm_mcmr_rcv_join_mgrp( osm_mcast_req_type_t req_type; uint8_t join_state; - OSM_LOG_ENTER( p_rcv->p_log, osm_mcmr_rcv_join_mgrp ); + OSM_LOG_ENTER( p_rcv->p_log, __osm_mcmr_rcv_join_mgrp ); p_mgrp = NULL; p_sa_mad = osm_madw_get_sa_mad_ptr( p_madw ); @@ -1579,8 +1560,8 @@ osm_mcmr_rcv_join_mgrp( if ( osm_log_is_active( p_rcv->p_log, OSM_LOG_DEBUG ) ) { osm_log( p_rcv->p_log, OSM_LOG_DEBUG, - "osm_mcmr_rcv_join_mgrp: " - "Dump of incoming record\n"); + "__osm_mcmr_rcv_join_mgrp: " + "Dump of incoming record\n" ); osm_dump_mc_record( p_rcv->p_log, &mcmember_rec, OSM_LOG_DEBUG ); } @@ -1595,11 +1576,11 @@ osm_mcmr_rcv_join_mgrp( CL_PLOCK_RELEASE( p_rcv->p_lock ); osm_log( p_rcv->p_log, OSM_LOG_DEBUG, - "osm_mcmr_rcv_join_mgrp: " - "Unknown portguid 0x%016" PRIx64 "\n", - portguid); - sa_status = IB_SA_MAD_STATUS_REQ_INVALID; - osm_sa_send_error( p_rcv->p_resp, p_madw, sa_status); + "__osm_mcmr_rcv_join_mgrp: " + "Unknown port GUID 0x%016" PRIx64 "\n", + portguid ); + sa_status = IB_SA_MAD_STATUS_REQ_INVALID; + osm_sa_send_error( p_rcv->p_resp, p_madw, sa_status ); goto Exit; } @@ -1616,15 +1597,15 @@ osm_mcmr_rcv_join_mgrp( goto Exit; } - if (! osm_physp_share_pkey( p_rcv->p_log, p_physp, p_request_physp)) + if (!osm_physp_share_pkey( p_rcv->p_log, p_physp, p_request_physp)) { CL_PLOCK_RELEASE( p_rcv->p_lock ); osm_log( p_rcv->p_log, OSM_LOG_DEBUG, - "osm_mcmr_rcv_join_mgrp: " - "port and requester don't share pkey\n" ); - sa_status = IB_SA_MAD_STATUS_REQ_INVALID; - osm_sa_send_error( p_rcv->p_resp, p_madw, sa_status); + "__osm_mcmr_rcv_join_mgrp: " + "Port and requester don't share pkey\n" ); + sa_status = IB_SA_MAD_STATUS_REQ_INVALID; + osm_sa_send_error( p_rcv->p_resp, p_madw, sa_status ); goto Exit; } @@ -1640,14 +1621,14 @@ osm_mcmr_rcv_join_mgrp( { CL_PLOCK_RELEASE( p_rcv->p_lock ); osm_log( p_rcv->p_log, OSM_LOG_ERROR, - "osm_mcmr_rcv_join_mgrp: ERR 1B10: " + "__osm_mcmr_rcv_join_mgrp: ERR 1B10: " "Provided Join State != FullMember - required for create, " "MGID: 0x%016" PRIx64 " : " "0x%016" PRIx64 "\n", cl_ntoh64( p_recvd_mcmember_rec->mgid.unicast.prefix ), cl_ntoh64( p_recvd_mcmember_rec->mgid.unicast.interface_id ) ); sa_status = IB_SA_MAD_STATUS_REQ_INVALID; - osm_sa_send_error( p_rcv->p_resp, p_madw, sa_status); + osm_sa_send_error( p_rcv->p_resp, p_madw, sa_status ); goto Exit; } @@ -1665,7 +1646,7 @@ osm_mcmr_rcv_join_mgrp( { CL_PLOCK_RELEASE( p_rcv->p_lock ); sa_status = status; - osm_sa_send_error( p_rcv->p_resp, p_madw, sa_status); + osm_sa_send_error( p_rcv->p_resp, p_madw, sa_status ); goto Exit; } /* copy the MGID to the result */ @@ -1673,24 +1654,26 @@ osm_mcmr_rcv_join_mgrp( } else { + CL_PLOCK_RELEASE( p_rcv->p_lock ); + osm_log( p_rcv->p_log, OSM_LOG_ERROR, - "osm_mcmr_rcv_join_mgrp: ERR 1B11: " + "__osm_mcmr_rcv_join_mgrp: ERR 1B11: " "method = %s, " "scope_state = 0x%x, " "component mask = 0x%016" PRIx64 ", " "expected comp mask = 0x%016" PRIx64 ", " "MGID: 0x%016" PRIx64 " : " - "0x%016" PRIx64 "\n", + "0x%016" PRIx64 " from port 0x%016" PRIx64 "\n", ib_get_sa_method_str(p_sa_mad->method), p_recvd_mcmember_rec->scope_state, cl_ntoh64(p_sa_mad->comp_mask), CL_NTOH64(REQUIRED_MC_CREATE_COMP_MASK), cl_ntoh64( p_recvd_mcmember_rec->mgid.unicast.prefix ), - cl_ntoh64( p_recvd_mcmember_rec->mgid.unicast.interface_id ) ); + cl_ntoh64( p_recvd_mcmember_rec->mgid.unicast.interface_id ), + cl_ntoh64( portguid ) ); - CL_PLOCK_RELEASE( p_rcv->p_lock ); - sa_status = IB_SA_MAD_STATUS_INSUF_COMPS; - osm_sa_send_error( p_rcv->p_resp, p_madw, sa_status); + sa_status = IB_SA_MAD_STATUS_INSUF_COMPS; + osm_sa_send_error( p_rcv->p_resp, p_madw, sa_status ); goto Exit; } is_new_group = 1; @@ -1723,7 +1706,7 @@ osm_mcmr_rcv_join_mgrp( * of components such as ProxyJoin and Reserved, which are ignored * by SA. * - * We we need to check #3 and #5 here: + * We need to check #3 and #5 here: */ valid = __validate_more_comp_fields( p_rcv->p_log, @@ -1734,28 +1717,29 @@ osm_mcmr_rcv_join_mgrp( p_mgrp, p_physp) && (join_state != 0); - if (! valid) + if (!valid) { - osm_log( p_rcv->p_log, OSM_LOG_ERROR, - "osm_mcmr_rcv_join_mgrp: ERR 1B12: " - "__validate_more_comp_fields, __validate_port_caps, " - "or JoinState = 0 failed, " - "sending IB_SA_MAD_STATUS_REQ_INVALID\n"); - /* since we might have created the new group we need to cleanup */ __cleanup_mgrp(p_rcv, mlid); CL_PLOCK_RELEASE( p_rcv->p_lock ); - sa_status = IB_SA_MAD_STATUS_REQ_INVALID; - osm_sa_send_error( p_rcv->p_resp, p_madw, sa_status); + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "__osm_mcmr_rcv_join_mgrp: ERR 1B12: " + "__validate_more_comp_fields, __validate_port_caps, " + "or JoinState = 0 failed from port 0x%016" PRIx64 ", " + "sending IB_SA_MAD_STATUS_REQ_INVALID\n", + cl_ntoh64( portguid ) ); + + sa_status = IB_SA_MAD_STATUS_REQ_INVALID; + osm_sa_send_error( p_rcv->p_resp, p_madw, sa_status ); goto Exit; } /* * Do some validation of the modification */ - if (! is_new_group) + if (!is_new_group) { /* * o15-0.2.1 requires validation of the requesting port @@ -1766,17 +1750,17 @@ osm_mcmr_rcv_join_mgrp( osm_madw_get_mad_addr_ptr(p_madw), p_recvd_mcmember_rec, &p_mcmr_port); - if (! valid) + if (!valid) { + CL_PLOCK_RELEASE( p_rcv->p_lock ); + osm_log( p_rcv->p_log, OSM_LOG_ERROR, - "osm_mcmr_rcv_join_mgrp: ERR 1B13: " + "__osm_mcmr_rcv_join_mgrp: ERR 1B13: " "__validate_modify failed, " - "sending IB_SA_MAD_STATUS_REQ_INVALID\n"); - - CL_PLOCK_RELEASE( p_rcv->p_lock ); + "sending IB_SA_MAD_STATUS_REQ_INVALID\n" ); - sa_status = IB_SA_MAD_STATUS_REQ_INVALID; - osm_sa_send_error( p_rcv->p_resp, p_madw, sa_status); + sa_status = IB_SA_MAD_STATUS_REQ_INVALID; + osm_sa_send_error( p_rcv->p_resp, p_madw, sa_status ); goto Exit; } } @@ -1791,13 +1775,16 @@ osm_mcmr_rcv_join_mgrp( if (status != IB_SUCCESS) { - /* we fail to add the port so we might need to delete the - group */ + /* we fail to add the port so we might need to delete the group */ __cleanup_mgrp(p_rcv, mlid); CL_PLOCK_RELEASE( p_rcv->p_lock ); - sa_status = IB_SA_MAD_STATUS_NO_RESOURCES; - osm_sa_send_error( p_rcv->p_resp, p_madw, sa_status); + if (status == IB_INVALID_PARAMETER) + sa_status = IB_SA_MAD_STATUS_REQ_INVALID; + else + sa_status = IB_SA_MAD_STATUS_NO_RESOURCES; + + osm_sa_send_error( p_rcv->p_resp, p_madw, sa_status ); goto Exit; } @@ -1815,14 +1802,14 @@ osm_mcmr_rcv_join_mgrp( osm_sm_mcgrp_join(p_rcv->p_sm, mlid, p_recvd_mcmember_rec->port_gid.unicast.interface_id, - req_type ); + req_type); if (status != IB_SUCCESS) { osm_log( p_rcv->p_log, OSM_LOG_ERROR, - "osm_mcmr_rcv_join_mgrp: ERR 1B14: " + "__osm_mcmr_rcv_join_mgrp: ERR 1B14: " "osm_sm_mcgrp_join failed, " - "sending IB_SA_MAD_STATUS_NO_RESOURCES\n"); + "sending IB_SA_MAD_STATUS_NO_RESOURCES\n" ); CL_PLOCK_EXCL_ACQUIRE(p_rcv->p_lock); @@ -1839,7 +1826,7 @@ osm_mcmr_rcv_join_mgrp( } CL_PLOCK_RELEASE( p_rcv->p_lock ); sa_status = IB_SA_MAD_STATUS_NO_RESOURCES; - osm_sa_send_error( p_rcv->p_resp, p_madw, sa_status); + osm_sa_send_error( p_rcv->p_resp, p_madw, sa_status ); goto Exit; } /* failed to route */ @@ -1847,14 +1834,11 @@ osm_mcmr_rcv_join_mgrp( if ( osm_log_is_active( p_rcv->p_log, OSM_LOG_DEBUG ) ) osm_dump_mc_record( p_rcv->p_log, &mcmember_rec, OSM_LOG_DEBUG ); - __osm_mcmr_rcv_respond( p_rcv, - p_madw, - &mcmember_rec ); + __osm_mcmr_rcv_respond( p_rcv, p_madw, &mcmember_rec ); Exit: OSM_LOG_EXIT( p_rcv->p_log ); return; - } /********************************************************************** @@ -1863,11 +1847,11 @@ osm_mcmr_rcv_join_mgrp( static ib_api_status_t __osm_mcmr_rcv_new_mcmr( IN osm_mcmr_recv_t* const p_rcv, - IN const ib_member_rec_t* p_rcvd_rec, - IN cl_qlist_t* const p_list) + IN const ib_member_rec_t* p_rcvd_rec, + IN cl_qlist_t* const p_list ) { osm_mcmr_item_t* p_rec_item; - ib_api_status_t status = IB_SUCCESS; + ib_api_status_t status = IB_SUCCESS; OSM_LOG_ENTER( p_rcv->p_log, __osm_mcmr_rcv_new_mcmr ); @@ -1881,7 +1865,7 @@ __osm_mcmr_rcv_new_mcmr( goto Exit; } - cl_memclr( &p_rec_item->rec, sizeof( p_rec_item->rec ) ); + memset( &p_rec_item->rec, 0, sizeof( p_rec_item->rec ) ); /* HACK: Not trusted requesters should result with 0 Join State, Port Guid, and Proxy */ @@ -1898,8 +1882,8 @@ __osm_mcmr_rcv_new_mcmr( **********************************************************************/ void __osm_sa_mcm_by_comp_mask_cb( - IN cl_map_item_t* const p_map_item, - IN void* context ) + IN cl_map_item_t* const p_map_item, + IN void* context ) { const osm_mgrp_t * const p_mgrp = (osm_mgrp_t *)p_map_item; osm_sa_mcmr_search_ctxt_t* const p_ctxt = @@ -1925,7 +1909,7 @@ __osm_sa_mcm_by_comp_mask_cb( osm_log(p_rcv->p_log, OSM_LOG_DEBUG, "__osm_sa_mcm_by_comp_mask_cb: " "Checking mlid:0x%X\n", - cl_ntoh16(p_mgrp->mlid )); + cl_ntoh16(p_mgrp->mlid)); /* the group might be marked for deletion */ if (p_mgrp->to_be_deleted) @@ -1933,23 +1917,23 @@ __osm_sa_mcm_by_comp_mask_cb( osm_log(p_rcv->p_log, OSM_LOG_DEBUG, "__osm_sa_mcm_by_comp_mask_cb: " "Group mlid:0x%X is marked to be deleted\n", - cl_ntoh16(p_mgrp->mlid )); + cl_ntoh16(p_mgrp->mlid)); goto Exit; } /* 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))) + 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))) + 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 (!osm_physp_has_pkey( p_rcv->p_log, p_mgrp->mcmember_rec.pkey, + p_req_physp )) goto Exit; /* now do the rest of the match */ @@ -2015,7 +1999,7 @@ __osm_sa_mcm_by_comp_mask_cb( 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)); + memcpy(&port_gid, &(p_mcm_port->port_gid), sizeof(ib_gid_t)); proxy_join = p_mcm_port->proxy_join; } else @@ -2035,7 +2019,7 @@ __osm_sa_mcm_by_comp_mask_cb( { 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"); + "Trusted req is TRUE and no specific port defined\n"); /* return all the ports that match in this MC group */ p_item = cl_qmap_head(&(p_mgrp->mcm_port_tbl)); @@ -2049,11 +2033,11 @@ __osm_sa_mcm_by_comp_mask_cb( /* 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), + 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 + "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), @@ -2077,7 +2061,7 @@ __osm_sa_mcm_by_comp_mask_cb( /* 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)); + 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); @@ -2090,14 +2074,15 @@ __osm_sa_mcm_by_comp_mask_cb( /********************************************************************** Handle a query request **********************************************************************/ -void -osm_mcmr_query_mgrp(IN osm_mcmr_recv_t* const p_rcv, - IN const osm_madw_t* const p_madw) { - const ib_sa_mad_t* p_rcvd_mad; +static void +__osm_mcmr_query_mgrp(IN osm_mcmr_recv_t* const p_rcv, + IN const osm_madw_t* const p_madw) +{ + const ib_sa_mad_t* p_rcvd_mad; const ib_member_rec_t* p_rcvd_rec; cl_qlist_t rec_list; osm_madw_t* p_resp_madw; - ib_sa_mad_t* p_resp_sa_mad; + ib_sa_mad_t* p_resp_sa_mad; ib_member_rec_t* p_resp_rec; uint32_t num_rec, pre_trim_num_rec; #ifndef VENDOR_RMPP_SUPPORT @@ -2106,23 +2091,17 @@ osm_mcmr_query_mgrp(IN osm_mcmr_recv_t* const p_rcv, uint32_t i; osm_sa_mcmr_search_ctxt_t context; osm_mcmr_item_t* p_rec_item; - ib_api_status_t status; + ib_api_status_t status; ib_net64_t comp_mask; osm_physp_t* p_req_physp; boolean_t trusted_req; - CL_ASSERT( p_rcv ); - - OSM_LOG_ENTER( p_rcv->p_log, osm_mcmr_query_mgrp ); - - CL_ASSERT( p_madw ); + OSM_LOG_ENTER( p_rcv->p_log, __osm_mcmr_query_mgrp ); p_rcvd_mad = osm_madw_get_sa_mad_ptr( p_madw ); p_rcvd_rec = (ib_member_rec_t*)ib_sa_mad_get_payload_ptr( p_rcvd_mad ); comp_mask = p_rcvd_mad->comp_mask; - 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 @@ -2136,7 +2115,7 @@ osm_mcmr_query_mgrp(IN osm_mcmr_recv_t* const p_rcv, if (p_req_physp == NULL) { osm_log( p_rcv->p_log, OSM_LOG_ERROR, - "osm_mcmr_query_mgrp: ERR 1B04: " + "__osm_mcmr_query_mgrp: ERR 1B04: " "Cannot find requester physical port\n" ); goto Exit; } @@ -2168,11 +2147,11 @@ osm_mcmr_query_mgrp(IN osm_mcmr_recv_t* const p_rcv, if ( (p_rcvd_mad->method == IB_MAD_METHOD_GET) && (num_rec > 1)) { osm_log( p_rcv->p_log, OSM_LOG_ERROR, - "osm_mcmr_query_mgrp: ERR 1B05: " + "__osm_mcmr_query_mgrp: ERR 1B05: " "Got more than one record for SubnAdmGet (%u)\n", num_rec ); osm_sa_send_error( p_rcv->p_resp, p_madw, - IB_SA_MAD_STATUS_TOO_MANY_RECORDS); + IB_SA_MAD_STATUS_TOO_MANY_RECORDS ); /* need to set the mem free ... */ p_rec_item = (osm_mcmr_item_t*)cl_qlist_remove_head( &rec_list ); @@ -2191,7 +2170,7 @@ osm_mcmr_query_mgrp(IN osm_mcmr_recv_t* const p_rcv, if (trim_num_rec < num_rec) { osm_log( p_rcv->p_log, OSM_LOG_VERBOSE, - "osm_mcmr_query_mgrp: " + "__osm_mcmr_query_mgrp: " "Number of records:%u trimmed to:%u to fit in one MAD\n", num_rec, trim_num_rec ); num_rec = trim_num_rec; @@ -2199,13 +2178,12 @@ osm_mcmr_query_mgrp(IN osm_mcmr_recv_t* const p_rcv, #endif osm_log( p_rcv->p_log, OSM_LOG_DEBUG, - "osm_mcmr_query_mgrp: " + "__osm_mcmr_query_mgrp: " "Returning %u records\n", num_rec ); if ((p_rcvd_mad->method == IB_MAD_METHOD_GET) && (num_rec == 0)) { - osm_sa_send_error( p_rcv->p_resp, p_madw, - IB_SA_MAD_STATUS_NO_RECORDS ); + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_SA_MAD_STATUS_NO_RECORDS ); goto Exit; } @@ -2219,9 +2197,9 @@ osm_mcmr_query_mgrp(IN osm_mcmr_recv_t* const p_rcv, if( !p_resp_madw ) { - osm_log(p_rcv->p_log, OSM_LOG_ERROR, - "osm_mcmr_query_mgrp: ERR 1B16: " - "osm_mad_pool_get failed\n" ); + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "__osm_mcmr_query_mgrp: ERR 1B16: " + "osm_mad_pool_get failed\n" ); for( i = 0; i < num_rec; i++ ) { @@ -2229,9 +2207,7 @@ osm_mcmr_query_mgrp(IN osm_mcmr_recv_t* const p_rcv, cl_qlock_pool_put( &p_rcv->pool, &p_rec_item->pool_item ); } - osm_sa_send_error( p_rcv->p_resp, p_madw, - IB_SA_MAD_STATUS_NO_RESOURCES ); - + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_SA_MAD_STATUS_NO_RESOURCES ); goto Exit; } @@ -2243,9 +2219,9 @@ osm_mcmr_query_mgrp(IN osm_mcmr_recv_t* const p_rcv, Then copy all records from the list into the response payload. */ - cl_memcpy( p_resp_sa_mad, p_rcvd_mad, IB_SA_MAD_HDR_SIZE ); - p_resp_sa_mad->method = (uint8_t)(p_resp_sa_mad->method | 0x80); - /* C15-0.1.5 - always return SM_Key = 0 (table 151 p 782) */ + memcpy( p_resp_sa_mad, p_rcvd_mad, IB_SA_MAD_HDR_SIZE ); + p_resp_sa_mad->method |= IB_MAD_METHOD_RESP_MASK; + /* C15-0.1.5 - always return SM_Key = 0 (table 185 p 884) */ p_resp_sa_mad->sm_key = 0; /* Fill in the offset (paylen will be done by the rmpp SAR) */ @@ -2269,7 +2245,7 @@ osm_mcmr_query_mgrp(IN osm_mcmr_recv_t* const p_rcv, p_resp_rec = (ib_member_rec_t*)ib_sa_mad_get_payload_ptr( p_resp_sa_mad ); /* - p819 - The PortGID, JoinState and ProxyJoin shall be zero, + p923 - The PortGID, JoinState and ProxyJoin shall be zero, except in the case of a trusted request. Note: In the mad controller we check that the SM_Key received on the mad is valid. Meaning - is either zero or equal to the local @@ -2285,7 +2261,7 @@ osm_mcmr_query_mgrp(IN osm_mcmr_recv_t* const p_rcv, *p_resp_rec = p_rec_item->rec; if (trusted_req == FALSE) { - cl_memclr(&p_resp_rec->port_gid, sizeof(ib_gid_t)); + memset(&p_resp_rec->port_gid, 0, sizeof(ib_gid_t)); ib_member_set_join_state(p_resp_rec, 0); p_resp_rec->proxy_join = 0; } @@ -2299,10 +2275,10 @@ osm_mcmr_query_mgrp(IN osm_mcmr_recv_t* const p_rcv, status = osm_vendor_send( p_resp_madw->h_bind, p_resp_madw, FALSE ); if(status != IB_SUCCESS) { - osm_log(p_rcv->p_log, OSM_LOG_ERROR, - "osm_mcmr_query_mgrp: ERR 1B17: " - "osm_vendor_send. status = %s\n", - ib_get_err_str(status)); + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "__osm_mcmr_query_mgrp: ERR 1B17: " + "osm_vendor_send status = %s\n", + ib_get_err_str(status) ); goto Exit; } @@ -2332,6 +2308,8 @@ osm_mcmr_rcv_process( p_recvd_mcmember_rec = (ib_member_rec_t*)ib_sa_mad_get_payload_ptr( p_sa_mad ); + CL_ASSERT( p_sa_mad->attr_id == IB_MAD_ATTR_MCMEMBER_RECORD ); + switch (p_sa_mad->method) { case IB_MAD_METHOD_SET: @@ -2353,14 +2331,14 @@ osm_mcmr_rcv_process( cl_ntoh64( p_recvd_mcmember_rec->port_gid.unicast.prefix ), cl_ntoh64( p_recvd_mcmember_rec->port_gid.unicast.interface_id ) ); - osm_sa_send_error( p_rcv->p_resp, p_madw, sa_status); + osm_sa_send_error( p_rcv->p_resp, p_madw, sa_status ); goto Exit; } /* * Join or Create Multicast Group */ - osm_mcmr_rcv_join_mgrp(p_rcv, p_madw); + __osm_mcmr_rcv_join_mgrp(p_rcv, p_madw); break; case IB_MAD_METHOD_DELETE: valid = __check_join_comp_mask(p_sa_mad->comp_mask); @@ -2371,35 +2349,35 @@ osm_mcmr_rcv_process( "component mask = 0x%016" PRIx64 ", " "expected comp mask = 0x%016" PRIx64 "\n", cl_ntoh64(p_sa_mad->comp_mask), - CL_NTOH64(JOIN_MC_COMP_MASK)); + CL_NTOH64(JOIN_MC_COMP_MASK) ); - osm_sa_send_error( p_rcv->p_resp, p_madw, sa_status); + osm_sa_send_error( p_rcv->p_resp, p_madw, sa_status ); goto Exit; } /* * Leave Multicast Group */ - osm_mcmr_rcv_leave_mgrp(p_rcv, p_madw); + __osm_mcmr_rcv_leave_mgrp(p_rcv, p_madw); break; case IB_MAD_METHOD_GET: case IB_MAD_METHOD_GETTABLE: /* * Querying a Multicast Group */ - osm_mcmr_query_mgrp(p_rcv, p_madw); + __osm_mcmr_query_mgrp(p_rcv, p_madw); break; default: osm_log( p_rcv->p_log, OSM_LOG_ERROR, "osm_mcmr_rcv_process: ERR 1B21: " "Unsupported Method (%s)\n", ib_get_sa_method_str( p_sa_mad->method ) ); - osm_sa_send_error( p_rcv->p_resp, p_madw, sa_status); + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_MAD_STATUS_UNSUP_METHOD_ATTR ); break; } Exit: OSM_LOG_EXIT( p_rcv->p_log ); return; - } + diff --git a/trunk/ulp/opensm/user/opensm/osm_sa_mcmember_record_ctrl.c b/trunk/ulp/opensm/user/opensm/osm_sa_mcmember_record_ctrl.c index fd97c4c2..19285e73 100644 --- a/trunk/ulp/opensm/user/opensm/osm_sa_mcmember_record_ctrl.c +++ b/trunk/ulp/opensm/user/opensm/osm_sa_mcmember_record_ctrl.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Implementation of osm_mcmr_rcv_ctrl_t. @@ -48,7 +49,7 @@ # include #endif /* HAVE_CONFIG_H */ -#include +#include #include #include #include @@ -76,7 +77,7 @@ void osm_mcmr_rcv_ctrl_construct( IN osm_mcmr_rcv_ctrl_t* const p_ctrl ) { - cl_memclr( p_ctrl, sizeof(*p_ctrl) ); + memset( p_ctrl, 0, sizeof(*p_ctrl) ); p_ctrl->h_disp = CL_DISP_INVALID_HANDLE; } @@ -128,3 +129,4 @@ osm_mcmr_rcv_ctrl_init( return( status ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_sa_mft_record.c b/trunk/ulp/opensm/user/opensm/osm_sa_mft_record.c new file mode 100644 index 00000000..5cd6efad --- /dev/null +++ b/trunk/ulp/opensm/user/opensm/osm_sa_mft_record.c @@ -0,0 +1,547 @@ +/* + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. + * + * This software is available to you under the OpenIB.org BSD license + * below: + * + * Redistribution and use in source and binary forms, with or + * without modification, are permitted provided that the following + * conditions are met: + * + * - Redistributions of source code must retain the above + * copyright notice, this list of conditions and the following + * disclaimer. + * + * - Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials + * provided with the distribution. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS + * BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN + * ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN + * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + * + * $Id$ + */ + + +/* + * Abstract: + * Implementation of osm_mftr_rcv_t. + * This object represents the MulticastForwardingTable Receiver object. + * This object is part of the opensm family of objects. + * + * Environment: + * Linux User Mode + * + */ + +#if HAVE_CONFIG_H +# include +#endif /* HAVE_CONFIG_H */ + +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#define OSM_MFTR_RCV_POOL_MIN_SIZE 32 +#define OSM_MFTR_RCV_POOL_GROW_SIZE 32 + +typedef struct _osm_mftr_item +{ + cl_pool_item_t pool_item; + ib_mft_record_t rec; +} osm_mftr_item_t; + +typedef struct _osm_mftr_search_ctxt +{ + const ib_mft_record_t* p_rcvd_rec; + ib_net64_t comp_mask; + cl_qlist_t* p_list; + osm_mftr_rcv_t* p_rcv; + const osm_physp_t* p_req_physp; +} osm_mftr_search_ctxt_t; + +/********************************************************************** + **********************************************************************/ +void +osm_mftr_rcv_construct( + IN osm_mftr_rcv_t* const p_rcv ) +{ + memset( p_rcv, 0, sizeof(*p_rcv) ); + cl_qlock_pool_construct( &p_rcv->pool ); +} + +/********************************************************************** + **********************************************************************/ +void +osm_mftr_rcv_destroy( + IN osm_mftr_rcv_t* const p_rcv ) +{ + OSM_LOG_ENTER( p_rcv->p_log, osm_mftr_rcv_destroy ); + cl_qlock_pool_destroy( &p_rcv->pool ); + OSM_LOG_EXIT( p_rcv->p_log ); +} + +/********************************************************************** + **********************************************************************/ +ib_api_status_t +osm_mftr_rcv_init( + IN osm_mftr_rcv_t* const p_rcv, + IN osm_sa_resp_t* const p_resp, + IN osm_mad_pool_t* const p_mad_pool, + IN osm_subn_t* const p_subn, + IN osm_log_t* const p_log, + IN cl_plock_t* const p_lock ) +{ + ib_api_status_t status; + + OSM_LOG_ENTER( p_log, osm_mftr_rcv_init ); + + osm_mftr_rcv_construct( p_rcv ); + + p_rcv->p_log = p_log; + p_rcv->p_subn = p_subn; + p_rcv->p_lock = p_lock; + p_rcv->p_resp = p_resp; + p_rcv->p_mad_pool = p_mad_pool; + + status = cl_qlock_pool_init( &p_rcv->pool, + OSM_MFTR_RCV_POOL_MIN_SIZE, + 0, + OSM_MFTR_RCV_POOL_GROW_SIZE, + sizeof(osm_mftr_item_t), + NULL, NULL, NULL ); + + OSM_LOG_EXIT( p_log ); + return( status ); +} + +/********************************************************************** + **********************************************************************/ +static ib_api_status_t +__osm_mftr_rcv_new_mftr( + IN osm_mftr_rcv_t* const p_rcv, + IN osm_switch_t* const p_sw, + IN cl_qlist_t* const p_list, + IN ib_net16_t const lid, + IN uint16_t const block, + IN uint8_t const position ) +{ + osm_mftr_item_t* p_rec_item; + ib_api_status_t status = IB_SUCCESS; + uint16_t position_block_num; + + OSM_LOG_ENTER( p_rcv->p_log, __osm_mftr_rcv_new_mftr ); + + p_rec_item = (osm_mftr_item_t*)cl_qlock_pool_get( &p_rcv->pool ); + if( p_rec_item == NULL ) + { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "__osm_mftr_rcv_new_mftr: ERR 4A02: " + "cl_qlock_pool_get failed\n" ); + status = IB_INSUFFICIENT_RESOURCES; + goto Exit; + } + + if( osm_log_is_active( p_rcv->p_log, OSM_LOG_DEBUG ) ) + { + osm_log( p_rcv->p_log, OSM_LOG_DEBUG, + "__osm_mftr_rcv_new_mftr: " + "New MulticastForwardingTable: sw 0x%016" PRIx64 + "\n\t\t\t\tblock %u position %u lid 0x%02X\n", + cl_ntoh64( osm_node_get_node_guid( p_sw->p_node ) ), + block, position, cl_ntoh16( lid ) + ); + } + + position_block_num = ((uint16_t)position << 12) | + (block & IB_MCAST_BLOCK_ID_MASK_HO); + + memset( &p_rec_item->rec, 0, sizeof(ib_mft_record_t) ); + + p_rec_item->rec.lid = lid; + p_rec_item->rec.position_block_num = cl_hton16( position_block_num ); + + /* copy the mft block */ + osm_switch_get_mft_block( p_sw, block, position, p_rec_item->rec.mft ); + + cl_qlist_insert_tail( p_list, (cl_list_item_t*)&p_rec_item->pool_item ); + + Exit: + OSM_LOG_EXIT( p_rcv->p_log ); + return( status ); +} + +/********************************************************************** + **********************************************************************/ +static osm_port_t* +__osm_mftr_get_port_by_guid( + IN osm_mftr_rcv_t* const p_rcv, + IN uint64_t port_guid ) +{ + osm_port_t* p_port; + + CL_PLOCK_ACQUIRE(p_rcv->p_lock); + + p_port = (osm_port_t *)cl_qmap_get(&p_rcv->p_subn->port_guid_tbl, + port_guid); + if (p_port == (osm_port_t *)cl_qmap_end(&p_rcv->p_subn->port_guid_tbl)) + { + osm_log( p_rcv->p_log, OSM_LOG_DEBUG, + "__osm_mftr_get_port_by_guid ERR 4A04: " + "Invalid port GUID 0x%016" PRIx64 "\n", + port_guid ); + p_port = NULL; + } + + CL_PLOCK_RELEASE(p_rcv->p_lock); + return p_port; +} + +/********************************************************************** + **********************************************************************/ +static void +__osm_mftr_rcv_by_comp_mask( + IN cl_map_item_t* const p_map_item, + IN void* context ) +{ + const osm_mftr_search_ctxt_t* const p_ctxt = + (osm_mftr_search_ctxt_t *)context; + osm_switch_t* const p_sw = (osm_switch_t*)p_map_item; + const ib_mft_record_t* const p_rcvd_rec = p_ctxt->p_rcvd_rec; + osm_mftr_rcv_t* const p_rcv = p_ctxt->p_rcv; + ib_net64_t const comp_mask = p_ctxt->comp_mask; + const osm_physp_t* const p_req_physp = p_ctxt->p_req_physp; + osm_port_t* p_port; + uint16_t min_lid_ho, max_lid_ho; + uint16_t position_block_num_ho; + uint16_t min_block, max_block, block; + const osm_physp_t* p_physp; + uint8_t min_position, max_position, position; + + /* In switches, the port guid is the node guid. */ + p_port = + __osm_mftr_get_port_by_guid( p_rcv, p_sw->p_node->node_info.port_guid ); + if (! p_port) + { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "__osm_mftr_rcv_by_comp_mask: ERR 4A05: " + "Failed to find Port by Node Guid:0x%016" PRIx64 + "\n", + cl_ntoh64( p_sw->p_node->node_info.node_guid ) + ); + return; + } + + /* check that the requester physp and the current physp are under + the same partition. */ + p_physp = osm_port_get_default_phys_ptr( p_port ); + if (! p_physp) + { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "__osm_mftr_rcv_by_comp_mask: ERR 4A06: " + "Failed to find default physical Port by Node Guid:0x%016" PRIx64 + "\n", + cl_ntoh64( p_sw->p_node->node_info.node_guid ) + ); + return; + } + if (! osm_physp_share_pkey( p_rcv->p_log, p_req_physp, p_physp )) + return; + + /* get the port 0 of the switch */ + osm_port_get_lid_range_ho( p_port, &min_lid_ho, &max_lid_ho ); + + /* compare the lids - if required */ + if( comp_mask & IB_MFTR_COMPMASK_LID ) + { + osm_log( p_rcv->p_log, OSM_LOG_DEBUG, + "__osm_mftr_rcv_by_comp_mask: " + "Comparing lid:0x%02X to port lid range: 0x%02X .. 0x%02X\n", + cl_ntoh16( p_rcvd_rec->lid ), min_lid_ho, max_lid_ho + ); + /* ok we are ready for range check */ + if (min_lid_ho > cl_ntoh16(p_rcvd_rec->lid) || + max_lid_ho < cl_ntoh16(p_rcvd_rec->lid)) + return; + } + + if ( !osm_switch_supports_mcast ( p_sw ) ) + return; + + /* Are there any blocks in use ? */ + if ( osm_switch_get_mft_max_block_in_use( p_sw ) == -1 ) + return; + + position_block_num_ho = cl_ntoh16( p_rcvd_rec->position_block_num ); + + /* now we need to decide which blocks to output */ + if( comp_mask & IB_MFTR_COMPMASK_BLOCK ) + { + max_block = min_block = position_block_num_ho & IB_MCAST_BLOCK_ID_MASK_HO; + if ( max_block > osm_switch_get_mft_max_block_in_use( p_sw ) ) + return; + } + else + { + /* use as many blocks as needed */ + min_block = 0; + max_block = osm_switch_get_mft_max_block_in_use( p_sw ); + } + + /* need to decide which positions to output */ + if ( comp_mask & IB_MFTR_COMPMASK_POSITION ) + { + min_position = max_position = (position_block_num_ho & 0xF000) >> 12; + if (max_position > osm_switch_get_mft_max_position( p_sw ) ) + return; + } + else + { + /* use as many positions as needed */ + min_position = 0; + max_position = osm_switch_get_mft_max_position( p_sw ); + } + + /* so we can add these one by one ... */ + for (block = min_block; block <= max_block; block++) + for (position = min_position; position <= max_position; position++) + __osm_mftr_rcv_new_mftr( p_rcv, p_sw, p_ctxt->p_list, + osm_port_get_base_lid(p_port), + block, position ); +} + +/********************************************************************** + **********************************************************************/ +void +osm_mftr_rcv_process( + IN osm_mftr_rcv_t* const p_rcv, + IN const osm_madw_t* const p_madw ) +{ + const ib_sa_mad_t* p_rcvd_mad; + const ib_mft_record_t* p_rcvd_rec; + ib_mft_record_t* p_resp_rec; + cl_qlist_t rec_list; + osm_madw_t* p_resp_madw; + ib_sa_mad_t* p_resp_sa_mad; + uint32_t num_rec, pre_trim_num_rec; +#ifndef VENDOR_RMPP_SUPPORT + uint32_t trim_num_rec; +#endif + uint32_t i; + osm_mftr_search_ctxt_t context; + osm_mftr_item_t* p_rec_item; + ib_api_status_t status = IB_SUCCESS; + osm_physp_t* p_req_physp; + + CL_ASSERT( p_rcv ); + + OSM_LOG_ENTER( p_rcv->p_log, osm_mftr_rcv_process ); + + CL_ASSERT( p_madw ); + + p_rcvd_mad = osm_madw_get_sa_mad_ptr( p_madw ); + p_rcvd_rec = (ib_mft_record_t*)ib_sa_mad_get_payload_ptr( p_rcvd_mad ); + + CL_ASSERT( p_rcvd_mad->attr_id == IB_MAD_ATTR_MFT_RECORD ); + + /* we only support SubnAdmGet and SubnAdmGetTable methods */ + if ( (p_rcvd_mad->method != IB_MAD_METHOD_GET) && + (p_rcvd_mad->method != IB_MAD_METHOD_GETTABLE) ) { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "osm_mftr_rcv_process: ERR 4A08: " + "Unsupported Method (%s)\n", + ib_get_sa_method_str( p_rcvd_mad->method ) ); + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_MAD_STATUS_UNSUP_METHOD_ATTR ); + goto Exit; + } + + /* update the requester physical port. */ + p_req_physp = osm_get_physp_by_mad_addr(p_rcv->p_log, + p_rcv->p_subn, + osm_madw_get_mad_addr_ptr(p_madw) ); + if (p_req_physp == NULL) + { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "osm_mftr_rcv_process: ERR 4A07: " + "Cannot find requester physical port\n" ); + goto Exit; + } + + cl_qlist_init( &rec_list ); + + context.p_rcvd_rec = p_rcvd_rec; + context.p_list = &rec_list; + context.comp_mask = p_rcvd_mad->comp_mask; + context.p_rcv = p_rcv; + context.p_req_physp = p_req_physp; + + cl_plock_acquire( p_rcv->p_lock ); + + /* Go over all switches */ + cl_qmap_apply_func( &p_rcv->p_subn->sw_guid_tbl, + __osm_mftr_rcv_by_comp_mask, + &context ); + + cl_plock_release( p_rcv->p_lock ); + + num_rec = cl_qlist_count( &rec_list ); + + /* + * C15-0.1.30: + * If we do a SubnAdmGet and got more than one record it is an error ! + */ + if (p_rcvd_mad->method == IB_MAD_METHOD_GET) + { + if (num_rec == 0) + { + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_SA_MAD_STATUS_NO_RECORDS ); + goto Exit; + } + if (num_rec > 1) + { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "osm_mftr_rcv_process: ERR 4A09: " + "Got more than one record for SubnAdmGet (%u)\n", + num_rec ); + osm_sa_send_error( p_rcv->p_resp, p_madw, + IB_SA_MAD_STATUS_TOO_MANY_RECORDS); + + /* need to set the mem free ... */ + p_rec_item = (osm_mftr_item_t*)cl_qlist_remove_head( &rec_list ); + while( p_rec_item != (osm_mftr_item_t*)cl_qlist_end( &rec_list ) ) + { + cl_qlock_pool_put( &p_rcv->pool, &p_rec_item->pool_item ); + p_rec_item = (osm_mftr_item_t*)cl_qlist_remove_head( &rec_list ); + } + + goto Exit; + } + } + + pre_trim_num_rec = num_rec; +#ifndef VENDOR_RMPP_SUPPORT + /* we limit the number of records to a single packet */ + trim_num_rec = (MAD_BLOCK_SIZE - IB_SA_MAD_HDR_SIZE) / sizeof(ib_mft_record_t); + if (trim_num_rec < num_rec) + { + osm_log( p_rcv->p_log, OSM_LOG_VERBOSE, + "osm_mftr_rcv_process: " + "Number of records:%u trimmed to:%u to fit in one MAD\n", + num_rec, trim_num_rec ); + num_rec = trim_num_rec; + } +#endif + + osm_log( p_rcv->p_log, OSM_LOG_DEBUG, + "osm_mftr_rcv_process: " + "Returning %u records\n", num_rec ); + + if ((p_rcvd_mad->method != IB_MAD_METHOD_GETTABLE) && + (num_rec == 0)) + { + osm_sa_send_error( p_rcv->p_resp, p_madw, + IB_SA_MAD_STATUS_NO_RECORDS ); + goto Exit; + } + + /* + * Get a MAD to reply. Address of Mad is in the received mad_wrapper + */ + p_resp_madw = osm_mad_pool_get( p_rcv->p_mad_pool, + p_madw->h_bind, + num_rec * sizeof(ib_mft_record_t) + IB_SA_MAD_HDR_SIZE, + &p_madw->mad_addr ); + + if( !p_resp_madw ) + { + osm_log(p_rcv->p_log, OSM_LOG_ERROR, + "osm_mftr_rcv_process: ERR 4A10: " + "osm_mad_pool_get failed\n" ); + + for( i = 0; i < num_rec; i++ ) + { + p_rec_item = (osm_mftr_item_t*)cl_qlist_remove_head( &rec_list ); + cl_qlock_pool_put( &p_rcv->pool, &p_rec_item->pool_item ); + } + + osm_sa_send_error( p_rcv->p_resp, p_madw, + IB_SA_MAD_STATUS_NO_RESOURCES ); + + goto Exit; + } + + p_resp_sa_mad = osm_madw_get_sa_mad_ptr( p_resp_madw ); + + /* + Copy the MAD header back into the response mad. + Set the 'R' bit and the payload length, + Then copy all records from the list into the response payload. + */ + + memcpy( p_resp_sa_mad, p_rcvd_mad, IB_SA_MAD_HDR_SIZE ); + p_resp_sa_mad->method |= IB_MAD_METHOD_RESP_MASK; + /* C15-0.1.5 - always return SM_Key = 0 (table 185 p 884) */ + p_resp_sa_mad->sm_key = 0; + /* Fill in the offset (paylen will be done by the rmpp SAR) */ + p_resp_sa_mad->attr_offset = + ib_get_attr_offset( sizeof(ib_mft_record_t) ); + + p_resp_rec = (ib_mft_record_t*)ib_sa_mad_get_payload_ptr( p_resp_sa_mad ); + +#ifndef VENDOR_RMPP_SUPPORT + /* we support only one packet RMPP - so we will set the first and + last flags for gettable */ + if (p_resp_sa_mad->method == IB_MAD_METHOD_GETTABLE_RESP) + { + p_resp_sa_mad->rmpp_type = IB_RMPP_TYPE_DATA; + p_resp_sa_mad->rmpp_flags = IB_RMPP_FLAG_FIRST | IB_RMPP_FLAG_LAST | IB_RMPP_FLAG_ACTIVE; + } +#else + /* forcefully define the packet as RMPP one */ + if (p_resp_sa_mad->method == IB_MAD_METHOD_GETTABLE_RESP) + p_resp_sa_mad->rmpp_flags = IB_RMPP_FLAG_ACTIVE; +#endif + + for( i = 0; i < pre_trim_num_rec; i++ ) + { + p_rec_item = (osm_mftr_item_t*)cl_qlist_remove_head( &rec_list ); + /* copy only if not trimmed */ + if (i < num_rec) + { + *p_resp_rec = p_rec_item->rec; + } + cl_qlock_pool_put( &p_rcv->pool, &p_rec_item->pool_item ); + p_resp_rec++; + } + + CL_ASSERT( cl_is_qlist_empty( &rec_list ) ); + + status = osm_vendor_send( p_resp_madw->h_bind, p_resp_madw, FALSE ); + if (status != IB_SUCCESS) + { + osm_log(p_rcv->p_log, OSM_LOG_ERROR, + "osm_mftr_rcv_process: ERR 4A11: " + "osm_vendor_send status = %s\n", + ib_get_err_str(status)); + goto Exit; + } + + Exit: + OSM_LOG_EXIT( p_rcv->p_log ); +} + diff --git a/trunk/ulp/opensm/user/opensm/osm_sa_mft_record_ctrl.c b/trunk/ulp/opensm/user/opensm/osm_sa_mft_record_ctrl.c new file mode 100644 index 00000000..3c0c39c7 --- /dev/null +++ b/trunk/ulp/opensm/user/opensm/osm_sa_mft_record_ctrl.c @@ -0,0 +1,123 @@ +/* + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. + * + * This software is available to you under the OpenIB.org BSD license + * below: + * + * Redistribution and use in source and binary forms, with or + * without modification, are permitted provided that the following + * conditions are met: + * + * - Redistributions of source code must retain the above + * copyright notice, this list of conditions and the following + * disclaimer. + * + * - Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials + * provided with the distribution. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS + * BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN + * ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN + * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + * + * $Id$ + */ + + +/* + * Abstract: + * Implementation of osm_mftr_rcv_ctrl_t. + * This object represents the MulticastForwardingTable request controller object. + * This object is part of the opensm family of objects. + * + * Environment: + * Linux User Mode + * + */ + +#if HAVE_CONFIG_H +# include +#endif /* HAVE_CONFIG_H */ + +#include +#include +#include + +/********************************************************************** + **********************************************************************/ +void +__osm_mftr_rcv_ctrl_disp_callback( + IN void *context, + IN void *p_data ) +{ + /* ignore return status when invoked via the dispatcher */ + osm_mftr_rcv_process( ((osm_mftr_rcv_ctrl_t*)context)->p_rcv, + (osm_madw_t*)p_data ); +} + +/********************************************************************** + **********************************************************************/ +void +osm_mftr_rcv_ctrl_construct( + IN osm_mftr_rcv_ctrl_t* const p_ctrl ) +{ + memset( p_ctrl, 0, sizeof(*p_ctrl) ); + p_ctrl->h_disp = CL_DISP_INVALID_HANDLE; +} + +/********************************************************************** + **********************************************************************/ +void +osm_mftr_rcv_ctrl_destroy( + IN osm_mftr_rcv_ctrl_t* const p_ctrl ) +{ + CL_ASSERT( p_ctrl ); + cl_disp_unregister( p_ctrl->h_disp ); +} + +/********************************************************************** + **********************************************************************/ +ib_api_status_t +osm_mftr_rcv_ctrl_init( + IN osm_mftr_rcv_ctrl_t* const p_ctrl, + IN osm_mftr_rcv_t* const p_rcv, + IN osm_log_t* const p_log, + IN cl_dispatcher_t* const p_disp ) +{ + ib_api_status_t status = IB_SUCCESS; + + OSM_LOG_ENTER( p_log, osm_mftr_rcv_ctrl_init ); + + osm_mftr_rcv_ctrl_construct( p_ctrl ); + p_ctrl->p_log = p_log; + p_ctrl->p_rcv = p_rcv; + p_ctrl->p_disp = p_disp; + + p_ctrl->h_disp = cl_disp_register( + p_disp, + OSM_MSG_MAD_MFT_RECORD, + __osm_mftr_rcv_ctrl_disp_callback, + p_ctrl ); + + if( p_ctrl->h_disp == CL_DISP_INVALID_HANDLE ) + { + osm_log( p_log, OSM_LOG_ERROR, + "osm_mftr_rcv_ctrl_init: ERR 4A01: " + "Dispatcher registration failed\n" ); + status = IB_INSUFFICIENT_RESOURCES; + goto Exit; + } + + Exit: + OSM_LOG_EXIT( p_log ); + return( status ); +} + diff --git a/trunk/ulp/opensm/user/opensm/osm_sa_multipath_record.c b/trunk/ulp/opensm/user/opensm/osm_sa_multipath_record.c new file mode 100644 index 00000000..83404e0b --- /dev/null +++ b/trunk/ulp/opensm/user/opensm/osm_sa_multipath_record.c @@ -0,0 +1,1652 @@ +/* + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. + * + * This software is available to you under the OpenIB.org BSD license + * below: + * + * Redistribution and use in source and binary forms, with or + * without modification, are permitted provided that the following + * conditions are met: + * + * - Redistributions of source code must retain the above + * copyright notice, this list of conditions and the following + * disclaimer. + * + * - Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials + * provided with the distribution. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS + * BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN + * ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN + * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + * + * $Id$ + */ + + +/* + * Abstract: + * Implementation of osm_mpr_rcv_t. + * This object represents the MultiPath Record Receiver object. + * This object is part of the opensm family of objects. + * + * Environment: + * Linux User Mode + * + */ + +#if defined (VENDOR_RMPP_SUPPORT) && defined (DUAL_SIDED_RMPP) + +#if HAVE_CONFIG_H +# include +#endif /* HAVE_CONFIG_H */ + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#define OSM_MPR_RCV_POOL_MIN_SIZE 64 +#define OSM_MPR_RCV_POOL_GROW_SIZE 64 + +#define OSM_SA_MPR_MAX_NUM_PATH 127 + +typedef struct _osm_mpr_item +{ + cl_pool_item_t pool_item; + const osm_port_t *p_src_port; + const osm_port_t *p_dest_port; + int hops; + ib_path_rec_t path_rec; +} osm_mpr_item_t; + +typedef struct _osm_path_parms +{ + ib_net16_t pkey; + uint8_t mtu; + uint8_t rate; + uint8_t sl; + uint8_t pkt_life; + boolean_t reversible; + int hops; +} osm_path_parms_t; + +/********************************************************************** + **********************************************************************/ +void +osm_mpr_rcv_construct( + IN osm_mpr_rcv_t* const p_rcv ) +{ + memset( p_rcv, 0, sizeof(*p_rcv) ); + cl_qlock_pool_construct( &p_rcv->pr_pool ); +} + +/********************************************************************** + **********************************************************************/ +void +osm_mpr_rcv_destroy( + IN osm_mpr_rcv_t* const p_rcv ) +{ + OSM_LOG_ENTER( p_rcv->p_log, osm_mpr_rcv_destroy ); + cl_qlock_pool_destroy( &p_rcv->pr_pool ); + OSM_LOG_EXIT( p_rcv->p_log ); +} + +/********************************************************************** + **********************************************************************/ +ib_api_status_t +osm_mpr_rcv_init( + IN osm_mpr_rcv_t* const p_rcv, + IN osm_sa_resp_t* const p_resp, + IN osm_mad_pool_t* const p_mad_pool, + IN osm_subn_t* const p_subn, + IN osm_log_t* const p_log, + IN cl_plock_t* const p_lock ) +{ + ib_api_status_t status; + + OSM_LOG_ENTER( p_log, osm_mpr_rcv_init ); + + osm_mpr_rcv_construct( p_rcv ); + + p_rcv->p_log = p_log; + p_rcv->p_subn = p_subn; + p_rcv->p_lock = p_lock; + p_rcv->p_resp = p_resp; + p_rcv->p_mad_pool = p_mad_pool; + + status = cl_qlock_pool_init( &p_rcv->pr_pool, + OSM_MPR_RCV_POOL_MIN_SIZE, + 0, + OSM_MPR_RCV_POOL_GROW_SIZE, + sizeof(osm_mpr_item_t), + NULL, NULL, NULL ); + + OSM_LOG_EXIT( p_rcv->p_log ); + return( status ); +} + +/********************************************************************** + **********************************************************************/ +static inline boolean_t +__osm_sa_multipath_rec_is_tavor_port( + IN const osm_port_t* const p_port) +{ + osm_node_t const* p_node; + ib_net32_t vend_id; + + p_node = osm_port_get_parent_node( p_port ); + vend_id = ib_node_info_get_vendor_id( &p_node->node_info ); + + return( (p_node->node_info.device_id == CL_HTON16(23108)) && + ((vend_id == CL_HTON32(OSM_VENDOR_ID_MELLANOX)) || + (vend_id == CL_HTON32(OSM_VENDOR_ID_TOPSPIN)) || + (vend_id == CL_HTON32(OSM_VENDOR_ID_SILVERSTORM)) || + (vend_id == CL_HTON32(OSM_VENDOR_ID_VOLTAIRE))) ); +} + +/********************************************************************** + **********************************************************************/ +boolean_t + __osm_sa_multipath_rec_apply_tavor_mtu_limit( + IN const ib_multipath_rec_t* const p_mpr, + IN const osm_port_t* const p_src_port, + IN const osm_port_t* const p_dest_port, + IN const ib_net64_t comp_mask) +{ + uint8_t required_mtu; + + /* only if at least one of the ports is a Tavor device */ + if (! __osm_sa_multipath_rec_is_tavor_port(p_src_port) && + ! __osm_sa_multipath_rec_is_tavor_port(p_dest_port) ) + return( FALSE ); + + /* + we can apply the patch if either: + 1. No MTU required + 2. Required MTU < + 3. Required MTU = 1K or 512 or 256 + 4. Required MTU > 256 or 512 + */ + required_mtu = ib_multipath_rec_mtu( p_mpr ); + if ( ( comp_mask & IB_MPR_COMPMASK_MTUSELEC ) && + ( comp_mask & IB_PR_COMPMASK_MTU ) ) + { + switch( ib_multipath_rec_mtu_sel( p_mpr ) ) + { + case 0: /* must be greater than */ + case 2: /* exact match */ + if( IB_MTU_LEN_1024 < required_mtu ) + return(FALSE); + break; + + case 1: /* must be less than */ + /* can't be disqualified by this one */ + break; + + case 3: /* largest available */ + /* the ULP intentionally requested */ + /* the largest MTU possible */ + return(FALSE); + break; + + default: + /* if we're here, there's a bug in ib_multipath_rec_mtu_sel() */ + CL_ASSERT( FALSE ); + break; + } + } + + return(TRUE); +} + +/********************************************************************** + **********************************************************************/ +static ib_api_status_t +__osm_mpr_rcv_get_path_parms( + IN osm_mpr_rcv_t* const p_rcv, + IN const ib_multipath_rec_t* const p_mpr, + IN const osm_port_t* const p_src_port, + IN const osm_port_t* const p_dest_port, + IN const uint16_t dest_lid_ho, + IN const ib_net64_t comp_mask, + OUT osm_path_parms_t* const p_parms ) +{ + const osm_node_t* p_node; + const osm_physp_t* p_physp; + const osm_physp_t* p_dest_physp; + const osm_prtn_t* p_prtn; + const ib_port_info_t* p_pi; + ib_slvl_table_t* p_slvl_tbl; + ib_api_status_t status = IB_SUCCESS; + uint8_t mtu; + uint8_t rate; + uint8_t pkt_life; + uint8_t required_mtu; + uint8_t required_rate; + uint16_t required_pkey; + uint8_t required_sl; + uint8_t required_pkt_life; + ib_net16_t dest_lid; + int hops = 0; + int in_port_num = 0; + uint8_t vl; + + OSM_LOG_ENTER( p_rcv->p_log, __osm_mpr_rcv_get_path_parms ); + + dest_lid = cl_hton16( dest_lid_ho ); + + p_dest_physp = osm_port_get_default_phys_ptr( p_dest_port ); + p_physp = osm_port_get_default_phys_ptr( p_src_port ); + p_pi = osm_physp_get_port_info_ptr( p_physp ); + + mtu = ib_port_info_get_mtu_cap( p_pi ); + rate = ib_port_info_compute_rate( p_pi ); + + /* + Mellanox Tavor device performance is better using 1K MTU. + If required MTU and MTU selector are such that 1K is OK + and at least one end of the path is Tavor we override the + port MTU with 1K. + */ + if ( p_rcv->p_subn->opt.enable_quirks && + __osm_sa_multipath_rec_apply_tavor_mtu_limit( + p_mpr, p_src_port, p_dest_port, comp_mask) ) + if (mtu > IB_MTU_LEN_1024) + { + mtu = IB_MTU_LEN_1024; + osm_log( p_rcv->p_log, OSM_LOG_DEBUG, + "__osm_mpr_rcv_get_path_parms: " + "Optimized Path MTU to 1K for Mellanox Tavor device\n"); + } + + if ( comp_mask & IB_MPR_COMPMASK_RAWTRAFFIC && + cl_ntoh32( p_mpr->hop_flow_raw ) & ( 1<<31 ) ) + required_pkey = osm_physp_find_common_pkey( p_physp, p_dest_physp ); + else if ( comp_mask & IB_MPR_COMPMASK_PKEY ) { + required_pkey = p_mpr->pkey; + if( !osm_physp_share_this_pkey( p_physp, p_dest_physp, required_pkey ) ) { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "__osm_mpr_rcv_get_path_parms: ERR 4518: " + "Ports do not share specified PKey 0x%04x\n" + "\t\tsrc %" PRIx64 " dst %" PRIx64 "\n", + cl_ntoh16( required_pkey ), + cl_ntoh64( osm_physp_get_port_guid( p_physp ) ), + cl_ntoh64( osm_physp_get_port_guid( p_dest_physp ) ) ); + status = IB_NOT_FOUND; + goto Exit; + } + } else { + required_pkey = osm_physp_find_common_pkey( p_physp, p_dest_physp ); + if ( !required_pkey ) { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "__osm_mpr_rcv_get_path_parms: ERR 4519: " + "Ports do not have any shared PKeys\n" + "\t\tsrc %" PRIx64 " dst %" PRIx64 "\n", + cl_ntoh64( osm_physp_get_port_guid( p_physp ) ), + cl_ntoh64( osm_physp_get_port_guid( p_dest_physp ) ) ); + status = IB_NOT_FOUND; + goto Exit; + } + } + + required_sl = OSM_DEFAULT_SL; + + if (required_pkey) { + p_prtn = (osm_prtn_t *)cl_qmap_get(&p_rcv->p_subn->prtn_pkey_tbl, + required_pkey & cl_ntoh16((uint16_t)~0x8000)); + if ( p_prtn == (osm_prtn_t *)cl_qmap_end(&p_rcv->p_subn->prtn_pkey_tbl) ) + { + /* this may be possible when pkey tables are created somehow in + previous runs or things are going wrong here */ + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "__osm_mpr_rcv_get_path_parms: ERR 451A: " + "No partition found for PKey 0x%04x - using default SL %d\n", cl_ntoh16(required_pkey), required_sl ); + } + else + required_sl = p_prtn->sl; + + /* reset pkey when raw traffic */ + if( comp_mask & IB_PR_COMPMASK_RAWTRAFFIC && + cl_ntoh32( p_mpr->hop_flow_raw ) & ( 1<<31 ) ) + required_pkey = 0; + } + + if ( ( comp_mask & IB_MPR_COMPMASK_SL ) && ib_multipath_rec_sl( p_mpr ) != required_sl ) + { + status = IB_NOT_FOUND; + goto Exit; + } + + /* + Walk the subnet object from source to destination, + tracking the most restrictive rate and mtu values along the way... + + If source port node is a switch, then p_physp should + point to the port that routes the destination lid + */ + + p_node = osm_physp_get_node_ptr( p_physp ); + + if ( p_node->sw ) + { + + /* + * If the dest_lid_ho is equal to the lid of the switch pointed by + * p_sw then p_physp will be the physical port of the switch port zero. + */ + p_physp = osm_switch_get_route_by_lid( p_node->sw, cl_ntoh16( dest_lid_ho ) ); + if ( p_physp == 0 ) + { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "__osm_mpr_rcv_get_path_parms: ERR 4514: " + "Can't find routing to LID 0x%X from switch for GUID 0x%016" PRIx64 "\n", + dest_lid_ho, + cl_ntoh64( osm_node_get_node_guid( p_node ) ) ); + status = IB_ERROR; + goto Exit; + } + } + + /* + * Same as above + */ + p_node = osm_physp_get_node_ptr( p_dest_physp ); + + if ( p_node->sw ) + { + + p_dest_physp = osm_switch_get_route_by_lid( p_node->sw, cl_ntoh16( dest_lid_ho ) ); + + if ( p_dest_physp == 0 ) + { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "__osm_mpr_rcv_get_path_parms: ERR 4515: " + "Can't find routing to LID 0x%X from switch for GUID 0x%016" PRIx64 "\n", + dest_lid_ho, + cl_ntoh64( osm_node_get_node_guid( p_node ) ) ); + status = IB_ERROR; + goto Exit; + } + + } + + while ( p_physp != p_dest_physp ) + { + p_physp = osm_physp_get_remote( p_physp ); + + if ( p_physp == 0 ) + { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "__osm_mpr_rcv_get_path_parms: ERR 4505: " + "Can't find remote phys port when routing to LID 0x%X from node GUID 0x%016" PRIx64 "\n", + dest_lid_ho, + cl_ntoh64( osm_node_get_node_guid( p_node ) ) ); + status = IB_ERROR; + goto Exit; + } + + hops++; + + /* + This is point to point case (no switch in between) + */ + if ( p_physp == p_dest_physp ) + break; + + p_node = osm_physp_get_node_ptr( p_physp ); + + if ( !p_node->sw ) + { + /* + There is some sort of problem in the subnet object! + If this isn't a switch, we should have reached + the destination by now! + */ + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "__osm_mpr_rcv_get_path_parms: ERR 4503: " + "Internal error, bad path\n" ); + status = IB_ERROR; + goto Exit; + } + + /* + Check parameters for the ingress port in this switch. + */ + p_pi = osm_physp_get_port_info_ptr( p_physp ); + + if ( mtu > ib_port_info_get_mtu_cap( p_pi ) ) + { + mtu = ib_port_info_get_mtu_cap( p_pi ); + if ( osm_log_is_active( p_rcv->p_log, OSM_LOG_DEBUG ) ) + { + osm_log( p_rcv->p_log, OSM_LOG_DEBUG, + "__osm_mpr_rcv_get_path_parms: " + "New smallest MTU = %u at intervening port 0x%016" PRIx64 + " port num 0x%X\n", + mtu, + cl_ntoh64( osm_physp_get_port_guid( p_physp ) ), + osm_physp_get_port_num( p_physp ) ); + } + } + + if ( rate > ib_port_info_compute_rate( p_pi ) ) + { + rate = ib_port_info_compute_rate( p_pi ); + if ( osm_log_is_active( p_rcv->p_log, OSM_LOG_DEBUG ) ) + { + osm_log( p_rcv->p_log, OSM_LOG_DEBUG, + "__osm_mpr_rcv_get_path_parms: " + "New smallest rate = %u at intervening port 0x%016" PRIx64 + " port num 0x%X\n", + rate, + cl_ntoh64( osm_physp_get_port_guid( p_physp ) ), + osm_physp_get_port_num( p_physp ) ); + } + } + + /* + Continue with the egress port on this switch. + */ + p_physp = osm_switch_get_route_by_lid( p_node->sw, dest_lid ); + + if ( p_physp == 0 ) + { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "__osm_mpr_rcv_get_path_parms: ERR 4516: " + "Dead end on path to LID 0x%X from switch for GUID 0x%016" PRIx64 "\n", + dest_lid_ho, + cl_ntoh64( osm_node_get_node_guid( p_node ) ) ); + status = IB_ERROR; + goto Exit; + } + + CL_ASSERT( p_physp ); + CL_ASSERT( osm_physp_is_valid( p_physp ) ); + + if ( comp_mask & IB_MPR_COMPMASK_SL ) { + in_port_num = osm_physp_get_port_num( p_physp ); + p_slvl_tbl = osm_physp_get_slvl_tbl( p_physp, in_port_num ); + vl = ib_slvl_table_get( p_slvl_tbl, required_sl ); + if (vl == IB_DROP_VL) { /* discard packet */ + osm_log( p_rcv->p_log, OSM_LOG_VERBOSE, + "__osm_mpr_rcv_get_path_parms: Path not found for SL %d\n" + "\t\tin_port_num %d port_guid %" PRIx64 "\n", + required_sl, in_port_num, + cl_ntoh64( osm_physp_get_port_guid( p_physp ) ) ); + status = IB_NOT_FOUND; + goto Exit; + } + } + + p_pi = osm_physp_get_port_info_ptr( p_physp ); + + if ( mtu > ib_port_info_get_mtu_cap( p_pi ) ) + { + mtu = ib_port_info_get_mtu_cap( p_pi ); + if ( osm_log_is_active( p_rcv->p_log, OSM_LOG_DEBUG ) ) + { + osm_log( p_rcv->p_log, OSM_LOG_DEBUG, + "__osm_mpr_rcv_get_path_parms: " + "New smallest MTU = %u at intervening port 0x%016" PRIx64 + " port num 0x%X\n", + mtu, + cl_ntoh64( osm_physp_get_port_guid( p_physp ) ), + osm_physp_get_port_num( p_physp ) ); + } + } + + if ( rate > ib_port_info_compute_rate( p_pi ) ) + { + rate = ib_port_info_compute_rate( p_pi ); + if ( osm_log_is_active( p_rcv->p_log, OSM_LOG_DEBUG ) ) + { + osm_log( p_rcv->p_log, OSM_LOG_DEBUG, + "__osm_mpr_rcv_get_path_parms: " + "New smallest rate = %u at intervening port 0x%016" PRIx64 + " port num 0x%X\n", + rate, + cl_ntoh64( osm_physp_get_port_guid( p_physp ) ), + osm_physp_get_port_num( p_physp ) ); + } + } + + } + + /* + p_physp now points to the destination + */ + p_pi = osm_physp_get_port_info_ptr( p_physp ); + + if ( mtu > ib_port_info_get_mtu_cap( p_pi ) ) + { + mtu = ib_port_info_get_mtu_cap( p_pi ); + if ( osm_log_is_active( p_rcv->p_log, OSM_LOG_DEBUG ) ) + { + osm_log( p_rcv->p_log, OSM_LOG_DEBUG, + "__osm_mpr_rcv_get_path_parms: " + "New smallest MTU = %u at destination port 0x%016" PRIx64 "\n", + mtu, + cl_ntoh64( osm_physp_get_port_guid( p_physp ) ) ); + } + } + + if ( rate > ib_port_info_compute_rate( p_pi ) ) + { + rate = ib_port_info_compute_rate( p_pi ); + if ( osm_log_is_active( p_rcv->p_log, OSM_LOG_DEBUG ) ) + { + osm_log( p_rcv->p_log, OSM_LOG_DEBUG, + "__osm_mpr_rcv_get_path_parms: " + "New smallest rate = %u at destination port 0x%016" PRIx64 "\n", + rate, + cl_ntoh64( osm_physp_get_port_guid( p_physp ) ) ); + } + } + + if ( osm_log_is_active( p_rcv->p_log, OSM_LOG_DEBUG ) ) + { + osm_log( p_rcv->p_log, OSM_LOG_DEBUG, + "__osm_mpr_rcv_get_path_parms: " + "Path min MTU = %u, min rate = %u\n", mtu, rate ); + } + + /* + Determine if these values meet the user criteria + */ + + /* we silently ignore cases where only the MTU selector is defined */ + if ( ( comp_mask & IB_MPR_COMPMASK_MTUSELEC ) && + ( comp_mask & IB_MPR_COMPMASK_MTU ) ) + { + required_mtu = ib_multipath_rec_mtu( p_mpr ); + switch ( ib_multipath_rec_mtu_sel( p_mpr ) ) + { + case 0: /* must be greater than */ + if ( mtu <= required_mtu ) + status = IB_NOT_FOUND; + break; + + case 1: /* must be less than */ + if ( mtu >= required_mtu ) + { + /* adjust to use the highest mtu + lower then the required one */ + if ( required_mtu > 1 ) + mtu = required_mtu - 1; + else + status = IB_NOT_FOUND; + } + break; + + case 2: /* exact match */ + if ( mtu < required_mtu ) + status = IB_NOT_FOUND; + else + mtu = required_mtu; + break; + + case 3: /* largest available */ + /* can't be disqualified by this one */ + break; + + default: + /* if we're here, there's a bug in ib_multipath_rec_mtu_sel() */ + CL_ASSERT( FALSE ); + status = IB_ERROR; + break; + } + } + + /* we silently ignore cases where only the Rate selector is defined */ + if ( ( comp_mask & IB_MPR_COMPMASK_RATESELEC ) && + ( comp_mask & IB_PR_COMPMASK_RATE ) ) + { + required_rate = ib_multipath_rec_rate( p_mpr ); + switch ( ib_multipath_rec_rate_sel( p_mpr ) ) + { + case 0: /* must be greater than */ + if ( rate <= required_rate ) + status = IB_NOT_FOUND; + break; + + case 1: /* must be less than */ + if ( rate >= required_rate ) + { + /* adjust the rate to use the highest rate + lower then the required one */ + if ( required_rate > 2 ) + rate = required_rate - 1; + else + status = IB_NOT_FOUND; + } + break; + + case 2: /* exact match */ + if ( rate < required_rate ) + status = IB_NOT_FOUND; + else + rate = required_rate; + break; + + case 3: /* largest available */ + /* can't be disqualified by this one */ + break; + + default: + /* if we're here, there's a bug in ib_multipath_rec_mtu_sel() */ + CL_ASSERT( FALSE ); + status = IB_ERROR; + break; + } + } + + /* Verify the pkt_life_time */ + /* According to spec definition IBA 1.2 Table 205 PacketLifeTime description, + for loopback paths, packetLifeTime shall be zero. */ + if ( p_src_port == p_dest_port ) + pkt_life = 0; /* loopback */ + else + pkt_life = OSM_DEFAULT_SUBNET_TIMEOUT; + + /* we silently ignore cases where only the PktLife selector is defined */ + if ( ( comp_mask & IB_MPR_COMPMASK_PKTLIFETIMESELEC ) && + ( comp_mask & IB_MPR_COMPMASK_PKTLIFETIME ) ) + { + required_pkt_life = ib_multipath_rec_pkt_life( p_mpr ); + switch ( ib_multipath_rec_pkt_life_sel( p_mpr ) ) + { + case 0: /* must be greater than */ + if ( pkt_life <= required_pkt_life ) + status = IB_NOT_FOUND; + break; + + case 1: /* must be less than */ + if ( pkt_life >= required_pkt_life ) + { + /* adjust the lifetime to use the highest possible + lower then the required one */ + if ( required_pkt_life > 1 ) + pkt_life = required_pkt_life - 1; + else + status = IB_NOT_FOUND; + } + break; + + case 2: /* exact match */ + if ( pkt_life < required_pkt_life ) + status = IB_NOT_FOUND; + else + pkt_life = required_pkt_life; + break; + + case 3: /* smallest available */ + /* can't be disqualified by this one */ + break; + + default: + /* if we're here, there's a bug in ib_path_rec_pkt_life_sel() */ + CL_ASSERT( FALSE ); + status = IB_ERROR; + break; + } + } + + if (status != IB_SUCCESS) + goto Exit; + + p_parms->mtu = mtu; + p_parms->rate = rate; + p_parms->pkey = required_pkey; + p_parms->pkt_life = pkt_life; + p_parms->sl = required_sl; + p_parms->hops = hops; + + Exit: + OSM_LOG_EXIT( p_rcv->p_log ); + return( status ); +} + +/********************************************************************** + **********************************************************************/ +static void +__osm_mpr_rcv_build_pr( + IN osm_mpr_rcv_t* const p_rcv, + IN const osm_port_t* const p_src_port, + IN const osm_port_t* const p_dest_port, + IN const uint16_t src_lid_ho, + IN const uint16_t dest_lid_ho, + IN const uint8_t preference, + IN const osm_path_parms_t* const p_parms, + OUT ib_path_rec_t* const p_pr ) +{ + const osm_physp_t* p_src_physp; + const osm_physp_t* p_dest_physp; + + OSM_LOG_ENTER( p_rcv->p_log, __osm_mpr_rcv_build_pr ); + + p_src_physp = osm_port_get_default_phys_ptr( p_src_port ); + p_dest_physp = osm_port_get_default_phys_ptr( p_dest_port ); + + p_pr->dgid.unicast.prefix = osm_physp_get_subnet_prefix( p_dest_physp ); + p_pr->dgid.unicast.interface_id = osm_physp_get_port_guid( p_dest_physp ); + + p_pr->sgid.unicast.prefix = osm_physp_get_subnet_prefix( p_src_physp ); + p_pr->sgid.unicast.interface_id = osm_physp_get_port_guid( p_src_physp ); + + p_pr->dlid = cl_hton16( dest_lid_ho ); + p_pr->slid = cl_hton16( src_lid_ho ); + + p_pr->hop_flow_raw &= cl_hton32(1<<31); + + p_pr->pkey = p_parms->pkey; + p_pr->sl = cl_hton16( p_parms->sl ); + p_pr->mtu = (uint8_t)( p_parms->mtu | 0x80 ); + p_pr->rate = (uint8_t)( p_parms->rate | 0x80 ); + + /* According to 1.2 spec definition Table 205 PacketLifeTime description, + for loopback paths, packetLifeTime shall be zero. */ + if ( p_src_port == p_dest_port ) + p_pr->pkt_life = 0x80; /* loopback */ + else + p_pr->pkt_life = (uint8_t)( p_parms->pkt_life | 0x80 ); + + p_pr->preference = preference; + + /* always return num_path = 0 so this is only the reversible component */ + if ( p_parms->reversible ) + p_pr->num_path = 0x80; + + OSM_LOG_EXIT( p_rcv->p_log ); +} + +/********************************************************************** + **********************************************************************/ +static osm_mpr_item_t* +__osm_mpr_rcv_get_lid_pair_path( + IN osm_mpr_rcv_t* const p_rcv, + IN const ib_multipath_rec_t* const p_mpr, + IN const osm_port_t* const p_src_port, + IN const osm_port_t* const p_dest_port, + IN const uint16_t src_lid_ho, + IN const uint16_t dest_lid_ho, + IN const ib_net64_t comp_mask, + IN const uint8_t preference ) +{ + osm_path_parms_t path_parms; + osm_path_parms_t rev_path_parms; + osm_mpr_item_t *p_pr_item; + ib_api_status_t status, rev_path_status; + + OSM_LOG_ENTER( p_rcv->p_log, __osm_mpr_rcv_get_lid_pair_path ); + + if ( osm_log_is_active( p_rcv->p_log, OSM_LOG_DEBUG ) ) + { + osm_log( p_rcv->p_log, OSM_LOG_DEBUG, + "__osm_mpr_rcv_get_lid_pair_path: " + "Src LID 0x%X, Dest LID 0x%X\n", + src_lid_ho, dest_lid_ho ); + } + + p_pr_item = (osm_mpr_item_t*)cl_qlock_pool_get( &p_rcv->pr_pool ); + if ( p_pr_item == NULL ) + { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "__osm_mpr_rcv_get_lid_pair_path: ERR 4501: " + "Unable to allocate path record\n" ); + goto Exit; + } + + status = __osm_mpr_rcv_get_path_parms( p_rcv, p_mpr, p_src_port, + p_dest_port, dest_lid_ho, + comp_mask, &path_parms ); + + if ( status != IB_SUCCESS ) + { + cl_qlock_pool_put( &p_rcv->pr_pool, &p_pr_item->pool_item ); + p_pr_item = NULL; + goto Exit; + } + + /* now try the reversible path */ + rev_path_status = __osm_mpr_rcv_get_path_parms( p_rcv, p_mpr, p_dest_port, + p_src_port, src_lid_ho, + comp_mask, &rev_path_parms ); + path_parms.reversible = ( rev_path_status == IB_SUCCESS ); + + /* did we get a Reversible Path compmask ? */ + /* + NOTE that if the reversible component = 0, it is a don't care + rather then requiring non-reversible paths ... + see Vol1 Ver1.2 p900 l16 + */ + if ( comp_mask & IB_MPR_COMPMASK_REVERSIBLE ) + { + if ( (! path_parms.reversible && ( p_mpr->num_path & 0x80 ) ) ) + { + osm_log( p_rcv->p_log, OSM_LOG_DEBUG, + "__osm_mpr_rcv_get_lid_pair_path: " + "Requested reversible path but failed to get one\n"); + + cl_qlock_pool_put( &p_rcv->pr_pool, &p_pr_item->pool_item ); + p_pr_item = NULL; + goto Exit; + } + } + + p_pr_item->p_src_port = p_src_port; + p_pr_item->p_dest_port = p_dest_port; + p_pr_item->hops = path_parms.hops; + + __osm_mpr_rcv_build_pr( p_rcv, p_src_port, p_dest_port, src_lid_ho, + dest_lid_ho, preference, &path_parms, + &p_pr_item->path_rec ); + + Exit: + OSM_LOG_EXIT( p_rcv->p_log ); + return( p_pr_item ); +} + +/********************************************************************** + **********************************************************************/ +static uint32_t +__osm_mpr_rcv_get_port_pair_paths( + IN osm_mpr_rcv_t* const p_rcv, + IN const ib_multipath_rec_t* const p_mpr, + IN const osm_port_t* const p_req_port, + IN const osm_port_t* const p_src_port, + IN const osm_port_t* const p_dest_port, + IN const uint32_t rem_paths, + IN const ib_net64_t comp_mask, + IN cl_qlist_t* const p_list ) +{ + osm_mpr_item_t* p_pr_item; + uint16_t src_lid_min_ho; + uint16_t src_lid_max_ho; + uint16_t dest_lid_min_ho; + uint16_t dest_lid_max_ho; + uint16_t src_lid_ho; + uint16_t dest_lid_ho; + uint32_t path_num = 0; + uint8_t preference; + uintn_t src_offset; + uintn_t dest_offset; + + OSM_LOG_ENTER( p_rcv->p_log, __osm_mpr_rcv_get_port_pair_paths ); + + if ( osm_log_is_active( p_rcv->p_log, OSM_LOG_DEBUG ) ) + { + osm_log( p_rcv->p_log, OSM_LOG_DEBUG, + "__osm_mpr_rcv_get_port_pair_paths: " + "Src port 0x%016" PRIx64 ", " + "Dst port 0x%016" PRIx64 "\n", + cl_ntoh64( osm_port_get_guid( p_src_port ) ), + cl_ntoh64( osm_port_get_guid( p_dest_port ) ) ); + } + + /* Check that the req_port, src_port and dest_port all share a + pkey. The check is done on the default physical port of the ports. */ + if ( osm_port_share_pkey(p_rcv->p_log, p_req_port, p_src_port ) == FALSE || + osm_port_share_pkey(p_rcv->p_log, p_req_port, p_dest_port ) == FALSE || + osm_port_share_pkey(p_rcv->p_log, p_src_port, p_dest_port ) == FALSE ) + { + /* One of the pairs doesn't share a pkey so the path is disqualified. */ + goto Exit; + } + + /* + We shouldn't be here if the paths are disqualified in some way... + Thus, we assume every possible connection is valid. + + We desire to return high-quality paths first. + In OpenSM, higher quality mean least overlap with other paths. + This is acheived in practice by returning paths with + different LID value on each end, which means these + paths are more redundant that paths with the same LID repeated + on one side. For example, in OpenSM the paths between two + endpoints with LMC = 1 might be as follows: + + Port A, LID 1 <-> Port B, LID 3 + Port A, LID 1 <-> Port B, LID 4 + Port A, LID 2 <-> Port B, LID 3 + Port A, LID 2 <-> Port B, LID 4 + + The OpenSM unicast routing algorithms attempt to disperse each path + to as varied a physical path as is reasonable. 1<->3 and 1<->4 have + more physical overlap (hence less redundancy) than 1<->3 and 2<->4. + + OpenSM ranks paths in three preference groups: + + Preference Value Description + ---------------- ------------------------------------------- + 0 Redundant in both directions with other + pref value = 0 paths + + 1 Redundant in one direction with other + pref value = 0 and pref value = 1 paths + + 2 Not redundant in either direction with + other paths + + 3-FF Unused + + + SA clients don't need to know these details, only that the lower + preference paths are preferred, as stated in the spec. The paths + may not actually be physically redundant depending on the topology + of the subnet, but the point of LMC > 0 is to offer redundancy, + so I assume the subnet is physically appropriate for the specified + LMC value. A more advanced implementation could inspect for physical + redundancy, but I'm not going to bother with that now. + */ + + osm_port_get_lid_range_ho( p_src_port, &src_lid_min_ho, &src_lid_max_ho ); + osm_port_get_lid_range_ho( p_dest_port, &dest_lid_min_ho, &dest_lid_max_ho ); + + if ( osm_log_is_active( p_rcv->p_log, OSM_LOG_DEBUG ) ) + { + osm_log( p_rcv->p_log, OSM_LOG_DEBUG, + "__osm_mpr_rcv_get_port_pair_paths: " + "Src LID [0x%X-0x%X], " + "Dest LID [0x%X-0x%X]\n", + src_lid_min_ho, src_lid_max_ho, + dest_lid_min_ho, dest_lid_max_ho ); + } + + src_lid_ho = src_lid_min_ho; + dest_lid_ho = dest_lid_min_ho; + + /* + Preferred paths come first in OpenSM + */ + preference = 0; + + while ( path_num < rem_paths ) + { + /* + These paths are "fully redundant" + */ + p_pr_item = __osm_mpr_rcv_get_lid_pair_path( p_rcv, p_mpr, + p_src_port, p_dest_port, + src_lid_ho, dest_lid_ho, + comp_mask, preference ); + + if ( p_pr_item ) + { + cl_qlist_insert_tail( p_list, + (cl_list_item_t*)&p_pr_item->pool_item ); + ++path_num; + } + + if ( ++src_lid_ho > src_lid_max_ho ) + break; + + if ( ++dest_lid_ho > dest_lid_max_ho ) + break; + } + + /* + Check if we've accumulated all the paths that the user cares to see + */ + if ( path_num == rem_paths ) + goto Exit; + + /* + Don't bother reporting preference 1 paths for now. + It's more trouble than it's worth and can only occur + if ports have different LMC values, which isn't supported + by OpenSM right now anyway. + */ + preference = 2; + src_lid_ho = src_lid_min_ho; + dest_lid_ho = dest_lid_min_ho; + src_offset = 0; + dest_offset = 0; + + /* + Iterate over the remaining paths + */ + while ( path_num < rem_paths ) + { + dest_offset++; + dest_lid_ho++; + + if ( dest_lid_ho > dest_lid_max_ho ) + { + src_offset++; + src_lid_ho++; + + if ( src_lid_ho > src_lid_max_ho ) + break; /* done */ + + dest_offset = 0; + dest_lid_ho = dest_lid_min_ho; + } + + /* + These paths are "fully non-redundant" with paths already + identified above and consequently not of much value. + + Don't return paths we already identified above, as indicated + by the offset values being equal. + */ + if ( src_offset == dest_offset ) + continue; /* already reported */ + + p_pr_item = __osm_mpr_rcv_get_lid_pair_path( p_rcv, p_mpr, + p_src_port, p_dest_port, + src_lid_ho, dest_lid_ho, + comp_mask, preference ); + + if ( p_pr_item ) + { + cl_qlist_insert_tail( p_list, + (cl_list_item_t*)&p_pr_item->pool_item ); + ++path_num; + } + } + + Exit: + OSM_LOG_EXIT( p_rcv->p_log ); + return path_num; +} + +#undef min +#define min(x,y) (((x) < (y)) ? (x) : (y)) + +/********************************************************************** + **********************************************************************/ +static osm_mpr_item_t* +__osm_mpr_rcv_get_apm_port_pair_paths( + IN osm_mpr_rcv_t* const p_rcv, + IN const ib_multipath_rec_t* const p_mpr, + IN const osm_port_t* const p_src_port, + IN const osm_port_t* const p_dest_port, + IN int base_offs, + IN const ib_net64_t comp_mask, + IN cl_qlist_t* const p_list ) +{ + osm_mpr_item_t* p_pr_item = 0; + uint16_t src_lid_min_ho; + uint16_t src_lid_max_ho; + uint16_t dest_lid_min_ho; + uint16_t dest_lid_max_ho; + uint16_t src_lid_ho; + uint16_t dest_lid_ho; + uintn_t iterations; + int src_lids, dest_lids; + + OSM_LOG_ENTER( p_rcv->p_log, __osm_mpr_rcv_get_apm_port_pair_paths ); + + if ( osm_log_is_active( p_rcv->p_log, OSM_LOG_DEBUG ) ) + { + osm_log( p_rcv->p_log, OSM_LOG_DEBUG, + "__osm_mpr_rcv_get_apm_port_pair_paths: " + "Src port 0x%016" PRIx64 ", " + "Dst port 0x%016" PRIx64 ", base offs %d\n", + cl_ntoh64( osm_port_get_guid( p_src_port ) ), + cl_ntoh64( osm_port_get_guid( p_dest_port ) ), + base_offs ); + } + + osm_port_get_lid_range_ho( p_src_port, &src_lid_min_ho, &src_lid_max_ho ); + osm_port_get_lid_range_ho( p_dest_port, &dest_lid_min_ho, &dest_lid_max_ho ); + + src_lid_ho = src_lid_min_ho; + dest_lid_ho = dest_lid_min_ho; + + src_lids = src_lid_max_ho - src_lid_min_ho + 1; + dest_lids = dest_lid_max_ho - dest_lid_min_ho + 1; + + src_lid_ho += base_offs % src_lids; + dest_lid_ho += base_offs % dest_lids; + + osm_log( p_rcv->p_log, OSM_LOG_DEBUG, + "__osm_mpr_rcv_get_apm_port_pair_paths: " + "Src LIDs [0x%X-0x%X] hashed %d, " + "Dest LIDs [0x%X-0x%X] hashed %d\n", + src_lid_min_ho, src_lid_max_ho, src_lid_ho, + dest_lid_min_ho, dest_lid_max_ho, dest_lid_ho ); + + iterations = min( src_lids, dest_lids ); + + while ( iterations-- ) + { + /* + These paths are "fully redundant" + */ + p_pr_item = __osm_mpr_rcv_get_lid_pair_path( p_rcv, p_mpr, + p_src_port, p_dest_port, + src_lid_ho, dest_lid_ho, + comp_mask, 0 ); + + if ( p_pr_item ) + { + osm_log( p_rcv->p_log, OSM_LOG_DEBUG, + "__osm_mpr_rcv_get_apm_port_pair_paths: " + "Found matching path from Src LID 0x%X to Dest LID 0x%X with %d hops\n", + src_lid_ho, dest_lid_ho, p_pr_item->hops); + break; + } + + if ( ++src_lid_ho > src_lid_max_ho ) + src_lid_ho = src_lid_min_ho; + + if ( ++dest_lid_ho > dest_lid_max_ho ) + dest_lid_ho = dest_lid_min_ho; + } + + OSM_LOG_EXIT( p_rcv->p_log ); + return p_pr_item; +} + +/********************************************************************** + **********************************************************************/ +static ib_net16_t +__osm_mpr_rcv_get_gids( + IN osm_mpr_rcv_t* const p_rcv, + IN const ib_gid_t * gids, + IN int ngids, + IN int is_sgid, + OUT osm_port_t** pp_port ) +{ + osm_port_t *p_port; + ib_net16_t ib_status = IB_SUCCESS; + int i; + + OSM_LOG_ENTER( p_rcv->p_log, __osm_mpr_rcv_get_gids ); + + for ( i = 0; i < ngids; i++, gids++ ) { + if ( !ib_gid_is_link_local ( gids ) ) { + if ( ( is_sgid && ib_gid_is_multicast( gids ) ) || + ( ib_gid_get_subnet_prefix ( gids ) != p_rcv->p_subn->opt.subnet_prefix ) ) { + /* + This 'error' is the client's fault (bad gid) so + don't enter it as an error in our own log. + Return an error response to the client. + */ + osm_log( p_rcv->p_log, OSM_LOG_VERBOSE, + "__osm_mpr_rcv_get_gids: ERR 451B: " + "Non local %sGID subnet prefix 0x%016" PRIx64 "\n", + is_sgid ? "S" : "D", + cl_ntoh64( gids->unicast.prefix ) ); + + ib_status = IB_SA_MAD_STATUS_INVALID_GID; + goto Exit; + } + } + + p_port = (osm_port_t *)cl_qmap_get( &p_rcv->p_subn->port_guid_tbl, + gids->unicast.interface_id ); + if ( !p_port || + p_port == (osm_port_t *)cl_qmap_end( &p_rcv->p_subn->port_guid_tbl ) ) { + /* + This 'error' is the client's fault (bad gid) so + don't enter it as an error in our own log. + Return an error response to the client. + */ + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "__osm_mpr_rcv_get_gids: ERR 4506: " + "No port with GUID 0x%016" PRIx64 "\n", + cl_ntoh64( gids->unicast.interface_id ) ); + + ib_status = IB_SA_MAD_STATUS_INVALID_GID; + goto Exit; + } + + pp_port[i] = p_port; + } + + Exit: + OSM_LOG_EXIT(p_rcv->p_log); + + return ib_status; +} + +/********************************************************************** + **********************************************************************/ +static ib_net16_t +__osm_mpr_rcv_get_end_points( + IN osm_mpr_rcv_t* const p_rcv, + IN const osm_madw_t* const p_madw, + OUT osm_port_t ** pp_ports, + OUT int * nsrc, + OUT int * ndest ) +{ + const ib_multipath_rec_t* p_mpr; + const ib_sa_mad_t* p_sa_mad; + ib_net64_t comp_mask; + ib_net16_t sa_status = IB_SA_MAD_STATUS_SUCCESS; + ib_gid_t * gids; + + OSM_LOG_ENTER( p_rcv->p_log, __osm_mpr_rcv_get_end_points ); + + /* + Determine what fields are valid and then get a pointer + to the source and destination port objects, if possible. + */ + p_sa_mad = osm_madw_get_sa_mad_ptr( p_madw ); + p_mpr = (ib_multipath_rec_t*)ib_sa_mad_get_payload_ptr( p_sa_mad ); + gids = (ib_gid_t *)p_mpr->gids; + + comp_mask = p_sa_mad->comp_mask; + + /* + Check a few easy disqualifying cases up front before getting + into the endpoints. + */ + *nsrc = *ndest = 0; + + if ( comp_mask & IB_MPR_COMPMASK_SGIDCOUNT ) { + *nsrc = p_mpr->sgid_count; + if ( *nsrc > IB_MULTIPATH_MAX_GIDS ) + *nsrc = IB_MULTIPATH_MAX_GIDS; + sa_status = __osm_mpr_rcv_get_gids( p_rcv, gids, *nsrc, 1, pp_ports ); + if ( sa_status != IB_SUCCESS ) + goto Exit; + } + + if ( comp_mask & IB_MPR_COMPMASK_DGIDCOUNT ) { + *ndest = p_mpr->dgid_count; + if ( *ndest + *nsrc > IB_MULTIPATH_MAX_GIDS ) + *ndest = IB_MULTIPATH_MAX_GIDS - *nsrc; + sa_status = __osm_mpr_rcv_get_gids( p_rcv, gids + *nsrc, *ndest, 0, + pp_ports + *nsrc ); + } + + Exit: + OSM_LOG_EXIT( p_rcv->p_log ); + return( sa_status ); +} + +#define __hash_lids(a, b, lmc) \ + (((((a) >> (lmc)) << 4) | ((b) >> (lmc))) % 103) + +/********************************************************************** + **********************************************************************/ +static void +__osm_mpr_rcv_get_apm_paths( + IN osm_mpr_rcv_t* const p_rcv, + IN const ib_multipath_rec_t* const p_mpr, + IN const osm_port_t* const p_req_port, + IN osm_port_t ** _pp_ports, + IN const ib_net64_t comp_mask, + IN cl_qlist_t* const p_list ) +{ + osm_port_t *pp_ports[4]; + osm_mpr_item_t *matrix[2][2]; + int base_offs, src_lid_ho, dest_lid_ho; + int sumA, sumB, minA, minB; + + OSM_LOG_ENTER( p_rcv->p_log, __osm_mpr_rcv_get_apm_paths ); + + /* + * We want to: + * 1. use different lid offsets (from base) for the resultant paths + * to increase the probability of redundant paths or in case + * of Clos - to ensure it (different offset => different spine!) + * 2. keep consistent paths no matter of direction and order of ports + * 3. distibute the lid offsets to balance the load + * So, we sort the ports (within the srcs, and within the dests), + * hash the lids of S0, D0 (after the sort), and call __osm_mpr_rcv_get_apm_port_pair_paths + * with base_lid for S0, D0 and base_lid + 1 for S1, D1. This way we will get + * always the same offsets - order indepentent, and make sure different spines are used. + * Note that the diagonals on a Clos have the same number of hops, so it doesn't + * really matter which diagonal we use. + */ + if ( _pp_ports[0]->guid < _pp_ports[1]->guid ) { + pp_ports[0] = _pp_ports[0]; + pp_ports[1] = _pp_ports[1]; + } + else + { + pp_ports[0] = _pp_ports[1]; + pp_ports[1] = _pp_ports[0]; + } + if ( _pp_ports[2]->guid < _pp_ports[3]->guid ) { + pp_ports[2] = _pp_ports[2]; + pp_ports[3] = _pp_ports[3]; + } + else + { + pp_ports[2] = _pp_ports[3]; + pp_ports[3] = _pp_ports[2]; + } + + src_lid_ho = osm_port_get_base_lid( pp_ports[0] ); + dest_lid_ho = osm_port_get_base_lid( pp_ports[2] ); + + base_offs = src_lid_ho < dest_lid_ho ? + __hash_lids( src_lid_ho, dest_lid_ho, p_rcv->p_subn->opt.lmc ) : + __hash_lids( dest_lid_ho, src_lid_ho, p_rcv->p_subn->opt.lmc ); + + matrix[0][0] = __osm_mpr_rcv_get_apm_port_pair_paths( p_rcv, p_mpr, pp_ports[0], + pp_ports[2], base_offs, comp_mask , p_list ); + matrix[0][1] = __osm_mpr_rcv_get_apm_port_pair_paths( p_rcv, p_mpr, pp_ports[0], + pp_ports[3], base_offs, comp_mask, p_list ); + matrix[1][0] = __osm_mpr_rcv_get_apm_port_pair_paths( p_rcv, p_mpr, pp_ports[1], + pp_ports[2], base_offs+1, comp_mask, p_list ); + matrix[1][1] = __osm_mpr_rcv_get_apm_port_pair_paths( p_rcv, p_mpr, pp_ports[1], + pp_ports[3], base_offs+1, comp_mask, p_list ); + + osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "__osm_mpr_rcv_get_apm_paths: " + "APM matrix:\n" + "\t{0,0} 0x%X->0x%X (%d)\t| {0,1} 0x%X->0x%X (%d)\n" + "\t{1,0} 0x%X->0x%X (%d)\t| {1,1} 0x%X->0x%X (%d)\n", + matrix[0][0]->path_rec.slid, matrix[0][0]->path_rec.dlid, matrix[0][0]->hops, + matrix[0][1]->path_rec.slid, matrix[0][1]->path_rec.dlid, matrix[0][1]->hops, + matrix[1][0]->path_rec.slid, matrix[1][0]->path_rec.dlid, matrix[1][0]->hops, + matrix[1][1]->path_rec.slid, matrix[1][1]->path_rec.dlid, matrix[1][1]->hops ); + + /* check diagonal A {(0,0), (1,1)} */ + sumA = matrix[0][0]->hops + matrix[1][1]->hops; + minA = min( matrix[0][0]->hops, matrix[1][1]->hops ); + + /* check diagonal B {(0,1), (1,0)} */ + sumB = matrix[0][1]->hops + matrix[1][0]->hops; + minB = min( matrix[0][1]->hops, matrix[1][0]->hops ); + + /* and the winner is... */ + if ( minA <= minB || ( minA == minB && sumA < sumB ) ) { + /* Diag A */ + osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "__osm_mpr_rcv_get_apm_paths: " + "Diag {0,0} & {1,1} is the best:\n" + "\t{0,0} 0x%X->0x%X (%d)\t & {1,1} 0x%X->0x%X (%d)\n", + matrix[0][0]->path_rec.slid, matrix[0][0]->path_rec.dlid, matrix[0][0]->hops, + matrix[1][1]->path_rec.slid, matrix[1][1]->path_rec.dlid, matrix[1][1]->hops ); + cl_qlist_insert_tail( p_list, + (cl_list_item_t*)&matrix[0][0]->pool_item ); + cl_qlist_insert_tail( p_list, + (cl_list_item_t*)&matrix[1][1]->pool_item ); + cl_qlock_pool_put( &p_rcv->pr_pool, &matrix[0][1]->pool_item ); + cl_qlock_pool_put( &p_rcv->pr_pool, &matrix[1][0]->pool_item ); + } + else + { + /* Diag B */ + osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "__osm_mpr_rcv_get_apm_paths: " + "Diag {0,1} & {1,0} is the best:\n" + "\t{0,1} 0x%X->0x%X (%d)\t & {1,0} 0x%X->0x%X (%d)\n", + matrix[0][1]->path_rec.slid, matrix[0][1]->path_rec.dlid, matrix[0][1]->hops, + matrix[1][0]->path_rec.slid, matrix[1][0]->path_rec.dlid, matrix[1][0]->hops ); + cl_qlist_insert_tail( p_list, + (cl_list_item_t*)&matrix[0][1]->pool_item ); + cl_qlist_insert_tail( p_list, + (cl_list_item_t*)&matrix[1][0]->pool_item ); + cl_qlock_pool_put( &p_rcv->pr_pool, &matrix[0][0]->pool_item ); + cl_qlock_pool_put( &p_rcv->pr_pool, &matrix[1][1]->pool_item ); + } + + OSM_LOG_EXIT( p_rcv->p_log ); +} + +/********************************************************************** + **********************************************************************/ +static void +__osm_mpr_rcv_process_pairs( + IN osm_mpr_rcv_t* const p_rcv, + IN const ib_multipath_rec_t* const p_mpr, + IN osm_port_t* const p_req_port, + IN osm_port_t ** pp_ports, + IN const int nsrc, + IN const int ndest, + IN const ib_net64_t comp_mask, + IN cl_qlist_t* const p_list ) +{ + osm_port_t **pp_src_port, **pp_es; + osm_port_t **pp_dest_port, **pp_ed; + uint32_t max_paths, num_paths, total_paths = 0; + + OSM_LOG_ENTER( p_rcv->p_log, __osm_mpr_rcv_process_pairs ); + + if ( comp_mask & IB_MPR_COMPMASK_NUMBPATH ) + max_paths = p_mpr->num_path & 0x7F; + else + max_paths = OSM_SA_MPR_MAX_NUM_PATH; + + for ( pp_src_port = pp_ports, pp_es = pp_ports + nsrc; pp_src_port < pp_es; pp_src_port++ ) + { + for ( pp_dest_port = pp_es, pp_ed = pp_es + ndest; pp_dest_port < pp_ed; pp_dest_port++ ) + { + num_paths = __osm_mpr_rcv_get_port_pair_paths( p_rcv, p_mpr, p_req_port, + *pp_src_port, *pp_dest_port, + max_paths - total_paths, + comp_mask, p_list ); + total_paths += num_paths; + osm_log( p_rcv->p_log, OSM_LOG_DEBUG, + "__osm_mpr_rcv_process_pairs: " + "%d paths %d total paths %d max paths\n", + num_paths, total_paths, max_paths ); + /* Just take first NumbPaths found */ + if (total_paths >= max_paths) + goto Exit; + } + } + + Exit: + OSM_LOG_EXIT( p_rcv->p_log ); +} + +/********************************************************************** + **********************************************************************/ +static void +__osm_mpr_rcv_respond( + IN osm_mpr_rcv_t* const p_rcv, + IN const osm_madw_t* const p_madw, + IN cl_qlist_t* const p_list ) +{ + osm_madw_t* p_resp_madw; + const ib_sa_mad_t* p_sa_mad; + ib_sa_mad_t* p_resp_sa_mad; + size_t num_rec; + size_t mad_size; + ib_path_rec_t* p_resp_pr; + ib_multipath_rec_t* p_mpr; + ib_api_status_t status; + osm_mpr_item_t* p_mpr_item; + uint32_t i; + + OSM_LOG_ENTER( p_rcv->p_log, __osm_mpr_rcv_respond ); + + p_sa_mad = osm_madw_get_sa_mad_ptr( p_madw ); + p_mpr = (ib_multipath_rec_t*)ib_sa_mad_get_payload_ptr( p_sa_mad ); + + num_rec = cl_qlist_count( p_list ); + + osm_log( p_rcv->p_log, OSM_LOG_DEBUG, + "__osm_mpr_rcv_respond: " + "Generating response with %zu records\n", num_rec ); + + mad_size = IB_SA_MAD_HDR_SIZE + num_rec * sizeof(ib_path_rec_t); + + /* + Get a MAD to reply. Address of Mad is in the received mad_wrapper + */ + p_resp_madw = osm_mad_pool_get( p_rcv->p_mad_pool, p_madw->h_bind, + mad_size, &p_madw->mad_addr ); + + if ( !p_resp_madw ) + { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "__osm_mpr_rcv_respond: " + "ERR 4502: Unable to allocate MAD\n" ); + + for ( i = 0; i < num_rec; i++ ) + { + p_mpr_item = (osm_mpr_item_t*)cl_qlist_remove_head( p_list ); + cl_qlock_pool_put( &p_rcv->pr_pool, &p_mpr_item->pool_item ); + } + + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_SA_MAD_STATUS_NO_RESOURCES ); + goto Exit; + } + + p_resp_sa_mad = osm_madw_get_sa_mad_ptr( p_resp_madw ); + + memcpy( p_resp_sa_mad, p_sa_mad, IB_SA_MAD_HDR_SIZE ); + p_resp_sa_mad->method |= IB_MAD_METHOD_RESP_MASK; + /* C15-0.1.5 - always return SM_Key = 0 (table 185 p 884) */ + p_resp_sa_mad->sm_key = 0; + + /* + o15-0.2.7: If MultiPath is supported, then SA shall respond to a + SubnAdmGetMulti() containing a valid MultiPathRecord attribute with + a set of zero or more PathRecords satisfying the constraints indicated + in the MultiPathRecord received. The PathRecord Attribute ID shall be + used in the response. + */ + p_resp_sa_mad->attr_id = IB_MAD_ATTR_PATH_RECORD; + p_resp_sa_mad->attr_offset = ib_get_attr_offset( sizeof(ib_path_rec_t) ); + + p_resp_sa_mad->rmpp_flags = IB_RMPP_FLAG_ACTIVE; + + p_resp_pr = (ib_path_rec_t*)ib_sa_mad_get_payload_ptr( p_resp_sa_mad ); + + for ( i = 0; i < num_rec; i++ ) + { + p_mpr_item = (osm_mpr_item_t*)cl_qlist_remove_head( p_list ); + + /* Copy the Path Records from the list into the MAD */ + *p_resp_pr = p_mpr_item->path_rec; + + cl_qlock_pool_put( &p_rcv->pr_pool, &p_mpr_item->pool_item ); + p_resp_pr++; + } + + CL_ASSERT( cl_is_qlist_empty( p_list ) ); + + osm_dump_sa_mad( p_rcv->p_log, p_resp_sa_mad, OSM_LOG_FRAMES ); + + status = osm_vendor_send( p_resp_madw->h_bind, p_resp_madw, FALSE ); + + if ( status != IB_SUCCESS ) + { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "__osm_mpr_rcv_respond: ERR 4507: " + "Unable to send MAD (%s)\n", ib_get_err_str( status ) ); + /* osm_mad_pool_put( p_rcv->p_mad_pool, p_resp_madw ); */ + } + + Exit: + OSM_LOG_EXIT( p_rcv->p_log ); +} + +/********************************************************************** + **********************************************************************/ +void +osm_mpr_rcv_process( + IN osm_mpr_rcv_t* const p_rcv, + IN osm_madw_t* const p_madw ) +{ + const ib_multipath_rec_t* p_mpr; + const ib_sa_mad_t* p_sa_mad; + osm_port_t* requester_port; + osm_port_t* pp_ports[IB_MULTIPATH_MAX_GIDS]; + cl_qlist_t pr_list; + ib_net16_t sa_status; + int nsrc, ndest; + + OSM_LOG_ENTER( p_rcv->p_log, osm_mpr_rcv_process ); + + CL_ASSERT( p_madw ); + + p_sa_mad = osm_madw_get_sa_mad_ptr( p_madw ); + p_mpr = (ib_multipath_rec_t*)ib_sa_mad_get_payload_ptr( p_sa_mad ); + + CL_ASSERT( p_sa_mad->attr_id == IB_MAD_ATTR_MULTIPATH_RECORD ); + + if ( ( p_sa_mad->rmpp_flags & IB_RMPP_FLAG_ACTIVE ) != IB_RMPP_FLAG_ACTIVE ) + { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "osm_mpr_rcv_process: ERR 4510: " + "Invalid request since RMPP_FLAG_ACTIVE is not set\n" ); + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_SA_MAD_STATUS_REQ_INVALID ); + goto Exit; + } + + /* we only support SubnAdmGetMulti method */ + if ( p_sa_mad->method != IB_MAD_METHOD_GETMULTI ) { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "osm_mpr_rcv_process: ERR 4513: " + "Unsupported Method (%s)\n", + ib_get_sa_method_str( p_sa_mad->method ) ); + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_MAD_STATUS_UNSUP_METHOD_ATTR ); + goto Exit; + } + + /* update the requester physical port. */ + requester_port = osm_get_port_by_mad_addr( p_rcv->p_log, p_rcv->p_subn, + osm_madw_get_mad_addr_ptr( p_madw ) ); + if ( requester_port == NULL ) + { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "osm_mpr_rcv_process: ERR 4517: " + "Cannot find requester physical port\n" ); + goto Exit; + } + + if ( osm_log_is_active( p_rcv->p_log, OSM_LOG_DEBUG ) ) + osm_dump_multipath_record( p_rcv->p_log, p_mpr, OSM_LOG_DEBUG ); + + cl_qlist_init( &pr_list ); + + /* + Most SA functions (including this one) are read-only on the + subnet object, so we grab the lock non-exclusively. + */ + cl_plock_acquire( p_rcv->p_lock ); + + sa_status = __osm_mpr_rcv_get_end_points( p_rcv, p_madw, pp_ports, + &nsrc, &ndest ); + + if ( sa_status != IB_SA_MAD_STATUS_SUCCESS || !nsrc || !ndest ) + { + if ( sa_status == IB_SA_MAD_STATUS_SUCCESS && ( !nsrc || !ndest ) ) + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "osm_mpr_rcv_process_cb: ERR 4512: " + "__osm_mpr_rcv_get_end_points failed, not enough GIDs " + "(nsrc %d ndest %d)\n", + nsrc, ndest); + cl_plock_release( p_rcv->p_lock ); + if ( sa_status == IB_SA_MAD_STATUS_SUCCESS ) + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_SA_MAD_STATUS_REQ_INVALID ); + else + osm_sa_send_error( p_rcv->p_resp, p_madw, sa_status ); + goto Exit; + } + + /* APM request */ + if ( nsrc == 2 && ndest == 2 && ( p_mpr->num_path & 0x7F ) == 2 ) + __osm_mpr_rcv_get_apm_paths( p_rcv, p_mpr, requester_port, pp_ports, + p_sa_mad->comp_mask, &pr_list ); + else + __osm_mpr_rcv_process_pairs( p_rcv, p_mpr, requester_port, pp_ports, + nsrc, ndest, + p_sa_mad->comp_mask, &pr_list ); + + cl_plock_release( p_rcv->p_lock ); + __osm_mpr_rcv_respond( p_rcv, p_madw, &pr_list ); + + Exit: + OSM_LOG_EXIT( p_rcv->p_log ); +} +#endif + diff --git a/trunk/ulp/opensm/user/opensm/osm_sa_multipath_record_ctrl.c b/trunk/ulp/opensm/user/opensm/osm_sa_multipath_record_ctrl.c new file mode 100644 index 00000000..6a30be92 --- /dev/null +++ b/trunk/ulp/opensm/user/opensm/osm_sa_multipath_record_ctrl.c @@ -0,0 +1,128 @@ +/* + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. + * + * This software is available to you under the OpenIB.org BSD license + * below: + * + * Redistribution and use in source and binary forms, with or + * without modification, are permitted provided that the following + * conditions are met: + * + * - Redistributions of source code must retain the above + * copyright notice, this list of conditions and the following + * disclaimer. + * + * - Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials + * provided with the distribution. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS + * BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN + * ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN + * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + * + * $Id$ + */ + + + +/* + * Abstract: + * Implementation of osm_mpr_rcv_ctrl_t. + * This object represents the MultiPathRecord request controller object. + * This object is part of the opensm family of objects. + * + * Environment: + * Linux User Mode + * + */ + +#if defined (VENDOR_RMPP_SUPPORT) && defined (DUAL_SIDED_RMPP) + +#if HAVE_CONFIG_H +# include +#endif /* HAVE_CONFIG_H */ + +#include +#include +#include + +/********************************************************************** + **********************************************************************/ +static void +__osm_mpr_rcv_ctrl_disp_callback( + IN void *context, + IN void *p_data ) +{ + /* ignore return status when invoked via the dispatcher */ + osm_mpr_rcv_process( ((osm_mpr_rcv_ctrl_t*)context)->p_rcv, + (osm_madw_t*)p_data ); +} + +/********************************************************************** + **********************************************************************/ +void +osm_mpr_rcv_ctrl_construct( + IN osm_mpr_rcv_ctrl_t* const p_ctrl ) +{ + memset( p_ctrl, 0, sizeof(*p_ctrl) ); + p_ctrl->h_disp = CL_DISP_INVALID_HANDLE; +} + +/********************************************************************** + **********************************************************************/ +void +osm_mpr_rcv_ctrl_destroy( + IN osm_mpr_rcv_ctrl_t* const p_ctrl ) +{ + CL_ASSERT( p_ctrl ); + cl_disp_unregister( p_ctrl->h_disp ); +} + +/********************************************************************** + **********************************************************************/ +ib_api_status_t +osm_mpr_rcv_ctrl_init( + IN osm_mpr_rcv_ctrl_t* const p_ctrl, + IN osm_mpr_rcv_t* const p_rcv, + IN osm_log_t* const p_log, + IN cl_dispatcher_t* const p_disp ) +{ + ib_api_status_t status = IB_SUCCESS; + + OSM_LOG_ENTER( p_log, osm_mpr_rcv_ctrl_init ); + + osm_mpr_rcv_ctrl_construct( p_ctrl ); + p_ctrl->p_log = p_log; + p_ctrl->p_rcv = p_rcv; + p_ctrl->p_disp = p_disp; + + p_ctrl->h_disp = cl_disp_register( + p_disp, + OSM_MSG_MAD_MULTIPATH_RECORD, + __osm_mpr_rcv_ctrl_disp_callback, + p_ctrl ); + + if( p_ctrl->h_disp == CL_DISP_INVALID_HANDLE ) + { + osm_log( p_log, OSM_LOG_ERROR, + "osm_mpr_rcv_ctrl_init: ERR 4B01: " + "Dispatcher registration failed\n" ); + status = IB_INSUFFICIENT_RESOURCES; + goto Exit; + } + + Exit: + OSM_LOG_EXIT( p_log ); + return( status ); +} + +#endif + diff --git a/trunk/ulp/opensm/user/opensm/osm_sa_node_record.c b/trunk/ulp/opensm/user/opensm/osm_sa_node_record.c index 2862af81..0c752afe 100644 --- a/trunk/ulp/opensm/user/opensm/osm_sa_node_record.c +++ b/trunk/ulp/opensm/user/opensm/osm_sa_node_record.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -48,6 +48,7 @@ # include #endif /* HAVE_CONFIG_H */ +#include #include #include #include @@ -64,7 +65,6 @@ typedef struct _osm_nr_item { cl_pool_item_t pool_item; ib_node_record_t rec; - } osm_nr_item_t; typedef struct _osm_nr_search_ctxt @@ -74,7 +74,6 @@ typedef struct _osm_nr_search_ctxt cl_qlist_t* p_list; osm_nr_rcv_t* p_rcv; const osm_physp_t* p_req_physp; - } osm_nr_search_ctxt_t; /********************************************************************** @@ -83,7 +82,7 @@ void osm_nr_rcv_construct( IN osm_nr_rcv_t* const p_rcv ) { - cl_memclr( p_rcv, sizeof(*p_rcv) ); + memset( p_rcv, 0, sizeof(*p_rcv) ); cl_qlock_pool_construct( &p_rcv->pool ); } @@ -159,7 +158,7 @@ __osm_nr_rcv_new_nr( if( osm_log_is_active( p_rcv->p_log, OSM_LOG_DEBUG ) ) { - osm_log( p_rcv->p_log, OSM_LOG_ERROR, + osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "__osm_nr_rcv_new_nr: " "New NodeRecord: node 0x%016" PRIx64 "\n\t\t\t\tport 0x%016" PRIx64 ", lid 0x%X\n", @@ -168,14 +167,14 @@ __osm_nr_rcv_new_nr( ); } - cl_memclr( &p_rec_item->rec, sizeof(ib_node_record_t) ); + memset( &p_rec_item->rec, 0, sizeof(ib_node_record_t) ); p_rec_item->rec.lid = lid; p_rec_item->rec.node_info = p_node->node_info; p_rec_item->rec.node_info.port_guid = port_guid; - cl_memcpy(&(p_rec_item->rec.node_desc), &(p_node->node_desc), - IB_NODE_DESCRIPTION_SIZE); + memcpy(&(p_rec_item->rec.node_desc), &(p_node->node_desc), + IB_NODE_DESCRIPTION_SIZE); cl_qlist_insert_tail( p_list, (cl_list_item_t*)&p_rec_item->pool_item ); Exit: @@ -197,19 +196,18 @@ __osm_nr_rcv_create_nr( const osm_physp_t* p_physp; uint8_t port_num; uint8_t num_ports; - uint16_t match_lid_ho; - uint16_t lid_ho; + uint16_t match_lid_ho; + ib_net16_t base_lid; ib_net16_t base_lid_ho; ib_net16_t max_lid_ho; uint8_t lmc; ib_net64_t port_guid; - ib_api_status_t status; OSM_LOG_ENTER( p_rcv->p_log, __osm_nr_rcv_create_nr ); if( osm_log_is_active( p_rcv->p_log, OSM_LOG_DEBUG ) ) { - osm_log( p_rcv->p_log, OSM_LOG_ERROR, + osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "__osm_nr_rcv_create_nr: " "Looking for NodeRecord with LID: 0x%X GUID:0x%016" PRIx64 "\n", cl_ntoh16( match_lid ), @@ -243,7 +241,8 @@ __osm_nr_rcv_create_nr( if( match_port_guid && ( port_guid != match_port_guid ) ) continue; - base_lid_ho = cl_ntoh16( osm_physp_get_base_lid( p_physp ) ); + base_lid = osm_physp_get_base_lid( p_physp ); + base_lid_ho = cl_ntoh16( base_lid ); lmc = osm_physp_get_lmc( p_physp ); max_lid_ho = (uint16_t)( base_lid_ho + (1 << lmc) - 1 ); match_lid_ho = cl_ntoh16( match_lid ); @@ -255,37 +254,19 @@ __osm_nr_rcv_create_nr( */ if( osm_log_is_active( p_rcv->p_log, OSM_LOG_DEBUG ) ) { - osm_log( p_rcv->p_log, OSM_LOG_ERROR, + osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "__osm_nr_rcv_create_nr: " "Comparing LID: 0x%X <= 0x%X <= 0x%X\n", - cl_ntoh16( base_lid_ho ), - cl_ntoh16( match_lid_ho ), - cl_ntoh16( max_lid_ho ) + base_lid_ho, match_lid_ho, max_lid_ho ); } - if( (match_lid_ho <= max_lid_ho) && (match_lid_ho >= base_lid_ho) ) - { - /* - Ignore return code for now. - */ - __osm_nr_rcv_new_nr( p_rcv, p_node, p_list, - port_guid, match_lid ); - } - } - else - { - /* - For every lid value create a Node Record. - */ - for( lid_ho = base_lid_ho; lid_ho <= max_lid_ho; lid_ho++ ) - { - status = __osm_nr_rcv_new_nr( p_rcv, p_node, p_list, - port_guid, cl_hton16( lid_ho ) ); - if( status != IB_SUCCESS ) - break; - } + if ( match_lid_ho < base_lid_ho || match_lid_ho > max_lid_ho ) + continue; } + + __osm_nr_rcv_new_nr( p_rcv, p_node, p_list, port_guid, base_lid ); + } OSM_LOG_EXIT( p_rcv->p_log ); @@ -293,15 +274,14 @@ __osm_nr_rcv_create_nr( /********************************************************************** **********************************************************************/ -static -void +static void __osm_nr_rcv_by_comp_mask( IN cl_map_item_t* const p_map_item, - IN void* context ) + IN void* context ) { const osm_nr_search_ctxt_t* const p_ctxt = (osm_nr_search_ctxt_t *)context; const osm_node_t* const p_node = (osm_node_t*)p_map_item; - const ib_node_record_t* const p_rcvd_rec = p_ctxt->p_rcvd_rec; + const ib_node_record_t* const p_rcvd_rec = p_ctxt->p_rcvd_rec; const osm_physp_t* const p_req_physp = p_ctxt->p_req_physp; osm_nr_rcv_t* const p_rcv = p_ctxt->p_rcv; ib_net64_t const comp_mask = p_ctxt->comp_mask; @@ -312,7 +292,7 @@ __osm_nr_rcv_by_comp_mask( osm_dump_node_info( p_ctxt->p_rcv->p_log, - & p_node->node_info, + &p_node->node_info, OSM_LOG_VERBOSE ); if( comp_mask & IB_NR_COMPMASK_LID ) @@ -325,7 +305,7 @@ __osm_nr_rcv_by_comp_mask( */ if( osm_log_is_active( p_rcv->p_log, OSM_LOG_DEBUG ) ) { - osm_log( p_rcv->p_log, OSM_LOG_ERROR, + osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "__osm_nr_rcv_by_comp_mask: " "Looking for node 0x%016" PRIx64 ", found 0x%016" PRIx64 "\n", @@ -336,74 +316,74 @@ __osm_nr_rcv_by_comp_mask( /* DEBUG BOTTOM */ - if( (p_node->node_info.node_guid != p_rcvd_rec->node_info.node_guid )) + if( (p_node->node_info.node_guid != p_rcvd_rec->node_info.node_guid) ) goto Exit; } - if( comp_mask & IB_NR_COMPMASK_PORTGUID) + if( comp_mask & IB_NR_COMPMASK_PORTGUID ) { match_port_guid = p_rcvd_rec->node_info.port_guid; } - if( comp_mask & IB_NR_COMPMASK_SYSIMAGEGUID) + if( comp_mask & IB_NR_COMPMASK_SYSIMAGEGUID ) { - if( (p_node->node_info.sys_guid != p_rcvd_rec->node_info.sys_guid)) + if( (p_node->node_info.sys_guid != p_rcvd_rec->node_info.sys_guid) ) goto Exit; } if( comp_mask & IB_NR_COMPMASK_BASEVERSION ) { - if( (p_node->node_info.base_version != p_rcvd_rec->node_info.base_version)) + if( (p_node->node_info.base_version != p_rcvd_rec->node_info.base_version) ) goto Exit; } - if( comp_mask & IB_NR_COMPMASK_CLASSVERSION) + if( comp_mask & IB_NR_COMPMASK_CLASSVERSION ) { - if( (p_node->node_info.class_version != p_rcvd_rec->node_info.class_version)) + if( (p_node->node_info.class_version != p_rcvd_rec->node_info.class_version) ) goto Exit; } - if( comp_mask & IB_NR_COMPMASK_NODETYPE) + if( comp_mask & IB_NR_COMPMASK_NODETYPE ) { - if( (p_node->node_info.node_type != p_rcvd_rec->node_info.node_type)) + if( (p_node->node_info.node_type != p_rcvd_rec->node_info.node_type) ) goto Exit; } - if( comp_mask & IB_NR_COMPMASK_NUMPORTS) + if( comp_mask & IB_NR_COMPMASK_NUMPORTS ) { - if( (p_node->node_info.num_ports != p_rcvd_rec->node_info.num_ports)) + if( (p_node->node_info.num_ports != p_rcvd_rec->node_info.num_ports) ) goto Exit; } - if( comp_mask & IB_NR_COMPMASK_PARTCAP) + if( comp_mask & IB_NR_COMPMASK_PARTCAP ) { - if( (p_node->node_info.partition_cap != p_rcvd_rec->node_info.partition_cap)) + if( (p_node->node_info.partition_cap != p_rcvd_rec->node_info.partition_cap) ) goto Exit; } - if( comp_mask & IB_NR_COMPMASK_DEVID) + if( comp_mask & IB_NR_COMPMASK_DEVID ) { - if( (p_node->node_info.device_id != p_rcvd_rec->node_info.device_id)) + if( (p_node->node_info.device_id != p_rcvd_rec->node_info.device_id) ) goto Exit; } - if( comp_mask & IB_NR_COMPMASK_REV) + if( comp_mask & IB_NR_COMPMASK_REV ) { - if( (p_node->node_info.revision != p_rcvd_rec->node_info.revision)) + if( (p_node->node_info.revision != p_rcvd_rec->node_info.revision) ) goto Exit; } - if( comp_mask & IB_NR_COMPMASK_PORTNUM) + if( comp_mask & IB_NR_COMPMASK_PORTNUM ) { if( ib_node_info_get_local_port_num(&p_node->node_info) != ib_node_info_get_local_port_num(&p_rcvd_rec->node_info) ) goto Exit; } - if( comp_mask & IB_NR_COMPMASK_VENDID) + if( comp_mask & IB_NR_COMPMASK_VENDID ) { if( ib_node_info_get_vendor_id(&p_node->node_info) != ib_node_info_get_vendor_id(&p_rcvd_rec->node_info) ) goto Exit; } - if( comp_mask & IB_NR_COMPMASK_NODEDESC) + if( comp_mask & IB_NR_COMPMASK_NODEDESC ) { if( strncmp((char*) &p_node->node_desc, - (char*) &p_rcvd_rec->node_desc, sizeof(ib_node_desc_t))) + (char*) &p_rcvd_rec->node_desc, sizeof(ib_node_desc_t)) ) goto Exit; } __osm_nr_rcv_create_nr( p_rcv, p_node, p_ctxt->p_list, - match_port_guid, match_lid, p_req_physp); + match_port_guid, match_lid, p_req_physp ); Exit: OSM_LOG_EXIT( p_ctxt->p_rcv->p_log ); @@ -417,16 +397,16 @@ osm_nr_rcv_process( IN const osm_madw_t* const p_madw ) { const ib_sa_mad_t* p_rcvd_mad; - const ib_node_record_t* p_rcvd_rec; + const ib_node_record_t* p_rcvd_rec; ib_node_record_t* p_resp_rec; cl_qlist_t rec_list; osm_madw_t* p_resp_madw; - ib_sa_mad_t* p_resp_sa_mad; - uint32_t num_rec, pre_trim_num_rec; + ib_sa_mad_t* p_resp_sa_mad; + uint32_t num_rec, pre_trim_num_rec; #ifndef VENDOR_RMPP_SUPPORT - uint32_t trim_num_rec; + uint32_t trim_num_rec; #endif - uint32_t i; + uint32_t i; osm_nr_search_ctxt_t context; osm_nr_item_t* p_rec_item; ib_api_status_t status; @@ -443,6 +423,17 @@ osm_nr_rcv_process( CL_ASSERT( p_rcvd_mad->attr_id == IB_MAD_ATTR_NODE_RECORD ); + /* we only support SubnAdmGet and SubnAdmGetTable methods */ + if ( (p_rcvd_mad->method != IB_MAD_METHOD_GET) && + (p_rcvd_mad->method != IB_MAD_METHOD_GETTABLE) ) { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "osm_nr_rcv_process: ERR 1D05: " + "Unsupported Method (%s)\n", + ib_get_sa_method_str( p_rcvd_mad->method ) ); + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_MAD_STATUS_UNSUP_METHOD_ATTR ); + goto Exit; + } + /* update the requester physical port. */ p_req_physp = osm_get_physp_by_mad_addr(p_rcv->p_log, p_rcv->p_subn, @@ -455,16 +446,6 @@ osm_nr_rcv_process( goto Exit; } - if ( (p_rcvd_mad->method != IB_MAD_METHOD_GET) && - (p_rcvd_mad->method != IB_MAD_METHOD_GETTABLE) ) { - osm_log( p_rcv->p_log, OSM_LOG_ERROR, - "osm_nr_rcv_process: ERR 1D05: " - "Unsupported Method (%s)\n", - ib_get_sa_method_str( p_rcvd_mad->method ) ); - osm_sa_send_error( p_rcv->p_resp, p_madw, IB_SA_MAD_STATUS_REQ_INVALID); - goto Exit; - } - if ( osm_log_is_active( p_rcv->p_log, OSM_LOG_DEBUG ) ) osm_dump_node_record( p_rcv->p_log, p_rcvd_rec, OSM_LOG_DEBUG ); @@ -490,14 +471,13 @@ osm_nr_rcv_process( * C15-0.1.30: * If we do a SubnAdmGet and got more than one record it is an error ! */ - if ( (p_rcvd_mad->method == IB_MAD_METHOD_GET) && - (num_rec > 1)) { + if ( (p_rcvd_mad->method == IB_MAD_METHOD_GET) && (num_rec > 1) ) { osm_log( p_rcv->p_log, OSM_LOG_ERROR, - "osm_nr_rcv_process: " + "osm_nr_rcv_process: ERR 1D03: " "Got more than one record for SubnAdmGet (%u)\n", num_rec ); osm_sa_send_error( p_rcv->p_resp, p_madw, - IB_SA_MAD_STATUS_TOO_MANY_RECORDS); + IB_SA_MAD_STATUS_TOO_MANY_RECORDS ); /* need to set the mem free ... */ p_rec_item = (osm_nr_item_t*)cl_qlist_remove_head( &rec_list ); @@ -530,8 +510,7 @@ osm_nr_rcv_process( if ((p_rcvd_mad->method == IB_MAD_METHOD_GET) && (num_rec == 0)) { - osm_sa_send_error( p_rcv->p_resp, p_madw, - IB_SA_MAD_STATUS_NO_RECORDS ); + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_SA_MAD_STATUS_NO_RECORDS ); goto Exit; } @@ -555,9 +534,7 @@ osm_nr_rcv_process( cl_qlock_pool_put( &p_rcv->pool, &p_rec_item->pool_item ); } - osm_sa_send_error( p_rcv->p_resp, p_madw, - IB_SA_MAD_STATUS_NO_RESOURCES ); - + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_SA_MAD_STATUS_NO_RESOURCES ); goto Exit; } @@ -569,9 +546,9 @@ osm_nr_rcv_process( Then copy all records from the list into the response payload. */ - cl_memcpy( p_resp_sa_mad, p_rcvd_mad, IB_SA_MAD_HDR_SIZE ); - p_resp_sa_mad->method = (uint8_t)(p_resp_sa_mad->method | 0x80); - /* C15-0.1.5 - always return SM_Key = 0 (table 151 p 782) */ + memcpy( p_resp_sa_mad, p_rcvd_mad, IB_SA_MAD_HDR_SIZE ); + p_resp_sa_mad->method |= IB_MAD_METHOD_RESP_MASK; + /* C15-0.1.5 - always return SM_Key = 0 (table 185 p 884) */ p_resp_sa_mad->sm_key = 0; /* Fill in the offset (paylen will be done by the rmpp SAR) */ p_resp_sa_mad->attr_offset = @@ -608,12 +585,11 @@ osm_nr_rcv_process( CL_ASSERT( cl_is_qlist_empty( &rec_list ) ); status = osm_vendor_send( p_resp_madw->h_bind, p_resp_madw, FALSE ); - - if(status != IB_SUCCESS) + if (status != IB_SUCCESS) { osm_log(p_rcv->p_log, OSM_LOG_ERROR, "osm_nr_rcv_process: ERR 1D07: " - "osm_vendor_send. status = %s\n", + "osm_vendor_send status = %s\n", ib_get_err_str(status)); goto Exit; } @@ -621,3 +597,4 @@ osm_nr_rcv_process( Exit: OSM_LOG_EXIT( p_rcv->p_log ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_sa_node_record_ctrl.c b/trunk/ulp/opensm/user/opensm/osm_sa_node_record_ctrl.c index 8c37d064..5712c83c 100644 --- a/trunk/ulp/opensm/user/opensm/osm_sa_node_record_ctrl.c +++ b/trunk/ulp/opensm/user/opensm/osm_sa_node_record_ctrl.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Implementation of osm_nr_rcv_ctrl_t. @@ -48,7 +49,7 @@ # include #endif /* HAVE_CONFIG_H */ -#include +#include #include #include @@ -70,7 +71,7 @@ void osm_nr_rcv_ctrl_construct( IN osm_nr_rcv_ctrl_t* const p_ctrl ) { - cl_memclr( p_ctrl, sizeof(*p_ctrl) ); + memset( p_ctrl, 0, sizeof(*p_ctrl) ); p_ctrl->h_disp = CL_DISP_INVALID_HANDLE; } @@ -121,3 +122,4 @@ osm_nr_rcv_ctrl_init( OSM_LOG_EXIT( p_log ); return( status ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_sa_path_record.c b/trunk/ulp/opensm/user/opensm/osm_sa_path_record.c index e82b2312..a8e60cc3 100644 --- a/trunk/ulp/opensm/user/opensm/osm_sa_path_record.c +++ b/trunk/ulp/opensm/user/opensm/osm_sa_path_record.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -44,20 +44,17 @@ * $Revision: 1.10 $ */ -/* - Next available error code: 0x403 -*/ - #if HAVE_CONFIG_H # include #endif /* HAVE_CONFIG_H */ +#include #include -#include #include #include #include #include +#include #include #include #include @@ -67,6 +64,7 @@ #include #include #include +#include #define OSM_PR_RCV_POOL_MIN_SIZE 64 #define OSM_PR_RCV_POOL_GROW_SIZE 64 @@ -75,7 +73,6 @@ typedef struct _osm_pr_item { cl_pool_item_t pool_item; ib_path_rec_t path_rec; - } osm_pr_item_t; typedef struct _osm_path_parms @@ -100,7 +97,7 @@ void osm_pr_rcv_construct( IN osm_pr_rcv_t* const p_rcv ) { - cl_memclr( p_rcv, sizeof(*p_rcv) ); + memset( p_rcv, 0, sizeof(*p_rcv) ); cl_qlock_pool_construct( &p_rcv->pr_pool ); } @@ -126,7 +123,7 @@ osm_pr_rcv_init( IN osm_log_t* const p_log, IN cl_plock_t* const p_lock ) { - ib_api_status_t status; + ib_api_status_t status; OSM_LOG_ENTER( p_log, osm_pr_rcv_init ); @@ -149,6 +146,80 @@ osm_pr_rcv_init( return( status ); } +/********************************************************************** + **********************************************************************/ +static inline boolean_t +__osm_sa_path_rec_is_tavor_port( + IN const osm_port_t* const p_port) +{ + osm_node_t const* p_node; + ib_net32_t vend_id; + + p_node = osm_port_get_parent_node( p_port ); + vend_id = ib_node_info_get_vendor_id( &p_node->node_info ); + + return( (p_node->node_info.device_id == CL_HTON16(23108)) && + ((vend_id == CL_HTON32(OSM_VENDOR_ID_MELLANOX)) || + (vend_id == CL_HTON32(OSM_VENDOR_ID_TOPSPIN)) || + (vend_id == CL_HTON32(OSM_VENDOR_ID_SILVERSTORM)) || + (vend_id == CL_HTON32(OSM_VENDOR_ID_VOLTAIRE))) ); +} + +/********************************************************************** + **********************************************************************/ +static boolean_t + __osm_sa_path_rec_apply_tavor_mtu_limit( + IN const ib_path_rec_t* const p_pr, + IN const osm_port_t* const p_src_port, + IN const osm_port_t* const p_dest_port, + IN const ib_net64_t comp_mask) +{ + uint8_t required_mtu; + + /* only if at least one of the ports is a Tavor device */ + if (! __osm_sa_path_rec_is_tavor_port(p_src_port) && + ! __osm_sa_path_rec_is_tavor_port(p_dest_port) ) + return( FALSE ); + + /* + we can apply the patch if either: + 1. No MTU required + 2. Required MTU < + 3. Required MTU = 1K or 512 or 256 + 4. Required MTU > 256 or 512 + */ + required_mtu = ib_path_rec_mtu( p_pr ); + if ( ( comp_mask & IB_PR_COMPMASK_MTUSELEC ) && + ( comp_mask & IB_PR_COMPMASK_MTU ) ) + { + switch( ib_path_rec_mtu_sel( p_pr ) ) + { + case 0: /* must be greater than */ + case 2: /* exact match */ + if( IB_MTU_LEN_1024 < required_mtu ) + return(FALSE); + break; + + case 1: /* must be less than */ + /* can't be disqualified by this one */ + break; + + case 3: /* largest available */ + /* the ULP intentionally requested */ + /* the largest MTU possible */ + return(FALSE); + break; + + default: + /* if we're here, there's a bug in ib_path_rec_mtu_sel() */ + CL_ASSERT( FALSE ); + break; + } + } + + return(TRUE); +} + /********************************************************************** **********************************************************************/ static ib_api_status_t @@ -161,21 +232,20 @@ __osm_pr_rcv_get_path_parms( IN const ib_net64_t comp_mask, OUT osm_path_parms_t* const p_parms ) { - ib_net64_t node_guid; const osm_node_t* p_node; const osm_physp_t* p_physp; const osm_physp_t* p_dest_physp; - const osm_switch_t* p_sw; + const osm_prtn_t* p_prtn; const ib_port_info_t* p_pi; - const cl_qmap_t* p_sw_tbl; - ib_api_status_t status = IB_SUCCESS; + ib_net16_t pkey; uint8_t mtu; uint8_t rate; uint8_t pkt_life; uint8_t required_mtu; uint8_t required_rate; uint8_t required_pkt_life; + uint8_t sl; ib_net16_t dest_lid; OSM_LOG_ENTER( p_rcv->p_log, __osm_pr_rcv_get_path_parms ); @@ -185,11 +255,27 @@ __osm_pr_rcv_get_path_parms( p_dest_physp = osm_port_get_default_phys_ptr( p_dest_port ); p_physp = osm_port_get_default_phys_ptr( p_src_port ); p_pi = osm_physp_get_port_info_ptr( p_physp ); - p_sw_tbl = &p_rcv->p_subn->sw_guid_tbl; mtu = ib_port_info_get_mtu_cap( p_pi ); rate = ib_port_info_compute_rate( p_pi ); + /* + Mellanox Tavor device performance is better using 1K MTU. + If required MTU and MTU selector are such that 1K is OK + and at least one end of the path is Tavor we override the + port MTU with 1K. + */ + if ( p_rcv->p_subn->opt.enable_quirks && + __osm_sa_path_rec_apply_tavor_mtu_limit( + p_pr, p_src_port, p_dest_port, comp_mask) ) + if (mtu > IB_MTU_LEN_1024) + { + mtu = IB_MTU_LEN_1024; + osm_log( p_rcv->p_log, OSM_LOG_DEBUG, + "__osm_pr_rcv_get_path_parms: " + "Optimized Path MTU to 1K for Mellanox Tavor device\n"); + } + /* Walk the subnet object from source to destination, tracking the most restrictive rate and mtu values along the way... @@ -200,28 +286,18 @@ __osm_pr_rcv_get_path_parms( p_node = osm_physp_get_node_ptr( p_physp ); - if( osm_node_get_type( p_node ) == IB_NODE_TYPE_SWITCH ) + if( p_node->sw ) { - p_sw = (osm_switch_t *)cl_qmap_get( p_sw_tbl, - osm_node_get_node_guid( p_node ) ); - - if( p_sw == (osm_switch_t *)cl_qmap_end( p_sw_tbl ) ) - { - status = IB_ERROR; - goto Exit; - } - /* * If the dest_lid_ho is equal to the lid of the switch pointed by * p_sw then p_physp will be the physical port of the switch port zero. */ - - p_physp = osm_switch_get_route_by_lid(p_sw, cl_ntoh16(dest_lid_ho) ); + p_physp = osm_switch_get_route_by_lid(p_node->sw, cl_ntoh16( dest_lid_ho ) ); if ( p_physp == 0 ) { osm_log( p_rcv->p_log, OSM_LOG_ERROR, "__osm_pr_rcv_get_path_parms: ERR 1F02: " - "Cannot find routing to lid:0x%X from switch for guid 0x%016" PRIx64 "\n", + "Cannot find routing to LID 0x%X from switch for GUID 0x%016" PRIx64 "\n", dest_lid_ho, cl_ntoh64( osm_node_get_node_guid( p_node ) ) ); status = IB_ERROR; @@ -232,28 +308,17 @@ __osm_pr_rcv_get_path_parms( /* * Same as above */ + p_node = osm_physp_get_node_ptr( p_dest_physp ); - p_node = osm_physp_get_node_ptr(p_dest_physp); - - if( osm_node_get_type( p_node ) == IB_NODE_TYPE_SWITCH ) + if( p_node->sw ) { - p_sw = (osm_switch_t *)cl_qmap_get( p_sw_tbl, - osm_node_get_node_guid(p_node)); - - if( p_sw == (osm_switch_t *)cl_qmap_end( p_sw_tbl ) ) - { - status = IB_ERROR; - goto Exit; - } - - p_dest_physp = osm_switch_get_route_by_lid( p_sw, - cl_ntoh16(dest_lid_ho) ); + p_dest_physp = osm_switch_get_route_by_lid( p_node->sw, cl_ntoh16( dest_lid_ho ) ); if ( p_dest_physp == 0 ) { osm_log( p_rcv->p_log, OSM_LOG_ERROR, "__osm_pr_rcv_get_path_parms: ERR 1F03: " - "Cannot find routing to lid:0x%X from switch for guid 0x%016" PRIx64 "\n", + "Cannot find routing to LID 0x%X from switch for GUID 0x%016" PRIx64 "\n", dest_lid_ho, cl_ntoh64( osm_node_get_node_guid( p_node ) ) ); status = IB_ERROR; @@ -270,7 +335,7 @@ __osm_pr_rcv_get_path_parms( { osm_log( p_rcv->p_log, OSM_LOG_ERROR, "__osm_pr_rcv_get_path_parms: ERR 1F05: " - "Cannot find remote phys port when routing to lid:0x%X from node guid 0x%016" PRIx64 "\n", + "Cannot find remote phys port when routing to LID 0x%X from node GUID 0x%016" PRIx64 "\n", dest_lid_ho, cl_ntoh64( osm_node_get_node_guid( p_node ) ) ); status = IB_ERROR; @@ -285,7 +350,7 @@ __osm_pr_rcv_get_path_parms( p_node = osm_physp_get_node_ptr( p_physp ); - if( osm_node_get_type( p_node ) != IB_NODE_TYPE_SWITCH ) + if( !p_node->sw ) { /* There is some sort of problem in the subnet object! @@ -299,22 +364,6 @@ __osm_pr_rcv_get_path_parms( goto Exit; } - node_guid = osm_node_get_node_guid( p_node ); - p_sw = (osm_switch_t*)cl_qmap_get( p_sw_tbl, node_guid ); - - if( p_sw == (osm_switch_t*)cl_qmap_end( p_sw_tbl ) ) - { - /* - There is some sort of problem in the subnet object! - */ - osm_log( p_rcv->p_log, OSM_LOG_ERROR, - "__osm_pr_rcv_get_path_parms: ERR 1F04: " - "Internal error, no switch for guid 0x%016" PRIx64 "\n", - cl_ntoh64( node_guid ) ); - status = IB_ERROR; - goto Exit; - } - /* Check parameters for the ingress port in this switch. */ @@ -327,38 +376,41 @@ __osm_pr_rcv_get_path_parms( { osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "__osm_pr_rcv_get_path_parms: " - "New smallest MTU = %u at intervening port 0x%016" PRIx64 "\n", + "New smallest MTU = %u at intervening port 0x%016" PRIx64 + " port num 0x%X\n", mtu, - osm_physp_get_port_guid( p_physp ) ); + cl_ntoh64( osm_physp_get_port_guid( p_physp ) ), + osm_physp_get_port_num( p_physp ) ); } } if( rate > ib_port_info_compute_rate( p_pi ) ) { - rate = ib_port_info_compute_rate( p_pi ); if( osm_log_is_active( p_rcv->p_log, OSM_LOG_DEBUG ) ) { osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "__osm_pr_rcv_get_path_parms: " - "New smallest rate = %u at intervening port 0x%016" PRIx64 "\n", + "New smallest rate = %u at intervening port 0x%016" PRIx64 + " port num 0x%X\n", rate, - osm_physp_get_port_guid( p_physp ) ); + cl_ntoh64( osm_physp_get_port_guid( p_physp ) ), + osm_physp_get_port_num( p_physp ) ); } } /* Continue with the egress port on this switch. */ - p_physp = osm_switch_get_route_by_lid( p_sw, dest_lid ); + p_physp = osm_switch_get_route_by_lid( p_node->sw, dest_lid ); if ( p_physp == 0 ) { osm_log( p_rcv->p_log, OSM_LOG_ERROR, "__osm_pr_rcv_get_path_parms: ERR 1F07: " - "Dead end on path to lid:0x%X from switch for guid 0x%016" PRIx64 "\n", + "Dead end on path to LID 0x%X from switch for GUID 0x%016" PRIx64 "\n", dest_lid_ho, - cl_ntoh64( node_guid ) ); + cl_ntoh64( osm_node_get_node_guid( p_node ) ) ); status = IB_ERROR; goto Exit; } @@ -375,23 +427,26 @@ __osm_pr_rcv_get_path_parms( { osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "__osm_pr_rcv_get_path_parms: " - "New smallest MTU = %u at intervening port 0x%016" PRIx64 "\n", + "New smallest MTU = %u at intervening port 0x%016" PRIx64 + " port num 0x%X\n", mtu, - osm_physp_get_port_guid( p_physp ) ); + cl_ntoh64( osm_physp_get_port_guid( p_physp ) ), + osm_physp_get_port_num( p_physp ) ); } } if( rate > ib_port_info_compute_rate( p_pi ) ) { - rate = ib_port_info_compute_rate( p_pi ); if( osm_log_is_active( p_rcv->p_log, OSM_LOG_DEBUG ) ) { osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "__osm_pr_rcv_get_path_parms: " - "New smallest rate = %u at intervening port 0x%016" PRIx64 "\n", + "New smallest rate = %u at intervening port 0x%016" PRIx64 + " port num 0x%X\n", rate, - osm_physp_get_port_guid( p_physp ) ); + cl_ntoh64( osm_physp_get_port_guid( p_physp ) ), + osm_physp_get_port_num( p_physp ) ); } } @@ -411,21 +466,20 @@ __osm_pr_rcv_get_path_parms( "__osm_pr_rcv_get_path_parms: " "New smallest MTU = %u at destination port 0x%016" PRIx64 "\n", mtu, - osm_physp_get_port_guid( p_physp ) ); + cl_ntoh64(osm_physp_get_port_guid( p_physp )) ); } } if( rate > ib_port_info_compute_rate( p_pi ) ) { - rate = ib_port_info_compute_rate( p_pi ); if( osm_log_is_active( p_rcv->p_log, OSM_LOG_DEBUG ) ) { osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "__osm_pr_rcv_get_path_parms: " - "New smallest rate = %u at destination port 0x%016" PRIx64 "\n", + "New smallest rate = %u at destination port 0x%016" PRIx64 "\n", rate, - osm_physp_get_port_guid( p_physp ) ); + cl_ntoh64(osm_physp_get_port_guid( p_physp )) ); } } @@ -438,11 +492,12 @@ __osm_pr_rcv_get_path_parms( /* Determine if these values meet the user criteria + and adjust appropriately */ /* we silently ignore cases where only the MTU selector is defined */ - if ((comp_mask & IB_PR_COMPMASK_MTUSELEC) && - (comp_mask & IB_PR_COMPMASK_MTU)) + if ( ( comp_mask & IB_PR_COMPMASK_MTUSELEC ) && + ( comp_mask & IB_PR_COMPMASK_MTU ) ) { required_mtu = ib_path_rec_mtu( p_pr ); switch( ib_path_rec_mtu_sel( p_pr ) ) @@ -453,13 +508,22 @@ __osm_pr_rcv_get_path_parms( break; case 1: /* must be less than */ - if( mtu >= required_mtu ) - status = IB_NOT_FOUND; + if( mtu >= required_mtu ) + { + /* adjust to use the highest mtu + lower then the required one */ + if( required_mtu > 1 ) + mtu = required_mtu - 1; + else + status = IB_NOT_FOUND; + } break; case 2: /* exact match */ - if( mtu != required_mtu ) + if( mtu < required_mtu ) status = IB_NOT_FOUND; + else + mtu = required_mtu; break; case 3: /* largest available */ @@ -475,8 +539,8 @@ __osm_pr_rcv_get_path_parms( } /* we silently ignore cases where only the Rate selector is defined */ - if ((comp_mask & IB_PR_COMPMASK_RATESELEC) && - (comp_mask & IB_PR_COMPMASK_RATE)) + if ( ( comp_mask & IB_PR_COMPMASK_RATESELEC ) && + ( comp_mask & IB_PR_COMPMASK_RATE ) ) { required_rate = ib_path_rec_rate( p_pr ); switch( ib_path_rec_rate_sel( p_pr ) ) @@ -488,12 +552,21 @@ __osm_pr_rcv_get_path_parms( case 1: /* must be less than */ if( rate >= required_rate ) - status = IB_NOT_FOUND; + { + /* adjust the rate to use the highest rate + lower then the required one */ + if( required_rate > 2 ) + rate = required_rate - 1; + else + status = IB_NOT_FOUND; + } break; case 2: /* exact match */ - if( rate != required_rate ) + if( rate < required_rate ) status = IB_NOT_FOUND; + else + rate = required_rate; break; case 3: /* largest available */ @@ -509,17 +582,16 @@ __osm_pr_rcv_get_path_parms( } /* Verify the pkt_life_time */ - /* According to spec definition IBA 1.1 Table 171 PacketLifeTime description, + /* According to spec definition IBA 1.2 Table 205 PacketLifeTime description, for loopback paths, packetLifeTime shall be zero. */ if ( p_src_port == p_dest_port ) - /* This is loopback */ - pkt_life = 0; + pkt_life = 0; /* loopback */ else pkt_life = OSM_DEFAULT_SUBNET_TIMEOUT; /* we silently ignore cases where only the PktLife selector is defined */ - if ((comp_mask & IB_PR_COMPMASK_PKTLIFETIMESELEC) && - (comp_mask & IB_PR_COMPMASK_PKTLIFETIME)) + if ( ( comp_mask & IB_PR_COMPMASK_PKTLIFETIMESELEC ) && + ( comp_mask & IB_PR_COMPMASK_PKTLIFETIME ) ) { required_pkt_life = ib_path_rec_pkt_life( p_pr ); switch( ib_path_rec_pkt_life_sel( p_pr ) ) @@ -531,12 +603,21 @@ __osm_pr_rcv_get_path_parms( case 1: /* must be less than */ if( pkt_life >= required_pkt_life ) - status = IB_NOT_FOUND; + { + /* adjust the lifetime to use the highest possible + lower then the required one */ + if( required_pkt_life > 1 ) + pkt_life = required_pkt_life - 1; + else + status = IB_NOT_FOUND; + } break; case 2: /* exact match */ - if( pkt_life != required_pkt_life ) - status = IB_NOT_FOUND; + if( pkt_life < required_pkt_life ) + status = IB_NOT_FOUND; + else + pkt_life = required_pkt_life; break; case 3: /* smallest available */ @@ -551,12 +632,72 @@ __osm_pr_rcv_get_path_parms( } } + if (status != IB_SUCCESS) + goto Exit; + p_parms->mtu = mtu; p_parms->rate = rate; - p_parms->pkey = IB_DEFAULT_PKEY; - /* the pkt_life */ p_parms->pkt_life = pkt_life; - p_parms->sl = OSM_DEFAULT_SL; + + if( comp_mask & IB_PR_COMPMASK_RAWTRAFFIC && + cl_ntoh32( p_pr->hop_flow_raw ) & ( 1<<31 ) ) + pkey = osm_physp_find_common_pkey( p_physp, p_dest_physp ); + else if( comp_mask & IB_PR_COMPMASK_PKEY ) + { + pkey = p_pr->pkey; + if( !osm_physp_share_this_pkey( p_physp, p_dest_physp, pkey ) ) + { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "__osm_pr_rcv_get_path_parms: ERR 1F1A: " + "Ports do not share specified PKey 0x%04x\n", cl_ntoh16(pkey)); + status = IB_NOT_FOUND; + goto Exit; + } + } + else + { + pkey = osm_physp_find_common_pkey( p_physp, p_dest_physp ); + if ( !pkey ) + { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "__osm_pr_rcv_get_path_parms: ERR 1F1B: " + "Ports do not have any shared PKeys\n"); + status = IB_NOT_FOUND; + goto Exit; + } + } + + sl = OSM_DEFAULT_SL; + + if (pkey) { + p_prtn = (osm_prtn_t *)cl_qmap_get(&p_rcv->p_subn->prtn_pkey_tbl, + pkey & cl_ntoh16((uint16_t)~0x8000)); + if ( p_prtn == (osm_prtn_t *)cl_qmap_end(&p_rcv->p_subn->prtn_pkey_tbl) ) + { + /* this may be possible when pkey tables are created somehow in + previous runs or things are going wrong here */ + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "__osm_pr_rcv_get_path_parms: ERR 1F1C: " + "No partition found for PKey 0x%04x - using default SL %d\n", + cl_ntoh16(pkey), sl ); + } + else + sl = p_prtn->sl; + + /* reset pkey when raw traffic */ + if( comp_mask & IB_PR_COMPMASK_RAWTRAFFIC && + cl_ntoh32( p_pr->hop_flow_raw ) & ( 1<<31 ) ) + pkey = 0; + } + + if ( ( comp_mask & IB_PR_COMPMASK_SL ) && ib_path_rec_sl( p_pr ) != sl ) + { + status = IB_NOT_FOUND; + goto Exit; + } + + p_parms->pkey = pkey; + p_parms->sl = sl; Exit: OSM_LOG_EXIT( p_rcv->p_log ); @@ -584,35 +725,32 @@ __osm_pr_rcv_build_pr( p_src_physp = osm_port_get_default_phys_ptr( p_src_port ); p_dest_physp = osm_port_get_default_phys_ptr( p_dest_port ); - p_pr->dgid.unicast.prefix = - osm_physp_get_subnet_prefix( p_dest_physp ); - p_pr->dgid.unicast.interface_id = - osm_physp_get_port_guid( p_dest_physp ); + p_pr->dgid.unicast.prefix = osm_physp_get_subnet_prefix( p_dest_physp ); + p_pr->dgid.unicast.interface_id = osm_physp_get_port_guid( p_dest_physp ); - p_pr->sgid.unicast.prefix = - osm_physp_get_subnet_prefix( p_src_physp ); - p_pr->sgid.unicast.interface_id = - osm_physp_get_port_guid( p_src_physp ); + p_pr->sgid.unicast.prefix = osm_physp_get_subnet_prefix( p_src_physp ); + p_pr->sgid.unicast.interface_id = osm_physp_get_port_guid( p_src_physp ); p_pr->dlid = cl_hton16( dest_lid_ho ); p_pr->slid = cl_hton16( src_lid_ho ); + p_pr->hop_flow_raw &= cl_hton32(1<<31); + p_pr->pkey = p_parms->pkey; - p_pr->sl = p_parms->sl; + p_pr->sl = cl_hton16(p_parms->sl); p_pr->mtu = (uint8_t)(p_parms->mtu | 0x80); p_pr->rate = (uint8_t)(p_parms->rate | 0x80); - /* According to spec definition Table 171 PacketLifeTime description, + /* According to 1.2 spec definition Table 205 PacketLifeTime description, for loopback paths, packetLifeTime shall be zero. */ if ( p_src_port == p_dest_port ) - /* This is loopback */ - p_pr->pkt_life = 0x80; + p_pr->pkt_life = 0x80; /* loopback */ else p_pr->pkt_life = (uint8_t)(p_parms->pkt_life | 0x80); p_pr->preference = preference; - /* always return num_path = 0; so this is only the reversible */ + /* always return num_path = 0 so this is only the reversible component */ if (p_parms->reversible) p_pr->num_path = 0x80; @@ -635,7 +773,7 @@ __osm_pr_rcv_get_lid_pair_path( osm_path_parms_t path_parms; osm_path_parms_t rev_path_parms; osm_pr_item_t *p_pr_item; - ib_api_status_t status, rev_path_status; + ib_api_status_t status, rev_path_status; OSM_LOG_ENTER( p_rcv->p_log, __osm_pr_rcv_get_lid_pair_path ); @@ -657,7 +795,8 @@ __osm_pr_rcv_get_lid_pair_path( } status = __osm_pr_rcv_get_path_parms( p_rcv, p_pr, p_src_port, - p_dest_port, dest_lid_ho, comp_mask, &path_parms ); + p_dest_port, dest_lid_ho, + comp_mask, &path_parms ); if( status != IB_SUCCESS ) { @@ -667,11 +806,10 @@ __osm_pr_rcv_get_lid_pair_path( } /* now try the reversible path */ - rev_path_status = - __osm_pr_rcv_get_path_parms( - p_rcv, p_pr, p_dest_port, - p_src_port, src_lid_ho, comp_mask, &rev_path_parms ); - path_parms.reversible = (rev_path_status == IB_SUCCESS); + rev_path_status = __osm_pr_rcv_get_path_parms( p_rcv, p_pr, p_dest_port, + p_src_port, src_lid_ho, + comp_mask, &rev_path_parms ); + path_parms.reversible = ( rev_path_status == IB_SUCCESS ); /* did we get a Reversible Path compmask ? */ /* @@ -679,8 +817,9 @@ __osm_pr_rcv_get_lid_pair_path( rather then requiring non-reversible paths ... see Vol1 Ver1.2 p900 l16 */ - if (comp_mask & IB_PR_COMPMASK_REVERSIBLE) - if ( (! path_parms.reversible && (p_pr->num_path & 0x80))) + if( comp_mask & IB_PR_COMPMASK_REVERSIBLE ) + { + if( (! path_parms.reversible && ( p_pr->num_path & 0x80 ) ) ) { osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "__osm_pr_rcv_get_lid_pair_path: " @@ -689,7 +828,8 @@ __osm_pr_rcv_get_lid_pair_path( cl_qlock_pool_put( &p_rcv->pr_pool, &p_pr_item->pool_item ); p_pr_item = NULL; goto Exit; - }; + } + } __osm_pr_rcv_build_pr( p_rcv, p_src_port, p_dest_port, src_lid_ho, dest_lid_ho, preference, &path_parms, @@ -709,19 +849,19 @@ __osm_pr_rcv_get_port_pair_paths( IN const osm_port_t* const p_req_port, IN const osm_port_t* const p_src_port, IN const osm_port_t* const p_dest_port, - IN const ib_net64_t comp_mask, + IN const ib_net64_t comp_mask, IN cl_qlist_t* const p_list ) { const ib_path_rec_t* p_pr; const ib_sa_mad_t* p_sa_mad; osm_pr_item_t* p_pr_item; - uint16_t src_lid_min_ho; - uint16_t src_lid_max_ho; - uint16_t dest_lid_min_ho; - uint16_t dest_lid_max_ho; - uint16_t src_lid_ho; - uint16_t dest_lid_ho; - uint32_t path_num; + uint16_t src_lid_min_ho; + uint16_t src_lid_max_ho; + uint16_t dest_lid_min_ho; + uint16_t dest_lid_max_ho; + uint16_t src_lid_ho; + uint16_t dest_lid_ho; + uint32_t path_num; uint8_t preference; uintn_t iterations; uintn_t src_offset; @@ -740,13 +880,12 @@ __osm_pr_rcv_get_port_pair_paths( } /* Check that the req_port, src_port and dest_port all share a - pkey. The check is done on the default physical port of the ports */ + pkey. The check is done on the default physical port of the ports. */ if (osm_port_share_pkey(p_rcv->p_log, p_req_port, p_src_port) == FALSE || osm_port_share_pkey(p_rcv->p_log, p_req_port, p_dest_port) == FALSE || osm_port_share_pkey(p_rcv->p_log, p_src_port, p_dest_port) == FALSE ) { - /* One of the pairs doesn't share a pkey so the path is disqualified. - Exit */ + /* One of the pairs doesn't share a pkey so the path is disqualified. */ goto Exit; } @@ -758,10 +897,10 @@ __osm_pr_rcv_get_port_pair_paths( Thus, we assume every possible connection is valid. We desire to return high-quality paths first. - In OpenSM, higher quality mean least overlap with other paths. + In OpenSM, higher quality means least overlap with other paths. This is acheived in practice by returning paths with different LID value on each end, which means these - paths are more redundent that paths with the same LID repeated + paths are more redundant that paths with the same LID repeated on one side. For example, in OpenSM the paths between two endpoints with LMC = 1 might be as follows: @@ -770,7 +909,7 @@ __osm_pr_rcv_get_port_pair_paths( Port A, LID 2 <-> Port B, LID 3 Port A, LID 2 <-> Port B, LID 4 - The OpenSM unicast routing algorithms attempt to dispurse each path + The OpenSM unicast routing algorithms attempt to disperse each path to as varied a physical path as is reasonable. 1<->3 and 1<->4 have more physical overlap (hence less redundancy) than 1<->3 and 2<->4. @@ -782,10 +921,10 @@ __osm_pr_rcv_get_port_pair_paths( pref value = 0 paths 1 Redundant in one direction with other - pref value = 0 and pref value = 1 paths. + pref value = 0 and pref value = 1 paths 2 Not redundant in either direction with - other paths. + other paths 3-FF Unused @@ -794,9 +933,9 @@ __osm_pr_rcv_get_port_pair_paths( preference paths are preferred, as stated in the spec. The paths may not actually be physically redundant depending on the topology of the subnet, but the point of LMC > 0 is to offer redundancy, - so I assume the subnet is physically appropriate for the specified - LMC value. A more advanced implementation could inspect for physical - redundancy, but I'm not going to bother with that now. + so it is assumed that the subnet is physically appropriate for the + specified LMC value. A more advanced implementation would inspect for + physical redundancy, but I'm not going to bother with that now. */ /* @@ -824,12 +963,28 @@ __osm_pr_rcv_get_port_pair_paths( &src_lid_max_ho ); } + if ( src_lid_min_ho == 0 ) + { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "__osm_pr_rcv_get_port_pair_paths: ERR 1F20:" + "Obtained source LID of 0. No such LID possible\n"); + goto Exit; + } + + if ( dest_lid_min_ho == 0 ) + { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "__osm_pr_rcv_get_port_pair_paths: ERR 1F21:" + "Obtained destination LID of 0. No such LID possible\n"); + goto Exit; + } + if( osm_log_is_active( p_rcv->p_log, OSM_LOG_DEBUG ) ) { osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "__osm_pr_rcv_get_port_pair_paths: " - "Src LIDs [0x%X,0x%X], " - "Dest LIDs [0x%X,0x%X]\n", + "Src LIDs [0x%X-0x%X], " + "Dest LIDs [0x%X-0x%X]\n", src_lid_min_ho, src_lid_max_ho, dest_lid_min_ho, dest_lid_max_ho ); } @@ -838,15 +993,15 @@ __osm_pr_rcv_get_port_pair_paths( dest_lid_ho = dest_lid_min_ho; /* - Preferred paths come first in OpenSM. + Preferred paths come first in OpenSM */ preference = 0; path_num = 0; /* If SubnAdmGet, assume NumbPaths 1 (1.2 erratum) */ - if (p_sa_mad->method != IB_MAD_METHOD_GET) + if( p_sa_mad->method != IB_MAD_METHOD_GET ) if( comp_mask & IB_PR_COMPMASK_NUMBPATH ) - iterations = p_pr->num_path & 0x7F; + iterations = ib_path_rec_num_path( p_pr ); else iterations = (uintn_t)(-1); else @@ -859,7 +1014,8 @@ __osm_pr_rcv_get_port_pair_paths( */ p_pr_item = __osm_pr_rcv_get_lid_pair_path( p_rcv, p_pr, - p_src_port, p_dest_port, src_lid_ho, dest_lid_ho, + p_src_port, p_dest_port, + src_lid_ho, dest_lid_ho, comp_mask, preference ); if( p_pr_item ) @@ -877,7 +1033,7 @@ __osm_pr_rcv_get_port_pair_paths( } /* - Check if we've accumulated all the user cares to see. + Check if we've accumulated all the paths that the user cares to see */ if( path_num == iterations ) goto Exit; @@ -895,7 +1051,7 @@ __osm_pr_rcv_get_port_pair_paths( dest_offset = 0; /* - Iterate over the remaining paths. + Iterate over the remaining paths */ while( path_num < iterations ) { @@ -925,7 +1081,8 @@ __osm_pr_rcv_get_port_pair_paths( continue; /* already reported */ p_pr_item = __osm_pr_rcv_get_lid_pair_path( p_rcv, p_pr, - p_src_port, p_dest_port, src_lid_ho, dest_lid_ho, + p_src_port, p_dest_port, + src_lid_ho, dest_lid_ho, comp_mask, preference ); if( p_pr_item ) @@ -946,8 +1103,8 @@ static ib_net16_t __osm_pr_rcv_get_end_points( IN osm_pr_rcv_t* const p_rcv, IN const osm_madw_t* const p_madw, - OUT const osm_port_t** const pp_src_port, - OUT const osm_port_t** const pp_dest_port ) + OUT const osm_port_t** const pp_src_port, + OUT const osm_port_t** const pp_dest_port ) { const ib_path_rec_t* p_pr; const ib_sa_mad_t* p_sa_mad; @@ -972,32 +1129,27 @@ __osm_pr_rcv_get_end_points( into the endpoints. */ - if( comp_mask & IB_PR_COMPMASK_PKEY ) + if( comp_mask & IB_PR_COMPMASK_SGID ) { - if( p_pr->pkey != IB_DEFAULT_PKEY ) + if ( ! ib_gid_is_link_local ( &p_pr->sgid ) ) { - if ( p_sa_mad->method == IB_MAD_METHOD_GET ) - sa_status = IB_SA_MAD_STATUS_NO_RECORDS; - *pp_src_port = 0; - *pp_dest_port = 0; - goto Exit; - } - } + if ( ib_gid_get_subnet_prefix ( &p_pr->sgid ) != p_rcv->p_subn->opt.subnet_prefix ) + { + /* + This 'error' is the client's fault (bad gid) so + don't enter it as an error in our own log. + Return an error response to the client. + */ + osm_log( p_rcv->p_log, OSM_LOG_VERBOSE, + "__osm_pr_rcv_get_end_points: " + "Non local SGID subnet prefix 0x%016" PRIx64 "\n", + cl_ntoh64( p_pr->sgid.unicast.prefix ) ); - if( comp_mask & IB_PR_COMPMASK_SL ) - { - if( p_pr->sl != OSM_DEFAULT_SL ) - { - if ( p_sa_mad->method == IB_MAD_METHOD_GET ) - sa_status = IB_SA_MAD_STATUS_NO_RECORDS; - *pp_src_port = 0; - *pp_dest_port = 0; - goto Exit; + sa_status = IB_SA_MAD_STATUS_INVALID_GID; + goto Exit; + } } - } - if( p_sa_mad->comp_mask & IB_PR_COMPMASK_SGID ) - { *pp_src_port = (osm_port_t*)cl_qmap_get( &p_rcv->p_subn->port_guid_tbl, p_pr->sgid.unicast.interface_id ); @@ -1012,7 +1164,7 @@ __osm_pr_rcv_get_end_points( */ osm_log( p_rcv->p_log, OSM_LOG_VERBOSE, "__osm_pr_rcv_get_end_points: " - "No source port with GUID = 0x%016" PRIx64 "\n", + "No source port with GUID 0x%016" PRIx64 "\n", cl_ntoh64( p_pr->sgid.unicast.interface_id) ); sa_status = IB_SA_MAD_STATUS_INVALID_GID; @@ -1022,13 +1174,12 @@ __osm_pr_rcv_get_end_points( else { *pp_src_port = 0; - if( p_sa_mad->comp_mask & IB_PR_COMPMASK_SLID ) + if( comp_mask & IB_PR_COMPMASK_SLID ) { status = cl_ptr_vector_at( &p_rcv->p_subn->port_lid_tbl, cl_ntoh16(p_pr->slid), (void**)pp_src_port ); - if( ( (status != CL_SUCCESS) || (*pp_src_port == NULL) ) && - (p_sa_mad->method == IB_MAD_METHOD_GET) ) + if( (status != CL_SUCCESS) || (*pp_src_port == NULL) ) { /* This 'error' is the client's fault (bad lid) so @@ -1046,8 +1197,28 @@ __osm_pr_rcv_get_end_points( } } - if( p_sa_mad->comp_mask & IB_PR_COMPMASK_DGID ) + if( comp_mask & IB_PR_COMPMASK_DGID ) { + if ( ! ib_gid_is_link_local ( &p_pr->dgid ) ) + { + if ( ! ib_gid_is_multicast ( &p_pr->dgid ) && + ib_gid_get_subnet_prefix ( &p_pr->dgid ) != p_rcv->p_subn->opt.subnet_prefix ) + { + /* + This 'error' is the client's fault (bad gid) so + don't enter it as an error in our own log. + Return an error response to the client. + */ + osm_log( p_rcv->p_log, OSM_LOG_VERBOSE, + "__osm_pr_rcv_get_end_points: " + "Non local DGID subnet prefix 0x%016" PRIx64 "\n", + cl_ntoh64( p_pr->dgid.unicast.prefix ) ); + + sa_status = IB_SA_MAD_STATUS_INVALID_GID; + goto Exit; + } + } + *pp_dest_port = (osm_port_t*)cl_qmap_get( &p_rcv->p_subn->port_guid_tbl, p_pr->dgid.unicast.interface_id ); @@ -1062,7 +1233,7 @@ __osm_pr_rcv_get_end_points( */ osm_log( p_rcv->p_log, OSM_LOG_VERBOSE, "__osm_pr_rcv_get_end_points: " - "No dest port with GUID = 0x%016" PRIx64 "\n", + "No dest port with GUID 0x%016" PRIx64 "\n", cl_ntoh64( p_pr->dgid.unicast.interface_id) ); sa_status = IB_SA_MAD_STATUS_INVALID_GID; @@ -1072,13 +1243,12 @@ __osm_pr_rcv_get_end_points( else { *pp_dest_port = 0; - if( p_sa_mad->comp_mask & IB_PR_COMPMASK_DLID ) + if( comp_mask & IB_PR_COMPMASK_DLID ) { status = cl_ptr_vector_at( &p_rcv->p_subn->port_lid_tbl, cl_ntoh16(p_pr->dlid), (void**)pp_dest_port ); - if( ( (status != CL_SUCCESS) || (*pp_dest_port == NULL) ) && - (p_sa_mad->method == IB_MAD_METHOD_GET) ) + if( (status != CL_SUCCESS) || (*pp_dest_port == NULL) ) { /* This 'error' is the client's fault (bad lid) so @@ -1108,7 +1278,7 @@ __osm_pr_rcv_process_world( IN osm_pr_rcv_t* const p_rcv, IN const osm_madw_t* const p_madw, IN const osm_port_t* const requester_port, - IN const ib_net64_t comp_mask, + IN const ib_net64_t comp_mask, IN cl_qlist_t* const p_list ) { const cl_qmap_t* p_tbl; @@ -1154,7 +1324,7 @@ __osm_pr_rcv_process_half( IN const osm_port_t* const requester_port, IN const osm_port_t* const p_src_port, IN const osm_port_t* const p_dest_port, - IN const ib_net64_t comp_mask, + IN const ib_net64_t comp_mask, IN cl_qlist_t* const p_list ) { const cl_qmap_t* p_tbl; @@ -1208,7 +1378,7 @@ __osm_pr_rcv_process_pair( IN const osm_port_t* const requester_port, IN const osm_port_t* const p_src_port, IN const osm_port_t* const p_dest_port, - IN const ib_net64_t comp_mask, + IN const ib_net64_t comp_mask, IN cl_qlist_t* const p_list ) { OSM_LOG_ENTER( p_rcv->p_log, __osm_pr_rcv_process_pair ); @@ -1221,42 +1391,41 @@ __osm_pr_rcv_process_pair( /********************************************************************** *********************************************************************/ -static -void +static void __search_mgrp_by_mgid( - IN cl_map_item_t* const p_map_item, - IN void* context ) + IN cl_map_item_t* const p_map_item, + IN void* context ) { - osm_mgrp_t* p_mgrp = (osm_mgrp_t*)p_map_item; + osm_mgrp_t* p_mgrp = (osm_mgrp_t*)p_map_item; osm_sa_pr_mcmr_search_ctxt_t *p_ctxt = (osm_sa_pr_mcmr_search_ctxt_t *) context; - const ib_gid_t *p_recvd_mgid; - osm_pr_rcv_t *p_rcv; - /* uint32_t i; */ + const ib_gid_t *p_recvd_mgid; + osm_pr_rcv_t *p_rcv; + /* uint32_t i; */ p_recvd_mgid = p_ctxt->p_mgid; p_rcv = p_ctxt->p_rcv; /* ignore groups marked for deletion */ - if (p_mgrp->to_be_deleted) + if ( p_mgrp->to_be_deleted ) return; /* compare entire MGID so different scope will not sneak in for the same MGID */ - if (cl_memcmp(&p_mgrp->mcmember_rec.mgid, + if ( memcmp( &p_mgrp->mcmember_rec.mgid, p_recvd_mgid, - sizeof(ib_gid_t))) + sizeof(ib_gid_t) ) ) return; #if 0 for ( i = 0 ; i < sizeof(p_mgrp->mcmember_rec.mgid.multicast.raw_group_id); i++) { - if (p_mgrp->mcmember_rec.mgid.multicast.raw_group_id[i] != - p_recvd_mgid->mgid.multicast.raw_group_id[i]) + if ( p_mgrp->mcmember_rec.mgid.multicast.raw_group_id[i] != + p_recvd_mgid->mgid.multicast.raw_group_id[i] ) return; } #endif - if(p_ctxt->p_mgrp) + if( p_ctxt->p_mgrp ) { osm_log( p_rcv->p_log, OSM_LOG_ERROR, "__search_mgrp_by_mgid: ERR 1F08: " @@ -1264,16 +1433,15 @@ __search_mgrp_by_mgid( return; } p_ctxt->p_mgrp = p_mgrp; - } /********************************************************************** **********************************************************************/ static ib_api_status_t __get_mgrp_by_mgid( - IN osm_pr_rcv_t* const p_rcv, - IN ib_path_rec_t* p_recvd_path_rec, - OUT osm_mgrp_t **pp_mgrp) + IN osm_pr_rcv_t* const p_rcv, + IN ib_path_rec_t* p_recvd_path_rec, + OUT osm_mgrp_t ** pp_mgrp ) { osm_sa_pr_mcmr_search_ctxt_t mcmr_search_context; @@ -1285,7 +1453,7 @@ __get_mgrp_by_mgid( __search_mgrp_by_mgid, &mcmr_search_context); - if(mcmr_search_context.p_mgrp == NULL) + if( mcmr_search_context.p_mgrp == NULL ) { return IB_NOT_FOUND; } @@ -1296,17 +1464,16 @@ __get_mgrp_by_mgid( /********************************************************************** **********************************************************************/ -static -osm_mgrp_t * +static osm_mgrp_t * __get_mgrp_by_mlid( IN const osm_pr_rcv_t* const p_rcv, - IN ib_net16_t const mlid) + IN ib_net16_t const mlid ) { - cl_map_item_t *map_item; + cl_map_item_t * map_item; - map_item = cl_qmap_get(&p_rcv->p_subn->mgrp_mlid_tbl, - mlid); - if(map_item == cl_qmap_end(&p_rcv->p_subn->mgrp_mlid_tbl)) + map_item = cl_qmap_get( &p_rcv->p_subn->mgrp_mlid_tbl, mlid ); + + if( map_item == cl_qmap_end(&p_rcv->p_subn->mgrp_mlid_tbl) ) { return NULL; } @@ -1414,14 +1581,15 @@ __osm_pr_match_mgrp_attributes( if( comp_mask & IB_PR_COMPMASK_SL ) { - if( ( p_pr->sl & 0xf ) != sl ) + if( ib_path_rec_sl( p_pr ) != sl ) goto Exit; } /* If SubnAdmGet, assume NumbPaths of 1 (1.2 erratum) */ - if( ( comp_mask & IB_PR_COMPMASK_NUMBPATH ) && ( p_sa_mad->method != IB_MAD_METHOD_GET ) ) + if( ( comp_mask & IB_PR_COMPMASK_NUMBPATH ) && + ( p_sa_mad->method != IB_MAD_METHOD_GET ) ) { - if( ( p_pr->num_path & 0x7f ) == 0 ) + if( ib_path_rec_num_path( p_pr ) == 0 ) goto Exit; } @@ -1452,7 +1620,7 @@ __osm_pr_match_mgrp_attributes( /********************************************************************** **********************************************************************/ -static boolean_t +static int __osm_pr_rcv_check_mcast_dest( IN osm_pr_rcv_t* const p_rcv, IN const osm_madw_t* const p_madw ) @@ -1460,7 +1628,7 @@ __osm_pr_rcv_check_mcast_dest( const ib_path_rec_t* p_pr; const ib_sa_mad_t* p_sa_mad; ib_net64_t comp_mask; - boolean_t is_multicast = FALSE; + int is_multicast = 0; OSM_LOG_ENTER( p_rcv->p_log, __osm_pr_rcv_check_mcast_dest ); @@ -1480,11 +1648,14 @@ __osm_pr_rcv_check_mcast_dest( { if( cl_ntoh16( p_pr->dlid ) >= IB_LID_MCAST_START_HO && cl_ntoh16( p_pr->dlid ) <= IB_LID_MCAST_END_HO ) - is_multicast = TRUE; + is_multicast = 1; else if( is_multicast ) + { osm_log( p_rcv->p_log, OSM_LOG_ERROR, "__osm_pr_rcv_check_mcast_dest: ERR 1F12: " "PathRecord request indicates MGID but not MLID\n" ); + is_multicast = -1; + } } Exit: @@ -1502,16 +1673,16 @@ __osm_pr_rcv_respond( { osm_madw_t* p_resp_madw; const ib_sa_mad_t* p_sa_mad; - ib_sa_mad_t* p_resp_sa_mad; - size_t num_rec, pre_trim_num_rec; + ib_sa_mad_t* p_resp_sa_mad; + size_t num_rec, pre_trim_num_rec; #ifndef VENDOR_RMPP_SUPPORT - size_t trim_num_rec; + size_t trim_num_rec; #endif ib_path_rec_t* p_resp_pr; ib_api_status_t status; - const ib_sa_mad_t* p_rcvd_mad = osm_madw_get_sa_mad_ptr( p_madw ); - osm_pr_item_t* p_pr_item; - uint32_t i; + const ib_sa_mad_t* p_rcvd_mad = osm_madw_get_sa_mad_ptr( p_madw ); + osm_pr_item_t* p_pr_item; + uint32_t i; OSM_LOG_ENTER( p_rcv->p_log, __osm_pr_rcv_respond ); @@ -1521,22 +1692,30 @@ __osm_pr_rcv_respond( * C15-0.1.30: * If we do a SubnAdmGet and got more than one record it is an error ! */ - if ( (p_rcvd_mad->method == IB_MAD_METHOD_GET) && - (num_rec > 1)) { - osm_log( p_rcv->p_log, OSM_LOG_ERROR, - "__osm_pr_rcv_respond: ERR 1F13: " - "Got more than one record for SubnAdmGet (%u)\n", - num_rec ); - osm_sa_send_error( p_rcv->p_resp, p_madw, - IB_SA_MAD_STATUS_TOO_MANY_RECORDS); - /* need to set the mem free ... */ - p_pr_item = (osm_pr_item_t*)cl_qlist_remove_head( p_list ); - while( p_pr_item != (osm_pr_item_t*)cl_qlist_end( p_list ) ) + if (p_rcvd_mad->method == IB_MAD_METHOD_GET) + { + if (num_rec == 0) { - cl_qlock_pool_put( &p_rcv->pr_pool, &p_pr_item->pool_item ); + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_SA_MAD_STATUS_NO_RECORDS ); + goto Exit; + } + if (num_rec > 1) + { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "__osm_pr_rcv_respond: ERR 1F13: " + "Got more than one record for SubnAdmGet (%zu)\n", + num_rec ); + osm_sa_send_error( p_rcv->p_resp, p_madw, + IB_SA_MAD_STATUS_TOO_MANY_RECORDS ); + /* need to set the mem free ... */ p_pr_item = (osm_pr_item_t*)cl_qlist_remove_head( p_list ); + while( p_pr_item != (osm_pr_item_t*)cl_qlist_end( p_list ) ) + { + cl_qlock_pool_put( &p_rcv->pr_pool, &p_pr_item->pool_item ); + p_pr_item = (osm_pr_item_t*)cl_qlist_remove_head( p_list ); + } + goto Exit; } - goto Exit; } pre_trim_num_rec = num_rec; @@ -1554,20 +1733,18 @@ __osm_pr_rcv_respond( osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "__osm_pr_rcv_respond: " - "Generating response with %u records\n", num_rec ); + "Generating response with %zu records\n", num_rec ); if ((p_rcvd_mad->method == IB_MAD_METHOD_GET) && (num_rec == 0)) { - osm_sa_send_error( p_rcv->p_resp, p_madw, - IB_SA_MAD_STATUS_NO_RECORDS ); + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_SA_MAD_STATUS_NO_RECORDS ); goto Exit; } /* * Get a MAD to reply. Address of Mad is in the received mad_wrapper */ - p_resp_madw = osm_mad_pool_get( p_rcv->p_mad_pool, - p_madw->h_bind, + p_resp_madw = osm_mad_pool_get( p_rcv->p_mad_pool, p_madw->h_bind, num_rec * sizeof(ib_path_rec_t) + IB_SA_MAD_HDR_SIZE, &p_madw->mad_addr ); if( !p_resp_madw ) @@ -1582,22 +1759,19 @@ __osm_pr_rcv_respond( cl_qlock_pool_put( &p_rcv->pr_pool, &p_pr_item->pool_item ); } - osm_sa_send_error( p_rcv->p_resp, p_madw, - IB_SA_MAD_STATUS_NO_RESOURCES ); - + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_SA_MAD_STATUS_NO_RESOURCES ); goto Exit; } p_sa_mad = osm_madw_get_sa_mad_ptr( p_madw ); p_resp_sa_mad = osm_madw_get_sa_mad_ptr( p_resp_madw ); - cl_memcpy( p_resp_sa_mad, p_sa_mad, IB_SA_MAD_HDR_SIZE ); + memcpy( p_resp_sa_mad, p_sa_mad, IB_SA_MAD_HDR_SIZE ); p_resp_sa_mad->method |= IB_MAD_METHOD_RESP_MASK; - /* C15-0.1.5 - always return SM_Key = 0 (table 151 p 782) */ + /* C15-0.1.5 - always return SM_Key = 0 (table 185 p 884) */ p_resp_sa_mad->sm_key = 0; /* Fill in the offset (paylen will be done by the rmpp SAR) */ - p_resp_sa_mad->attr_offset = - ib_get_attr_offset( sizeof(ib_path_rec_t) ); + p_resp_sa_mad->attr_offset = ib_get_attr_offset( sizeof(ib_path_rec_t) ); p_resp_pr = (ib_path_rec_t*)ib_sa_mad_get_payload_ptr( p_resp_sa_mad ); @@ -1636,7 +1810,6 @@ __osm_pr_rcv_respond( "__osm_pr_rcv_respond: ERR 1F15: " "Unable to send MAD (%s)\n", ib_get_err_str( status ) ); /* osm_mad_pool_put( p_rcv->p_mad_pool, p_resp_madw ); */ - goto Exit; } Exit: @@ -1657,36 +1830,36 @@ osm_pr_rcv_process( cl_qlist_t pr_list; ib_net16_t sa_status; osm_port_t* requester_port; + int ret; OSM_LOG_ENTER( p_rcv->p_log, osm_pr_rcv_process ); CL_ASSERT( p_madw ); - /* update the requester physical port. */ - requester_port = - osm_get_port_by_mad_addr(p_rcv->p_log, - p_rcv->p_subn, - osm_madw_get_mad_addr_ptr(p_madw) ); - if (requester_port == NULL) - { - osm_log( p_rcv->p_log, OSM_LOG_ERROR, - "osm_pr_rcv_process: ERR 1F16: " - "Cannot find requester physical port\n" ); - goto Exit; - } - p_sa_mad = osm_madw_get_sa_mad_ptr( p_madw ); p_pr = (ib_path_rec_t*)ib_sa_mad_get_payload_ptr( p_sa_mad ); CL_ASSERT( p_sa_mad->attr_id == IB_MAD_ATTR_PATH_RECORD ); + /* we only support SubnAdmGet and SubnAdmGetTable methods */ if ((p_sa_mad->method != IB_MAD_METHOD_GET) && (p_sa_mad->method != IB_MAD_METHOD_GETTABLE)) { osm_log( p_rcv->p_log, OSM_LOG_ERROR, "osm_pr_rcv_process: ERR 1F17: " "Unsupported Method (%s)\n", ib_get_sa_method_str( p_sa_mad->method ) ); - osm_sa_send_error( p_rcv->p_resp, p_madw, IB_SA_MAD_STATUS_REQ_INVALID); + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_MAD_STATUS_UNSUP_METHOD_ATTR ); + goto Exit; + } + + /* update the requester physical port. */ + requester_port = osm_get_port_by_mad_addr( p_rcv->p_log, p_rcv->p_subn, + osm_madw_get_mad_addr_ptr( p_madw ) ); + if( requester_port == NULL ) + { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "osm_pr_rcv_process: ERR 1F16: " + "Cannot find requester physical port\n" ); goto Exit; } @@ -1702,7 +1875,15 @@ osm_pr_rcv_process( cl_plock_acquire( p_rcv->p_lock ); /* Handle multicast destinations separately */ - if( __osm_pr_rcv_check_mcast_dest( p_rcv, p_madw ) ) + if( (ret = __osm_pr_rcv_check_mcast_dest( p_rcv, p_madw )) < 0 ) + { + /* Multicast DGID with unicast DLID */ + cl_plock_release( p_rcv->p_lock ); + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_MAD_STATUS_INVALID_FIELD ); + goto Exit; + } + + if(ret > 0) goto McastDest; osm_log( p_rcv->p_log, OSM_LOG_DEBUG, @@ -1712,37 +1893,36 @@ osm_pr_rcv_process( sa_status = __osm_pr_rcv_get_end_points( p_rcv, p_madw, &p_src_port, &p_dest_port ); - if( sa_status != IB_SA_MAD_STATUS_SUCCESS ) + if( sa_status == IB_SA_MAD_STATUS_SUCCESS ) { - cl_plock_release( p_rcv->p_lock ); - osm_sa_send_error( p_rcv->p_resp, p_madw, sa_status ); - goto Exit; - } - - /* - What happens next depends on the type of endpoint information - that was specified.... - */ - if( p_src_port ) - { - if( p_dest_port ) - __osm_pr_rcv_process_pair( p_rcv, p_madw, requester_port, p_src_port, p_dest_port, - p_sa_mad->comp_mask, &pr_list ); - else - __osm_pr_rcv_process_half( p_rcv, p_madw, requester_port, p_src_port, NULL, - p_sa_mad->comp_mask, &pr_list ); - } - else - { - if( p_dest_port ) - __osm_pr_rcv_process_half( p_rcv, p_madw, requester_port, NULL, p_dest_port, - p_sa_mad->comp_mask, &pr_list ); + /* + What happens next depends on the type of endpoint information + that was specified.... + */ + if( p_src_port ) + { + if( p_dest_port ) + __osm_pr_rcv_process_pair( p_rcv, p_madw, requester_port, + p_src_port, p_dest_port, + p_sa_mad->comp_mask, &pr_list ); + else + __osm_pr_rcv_process_half( p_rcv, p_madw, requester_port, + p_src_port, NULL, + p_sa_mad->comp_mask, &pr_list ); + } else - /* - Katie, bar the door! - */ - __osm_pr_rcv_process_world( p_rcv, p_madw, requester_port, - p_sa_mad->comp_mask, &pr_list ); + { + if( p_dest_port ) + __osm_pr_rcv_process_half( p_rcv, p_madw, requester_port, + NULL, p_dest_port, + p_sa_mad->comp_mask, &pr_list ); + else + /* + Katie, bar the door! + */ + __osm_pr_rcv_process_world( p_rcv, p_madw, requester_port, + p_sa_mad->comp_mask, &pr_list ); + } } goto Unlock; @@ -1764,7 +1944,7 @@ osm_pr_rcv_process( if ( p_mgrp ) { /* Make sure the rest of the PathRecord matches the MC group attributes */ - status = __osm_pr_match_mgrp_attributes( p_rcv, p_madw, p_mgrp); + status = __osm_pr_match_mgrp_attributes( p_rcv, p_madw, p_mgrp ); if ( status == IB_SUCCESS ) { p_pr_item = (osm_pr_item_t*)cl_qlock_pool_get( &p_rcv->pr_pool ); @@ -1796,7 +1976,7 @@ osm_pr_rcv_process( /* SL, Hop Limit, and Flow Label */ ib_member_get_sl_flow_hop( p_mgrp->mcmember_rec.sl_flow_hop, &sl, &flow_label, &hop_limit ); - p_pr_item->path_rec.sl = sl; + p_pr_item->path_rec.sl = cl_hton16( sl ); p_pr_item->path_rec.hop_flow_raw = (uint32_t)(hop_limit) | (flow_label << 8); @@ -1814,12 +1994,13 @@ osm_pr_rcv_process( } } - /* Now, (finally) respond to the PathRecord request */ - Unlock: cl_plock_release( p_rcv->p_lock ); + + /* Now, (finally) respond to the PathRecord request */ __osm_pr_rcv_respond( p_rcv, p_madw, &pr_list ); Exit: OSM_LOG_EXIT( p_rcv->p_log ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_sa_path_record_ctrl.c b/trunk/ulp/opensm/user/opensm/osm_sa_path_record_ctrl.c index 52fa1723..ec13fdc2 100644 --- a/trunk/ulp/opensm/user/opensm/osm_sa_path_record_ctrl.c +++ b/trunk/ulp/opensm/user/opensm/osm_sa_path_record_ctrl.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Implementation of osm_pr_rcv_ctrl_t. @@ -44,15 +45,11 @@ * $Revision: 1.5 $ */ -/* - Next available error code: 0x203 -*/ - #if HAVE_CONFIG_H # include #endif /* HAVE_CONFIG_H */ -#include +#include #include #include @@ -74,7 +71,7 @@ void osm_pr_rcv_ctrl_construct( IN osm_pr_rcv_ctrl_t* const p_ctrl ) { - cl_memclr( p_ctrl, sizeof(*p_ctrl) ); + memset( p_ctrl, 0, sizeof(*p_ctrl) ); p_ctrl->h_disp = CL_DISP_INVALID_HANDLE; } @@ -126,3 +123,4 @@ osm_pr_rcv_ctrl_init( return( status ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_sa_pkey_record.c b/trunk/ulp/opensm/user/opensm/osm_sa_pkey_record.c index cfdcd10d..60d8d937 100644 --- a/trunk/ulp/opensm/user/opensm/osm_sa_pkey_record.c +++ b/trunk/ulp/opensm/user/opensm/osm_sa_pkey_record.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,16 +32,12 @@ */ -/* - Next available error code: 0x403 -*/ - #if HAVE_CONFIG_H # include #endif /* HAVE_CONFIG_H */ +#include #include -#include #include #include #include @@ -59,19 +55,17 @@ typedef struct _osm_pkey_item { cl_pool_item_t pool_item; - ib_pkey_table_record_t rec; - + ib_pkey_table_record_t rec; } osm_pkey_item_t; typedef struct _osm_pkey_search_ctxt { const ib_pkey_table_record_t* p_rcvd_rec; ib_net64_t comp_mask; - uint16_t block_num; + uint16_t block_num; cl_qlist_t* p_list; osm_pkey_rec_rcv_t* p_rcv; const osm_physp_t* p_req_physp; - } osm_pkey_search_ctxt_t; /********************************************************************** @@ -80,7 +74,7 @@ void osm_pkey_rec_rcv_construct( IN osm_pkey_rec_rcv_t* const p_rcv ) { - cl_memclr( p_rcv, sizeof(*p_rcv) ); + memset( p_rcv, 0, sizeof(*p_rcv) ); cl_qlock_pool_construct( &p_rcv->pool ); } @@ -134,26 +128,17 @@ osm_pkey_rec_rcv_init( **********************************************************************/ void __osm_sa_pkey_create( - IN osm_pkey_rec_rcv_t* const p_rcv, - IN osm_physp_t* const p_physp, + IN osm_pkey_rec_rcv_t* const p_rcv, + IN osm_physp_t* const p_physp, IN osm_pkey_search_ctxt_t* const p_ctxt, - IN uint16_t block) + IN uint16_t block ) { - osm_pkey_item_t* p_rec_item; - uint16_t lid; - ib_api_status_t status = IB_SUCCESS; + osm_pkey_item_t* p_rec_item; + uint16_t lid; + ib_api_status_t status = IB_SUCCESS; OSM_LOG_ENTER( p_rcv->p_log, __osm_sa_pkey_create ); - if (p_physp->p_node->node_info.node_type != IB_NODE_TYPE_SWITCH) - { - lid = osm_physp_get_port_info_ptr( p_physp )->base_lid; - } - else - { - lid = osm_node_get_base_lid( p_physp->p_node, 0 ); - } - p_rec_item = (osm_pkey_item_t*)cl_qlock_pool_get( &p_rcv->pool ); if( p_rec_item == NULL ) { @@ -164,9 +149,18 @@ __osm_sa_pkey_create( goto Exit; } + if (p_physp->p_node->node_info.node_type != IB_NODE_TYPE_SWITCH) + { + lid = osm_physp_get_port_info_ptr( p_physp )->base_lid; + } + else + { + lid = osm_node_get_base_lid( p_physp->p_node, 0 ); + } + if( osm_log_is_active( p_rcv->p_log, OSM_LOG_DEBUG ) ) { - osm_log( p_rcv->p_log, OSM_LOG_ERROR, + osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "__osm_sa_pkey_create: " "New P_Key table for: port 0x%016" PRIx64 ", lid 0x%X, port# 0x%X Block:%u\n", @@ -176,13 +170,13 @@ __osm_sa_pkey_create( ); } - cl_memclr( &p_rec_item->rec, sizeof( p_rec_item->rec ) ); + memset( &p_rec_item->rec, 0, sizeof( p_rec_item->rec ) ); p_rec_item->rec.lid = lid; p_rec_item->rec.block_num = block; p_rec_item->rec.port_num = osm_physp_get_port_num( p_physp ); p_rec_item->rec.pkey_tbl = - *(osm_pkey_tbl_block_get(osm_physp_get_pkey_tbl(p_physp) , block)); + *(osm_pkey_tbl_block_get(osm_physp_get_pkey_tbl(p_physp), block)); cl_qlist_insert_tail( p_ctxt->p_list, (cl_list_item_t*)&p_rec_item->pool_item ); @@ -195,8 +189,8 @@ __osm_sa_pkey_create( **********************************************************************/ void __osm_sa_pkey_check_physp( - IN osm_pkey_rec_rcv_t* const p_rcv, - IN osm_physp_t* const p_physp, + IN osm_pkey_rec_rcv_t* const p_rcv, + IN osm_physp_t* const p_physp, osm_pkey_search_ctxt_t* const p_ctxt ) { ib_net64_t comp_mask = p_ctxt->comp_mask; @@ -213,22 +207,21 @@ __osm_sa_pkey_check_physp( { num_blocks = osm_pkey_tbl_get_num_blocks( osm_physp_get_pkey_tbl( p_physp )); - for (block = 0 ; block < num_blocks ; block++) { + for (block = 0; block < num_blocks; block++) { __osm_sa_pkey_create( p_rcv, p_physp, p_ctxt, block ); } } - //Exit: OSM_LOG_EXIT( p_rcv->p_log ); } /********************************************************************** **********************************************************************/ -void +static void __osm_sa_pkey_by_comp_mask( - IN osm_pkey_rec_rcv_t* const p_rcv, - IN const osm_port_t* const p_port, - osm_pkey_search_ctxt_t* const p_ctxt ) + IN osm_pkey_rec_rcv_t* const p_rcv, + IN const osm_port_t* const p_port, + osm_pkey_search_ctxt_t* const p_ctxt ) { const ib_pkey_table_record_t* p_rcvd_rec; ib_net64_t comp_mask; @@ -246,7 +239,7 @@ __osm_sa_pkey_by_comp_mask( /* if this is a switch port we can search all ports otherwise we must be looking on port 0 */ - if ( p_port->p_node->node_info.node_type != IB_NODE_TYPE_SWITCH) + if ( p_port->p_node->node_info.node_type != IB_NODE_TYPE_SWITCH ) { /* we put it in the comp mask and port num */ port_num = p_port->default_port_num; @@ -303,10 +296,10 @@ __osm_sa_pkey_by_comp_mask( /********************************************************************** **********************************************************************/ -void +static void __osm_sa_pkey_by_comp_mask_cb( IN cl_map_item_t* const p_map_item, - IN void* context ) + IN void* context ) { const osm_port_t* const p_port = (osm_port_t*)p_map_item; osm_pkey_search_ctxt_t* const p_ctxt = (osm_pkey_search_ctxt_t *)context; @@ -323,23 +316,23 @@ osm_pkey_rec_rcv_process( { const ib_sa_mad_t* p_rcvd_mad; const ib_pkey_table_record_t* p_rcvd_rec; - const cl_ptr_vector_t* p_tbl; + const cl_ptr_vector_t* p_tbl; const osm_port_t* p_port = NULL; - const ib_pkey_table_t* p_pkey; + const ib_pkey_table_t* p_pkey; cl_qlist_t rec_list; osm_madw_t* p_resp_madw; ib_sa_mad_t* p_resp_sa_mad; - ib_pkey_table_record_t* p_resp_rec; - uint32_t num_rec, pre_trim_num_rec; + ib_pkey_table_record_t* p_resp_rec; + uint32_t num_rec, pre_trim_num_rec; #ifndef VENDOR_RMPP_SUPPORT - uint32_t trim_num_rec; + uint32_t trim_num_rec; #endif - uint32_t i; - osm_pkey_search_ctxt_t context; - osm_pkey_item_t* p_rec_item; - ib_api_status_t status; - ib_net64_t comp_mask; - osm_physp_t* p_req_physp; + uint32_t i; + osm_pkey_search_ctxt_t context; + osm_pkey_item_t* p_rec_item; + ib_api_status_t status = IB_SUCCESS; + ib_net64_t comp_mask; + osm_physp_t* p_req_physp; CL_ASSERT( p_rcv ); @@ -353,18 +346,7 @@ osm_pkey_rec_rcv_process( CL_ASSERT( p_rcvd_mad->attr_id == IB_MAD_ATTR_PKEY_TBL_RECORD ); - /* update the requester physical port. */ - p_req_physp = osm_get_physp_by_mad_addr(p_rcv->p_log, - p_rcv->p_subn, - osm_madw_get_mad_addr_ptr(p_madw) ); - if (p_req_physp == NULL) - { - osm_log( p_rcv->p_log, OSM_LOG_ERROR, - "osm_pkey_rec_rcv_process: ERR 4604: " - "Cannot find requester physical port\n" ); - goto Exit; - } - + /* we only support SubnAdmGet and SubnAdmGetTable methods */ if ( (p_rcvd_mad->method != IB_MAD_METHOD_GET) && (p_rcvd_mad->method != IB_MAD_METHOD_GETTABLE) ) { @@ -372,12 +354,12 @@ osm_pkey_rec_rcv_process( "osm_pkey_rec_rcv_process: ERR 4605: " "Unsupported Method (%s)\n", ib_get_sa_method_str( p_rcvd_mad->method ) ); - osm_sa_send_error( p_rcv->p_resp, p_madw, IB_SA_MAD_STATUS_REQ_INVALID); + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_MAD_STATUS_UNSUP_METHOD_ATTR ); goto Exit; } - + /* - p819 - P_KeyTableRecords shall only be provided in response + p922 - P_KeyTableRecords shall only be provided in response to trusted requests. Check that the requester is a trusted one. */ @@ -389,11 +371,22 @@ osm_pkey_rec_rcv_process( "Request from non-trusted requester: " "Given SM_Key:0x%016" PRIx64 "\n", cl_ntoh64(p_rcvd_mad->sm_key) ); - osm_sa_send_error( p_rcv->p_resp, p_madw, IB_SA_MAD_STATUS_REQ_INVALID); + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_SA_MAD_STATUS_REQ_INVALID ); + goto Exit; + } + + /* update the requester physical port. */ + p_req_physp = osm_get_physp_by_mad_addr(p_rcv->p_log, + p_rcv->p_subn, + osm_madw_get_mad_addr_ptr(p_madw) ); + if (p_req_physp == NULL) + { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "osm_pkey_rec_rcv_process: ERR 4604: " + "Cannot find requester physical port\n" ); goto Exit; } - p_tbl = &p_rcv->p_subn->port_lid_tbl; p_pkey = (ib_pkey_table_t*)ib_sa_mad_get_payload_ptr( p_rcvd_mad ); cl_qlist_init( &rec_list ); @@ -407,10 +400,11 @@ osm_pkey_rec_rcv_process( osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "osm_pkey_rec_rcv_process: " - "Got Query Lid:0x%04X(%02X), Block:0x%02X(%02X), Port:0x%02X(%02X)\n", - cl_ntoh16(p_rcvd_rec->lid), (comp_mask &IB_PKEY_COMPMASK_LID) != 0, - p_rcvd_rec->port_num, (comp_mask &IB_PKEY_COMPMASK_PORT) != 0, - p_rcvd_rec->block_num, (comp_mask &IB_PKEY_COMPMASK_BLOCK) != 0) ; + "Got Query Lid:0x%04X(%02X), Block:0x%02X(%02X), Port:0x%02X(%02X)\n", + cl_ntoh16(p_rcvd_rec->lid), (comp_mask & IB_PKEY_COMPMASK_LID) != 0, + p_rcvd_rec->port_num, (comp_mask & IB_PKEY_COMPMASK_PORT) != 0, + p_rcvd_rec->block_num, (comp_mask & IB_PKEY_COMPMASK_BLOCK) != 0 ); + cl_plock_acquire( p_rcv->p_lock ); /* @@ -420,30 +414,33 @@ osm_pkey_rec_rcv_process( if( comp_mask & IB_PKEY_COMPMASK_LID ) { + p_tbl = &p_rcv->p_subn->port_lid_tbl; + CL_ASSERT( cl_ptr_vector_get_size(p_tbl) < 0x10000 ); - if ((uint16_t)cl_ptr_vector_get_size(p_tbl) > cl_ntoh16(p_rcvd_rec->lid)) + status = osm_get_port_by_base_lid( p_rcv->p_subn, p_rcvd_rec->lid, &p_port ); + if ( ( status != IB_SUCCESS ) || ( p_port == NULL ) ) { - p_port = cl_ptr_vector_get( p_tbl, cl_ntoh16(p_rcvd_rec->lid) ); - } - else - { /* port out of range */ + status = IB_NOT_FOUND; osm_log( p_rcv->p_log, OSM_LOG_ERROR, - "osm_pkey_rec_rcv_process: " - "Given LID (%u) is out of range:%u\n", - cl_ntoh16(p_rcvd_rec->lid), cl_ptr_vector_get_size(p_tbl)); + "osm_pkey_rec_rcv_process: ERR 460B: " + "No port found with LID 0x%x\n", + cl_ntoh16(p_rcvd_rec->lid) ); } } - /* if we got a unique port - no need for a port search */ - if( p_port ) - /* this does the loop on all the port phys ports */ - __osm_sa_pkey_by_comp_mask( p_rcv, p_port, &context ); - else + if ( status == IB_SUCCESS ) { - cl_qmap_apply_func( &p_rcv->p_subn->port_guid_tbl, - __osm_sa_pkey_by_comp_mask_cb, - &context ); + /* if we got a unique port - no need for a port search */ + if( p_port ) + /* this does the loop on all the port phys ports */ + __osm_sa_pkey_by_comp_mask( p_rcv, p_port, &context ); + else + { + cl_qmap_apply_func( &p_rcv->p_subn->port_guid_tbl, + __osm_sa_pkey_by_comp_mask_cb, + &context ); + } } cl_plock_release( p_rcv->p_lock ); @@ -454,24 +451,32 @@ osm_pkey_rec_rcv_process( * C15-0.1.30: * If we do a SubnAdmGet and got more than one record it is an error ! */ - if ( (p_rcvd_mad->method == IB_MAD_METHOD_GET) && - (num_rec > 1)) { - osm_log( p_rcv->p_log, OSM_LOG_ERROR, - "osm_pkey_rec_rcv_process: " - "Got more than one record for SubnAdmGet (%u)\n", - num_rec ); - osm_sa_send_error( p_rcv->p_resp, p_madw, - IB_SA_MAD_STATUS_TOO_MANY_RECORDS); - - /* need to set the mem free ... */ - p_rec_item = (osm_pkey_item_t*)cl_qlist_remove_head( &rec_list ); - while( p_rec_item != (osm_pkey_item_t*)cl_qlist_end( &rec_list ) ) + if (p_rcvd_mad->method == IB_MAD_METHOD_GET) + { + if (num_rec == 0) { - cl_qlock_pool_put( &p_rcv->pool, &p_rec_item->pool_item ); - p_rec_item = (osm_pkey_item_t*)cl_qlist_remove_head( &rec_list ); + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_SA_MAD_STATUS_NO_RECORDS ); + goto Exit; } + if (num_rec > 1) + { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "osm_pkey_rec_rcv_process: ERR 460A: " + "Got more than one record for SubnAdmGet (%u)\n", + num_rec ); + osm_sa_send_error( p_rcv->p_resp, p_madw, + IB_SA_MAD_STATUS_TOO_MANY_RECORDS); - goto Exit; + /* need to set the mem free ... */ + p_rec_item = (osm_pkey_item_t*)cl_qlist_remove_head( &rec_list ); + while( p_rec_item != (osm_pkey_item_t*)cl_qlist_end( &rec_list ) ) + { + cl_qlock_pool_put( &p_rcv->pool, &p_rec_item->pool_item ); + p_rec_item = (osm_pkey_item_t*)cl_qlist_remove_head( &rec_list ); + } + + goto Exit; + } } pre_trim_num_rec = num_rec; @@ -493,8 +498,7 @@ osm_pkey_rec_rcv_process( if((p_rcvd_mad->method == IB_MAD_METHOD_GET) && (num_rec == 0)) { - osm_sa_send_error( p_rcv->p_resp, p_madw, - IB_SA_MAD_STATUS_NO_RECORDS ); + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_SA_MAD_STATUS_NO_RECORDS ); goto Exit; } @@ -518,9 +522,7 @@ osm_pkey_rec_rcv_process( cl_qlock_pool_put( &p_rcv->pool, &p_rec_item->pool_item ); } - osm_sa_send_error( p_rcv->p_resp, p_madw, - IB_SA_MAD_STATUS_NO_RESOURCES ); - + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_SA_MAD_STATUS_NO_RESOURCES ); goto Exit; } @@ -532,9 +534,9 @@ osm_pkey_rec_rcv_process( Then copy all records from the list into the response payload. */ - cl_memcpy( p_resp_sa_mad, p_rcvd_mad, IB_SA_MAD_HDR_SIZE ); - p_resp_sa_mad->method = (uint8_t)(p_resp_sa_mad->method | 0x80); - /* C15-0.1.5 - always return SM_Key = 0 (table 151 p 782) */ + memcpy( p_resp_sa_mad, p_rcvd_mad, IB_SA_MAD_HDR_SIZE ); + p_resp_sa_mad->method |= IB_MAD_METHOD_RESP_MASK; + /* C15-0.1.5 - always return SM_Key = 0 (table 185 p 884) */ p_resp_sa_mad->sm_key = 0; /* Fill in the offset (paylen will be done by the rmpp SAR) */ @@ -573,11 +575,11 @@ osm_pkey_rec_rcv_process( CL_ASSERT( cl_is_qlist_empty( &rec_list ) ); status = osm_vendor_send( p_resp_madw->h_bind, p_resp_madw, FALSE); - if(status != IB_SUCCESS) + if (status != IB_SUCCESS) { osm_log(p_rcv->p_log, OSM_LOG_ERROR, "osm_pkey_rec_rcv_process: ERR 4607: " - "osm_vendor_send. status = %s\n", + "osm_vendor_send status = %s\n", ib_get_err_str(status)); goto Exit; } diff --git a/trunk/ulp/opensm/user/opensm/osm_sa_pkey_record_ctrl.c b/trunk/ulp/opensm/user/opensm/osm_sa_pkey_record_ctrl.c index a20aed9a..324b6edf 100644 --- a/trunk/ulp/opensm/user/opensm/osm_sa_pkey_record_ctrl.c +++ b/trunk/ulp/opensm/user/opensm/osm_sa_pkey_record_ctrl.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,15 +32,11 @@ */ -/* - Next available error code: 0x203 -*/ - #if HAVE_CONFIG_H # include #endif /* HAVE_CONFIG_H */ -#include +#include #include #include @@ -62,7 +58,7 @@ void osm_pkey_rec_rcv_ctrl_construct( IN osm_pkey_rec_rcv_ctrl_t* const p_ctrl ) { - cl_memclr( p_ctrl, sizeof(*p_ctrl) ); + memset( p_ctrl, 0, sizeof(*p_ctrl) ); p_ctrl->h_disp = CL_DISP_INVALID_HANDLE; } @@ -114,3 +110,4 @@ osm_pkey_rec_rcv_ctrl_init( return( status ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_sa_portinfo_record.c b/trunk/ulp/opensm/user/opensm/osm_sa_portinfo_record.c index aeb40734..bf868991 100644 --- a/trunk/ulp/opensm/user/opensm/osm_sa_portinfo_record.c +++ b/trunk/ulp/opensm/user/opensm/osm_sa_portinfo_record.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Implementation of osm_pir_rcv_t. @@ -44,16 +45,12 @@ * $Revision: 1.10 $ */ -/* - Next available error code: 0x403 -*/ - #if HAVE_CONFIG_H # include #endif /* HAVE_CONFIG_H */ +#include #include -#include #include #include #include @@ -61,6 +58,7 @@ #include #include #include +#include #include #include #include @@ -72,7 +70,6 @@ typedef struct _osm_pir_item { cl_pool_item_t pool_item; ib_portinfo_record_t rec; - } osm_pir_item_t; typedef struct _osm_pir_search_ctxt @@ -82,7 +79,7 @@ typedef struct _osm_pir_search_ctxt cl_qlist_t* p_list; osm_pir_rcv_t* p_rcv; const osm_physp_t* p_req_physp; - + boolean_t is_enhanced_comp_mask; } osm_pir_search_ctxt_t; /********************************************************************** @@ -91,7 +88,7 @@ void osm_pir_rcv_construct( IN osm_pir_rcv_t* const p_rcv ) { - cl_memclr( p_rcv, sizeof(*p_rcv) ); + memset( p_rcv, 0, sizeof(*p_rcv) ); cl_qlock_pool_construct( &p_rcv->pool ); } @@ -110,12 +107,12 @@ osm_pir_rcv_destroy( **********************************************************************/ ib_api_status_t osm_pir_rcv_init( - IN osm_pir_rcv_t* const p_rcv, - IN osm_sa_resp_t* const p_resp, - IN osm_mad_pool_t* const p_mad_pool, - IN const osm_subn_t* const p_subn, - IN osm_log_t* const p_log, - IN cl_plock_t* const p_lock ) + IN osm_pir_rcv_t* const p_rcv, + IN osm_sa_resp_t* const p_resp, + IN osm_mad_pool_t* const p_mad_pool, + IN osm_subn_t* const p_subn, + IN osm_log_t* const p_log, + IN cl_plock_t* const p_lock ) { ib_api_status_t status; @@ -166,7 +163,7 @@ __osm_pir_rcv_new_pir( if( osm_log_is_active( p_rcv->p_log, OSM_LOG_DEBUG ) ) { - osm_log( p_rcv->p_log, OSM_LOG_ERROR, + osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "__osm_pir_rcv_new_pir: " "New PortInfoRecord: port 0x%016" PRIx64 ", lid 0x%X, port# 0x%X\n", @@ -174,7 +171,7 @@ __osm_pir_rcv_new_pir( cl_ntoh16( lid ), osm_physp_get_port_num( p_physp ) ); } - cl_memclr( &p_rec_item->rec, sizeof( p_rec_item->rec ) ); + memset( &p_rec_item->rec, 0, sizeof( p_rec_item->rec ) ); p_rec_item->rec.lid = lid; p_rec_item->rec.port_info = *osm_physp_get_port_info_ptr( p_physp ); @@ -191,57 +188,66 @@ __osm_pir_rcv_new_pir( **********************************************************************/ void __osm_sa_pir_create( - IN osm_pir_rcv_t* const p_rcv, - IN const osm_physp_t* const p_physp, + IN osm_pir_rcv_t* const p_rcv, + IN const osm_physp_t* const p_physp, IN osm_pir_search_ctxt_t* const p_ctxt ) { - uint8_t lmc; - uint16_t lid_ho; - uint16_t max_lid_ho; - uint16_t base_lid_ho; + uint8_t lmc; + uint16_t max_lid_ho; + uint16_t base_lid_ho; + uint16_t match_lid_ho; + osm_physp_t *p_node_physp; OSM_LOG_ENTER( p_rcv->p_log, __osm_sa_pir_create ); - if(p_physp->p_node->node_info.node_type == IB_NODE_TYPE_SWITCH) + if (p_physp->p_node->sw) { - lmc = 0; - base_lid_ho = cl_ntoh16( - osm_physp_get_base_lid( - osm_node_get_physp_ptr(p_physp->p_node, 0)) - ); - max_lid_ho = base_lid_ho; + p_node_physp = osm_node_get_physp_ptr( p_physp->p_node, 0 ); + base_lid_ho = cl_ntoh16( osm_physp_get_base_lid( p_node_physp ) ); + lmc = osm_switch_sp0_is_lmc_capable(p_physp->p_node->sw, p_rcv->p_subn) ? + osm_physp_get_lmc( p_node_physp ) : 0; } else { lmc = osm_physp_get_lmc( p_physp ); base_lid_ho = cl_ntoh16( osm_physp_get_base_lid( p_physp ) ); - max_lid_ho = (uint16_t)( base_lid_ho + (1 << lmc) - 1 ); } + max_lid_ho = (uint16_t)( base_lid_ho + (1 << lmc) - 1 ); if( p_ctxt->comp_mask & IB_PIR_COMPMASK_LID ) { - __osm_pir_rcv_new_pir( p_rcv, p_physp, p_ctxt->p_list, - p_ctxt->p_rcvd_rec->lid ); - } - else - { - for( lid_ho = base_lid_ho; lid_ho <= max_lid_ho; lid_ho++ ) + match_lid_ho = cl_ntoh16( p_ctxt->p_rcvd_rec->lid ); + + /* + We validate that the lid belongs to this node. + */ + if( osm_log_is_active( p_rcv->p_log, OSM_LOG_DEBUG ) ) { - __osm_pir_rcv_new_pir( p_rcv, p_physp, p_ctxt->p_list, - cl_hton16( lid_ho ) ); + osm_log( p_rcv->p_log, OSM_LOG_DEBUG, + "__osm_sa_pir_create: " + "Comparing LID: 0x%X <= 0x%X <= 0x%X\n", + base_lid_ho, match_lid_ho, max_lid_ho + ); } + + if ( match_lid_ho < base_lid_ho || match_lid_ho > max_lid_ho ) + goto Exit; } + + __osm_pir_rcv_new_pir( p_rcv, p_physp, p_ctxt->p_list, + cl_hton16( base_lid_ho ) ); + + Exit: OSM_LOG_EXIT( p_rcv->p_log ); } - /********************************************************************** **********************************************************************/ void __osm_sa_pir_check_physp( IN osm_pir_rcv_t* const p_rcv, IN const osm_physp_t* const p_physp, - osm_pir_search_ctxt_t* const p_ctxt ) + osm_pir_search_ctxt_t* const p_ctxt ) { const ib_portinfo_record_t* p_rcvd_rec; ib_net64_t comp_mask; @@ -285,11 +291,23 @@ __osm_sa_pir_check_physp( if( p_comp_pi->master_sm_base_lid != p_pi->master_sm_base_lid ) goto Exit; } + + /* IBTA 1.2 errata provides support for bitwise compare if the bit 31 + of the attribute modifier of the Get/GetTable is set */ if( comp_mask & IB_PIR_COMPMASK_CAPMASK ) { - if( p_comp_pi->capability_mask != p_pi->capability_mask ) - goto Exit; + if (p_ctxt->is_enhanced_comp_mask) + { + if ( ( ( p_comp_pi->capability_mask & p_pi->capability_mask ) != p_comp_pi->capability_mask) ) + goto Exit; + } + else + { + if( p_comp_pi->capability_mask != p_pi->capability_mask ) + goto Exit; + } } + if( comp_mask & IB_PIR_COMPMASK_DIAGCODE ) { if( p_comp_pi->diag_code != p_pi->diag_code ) @@ -500,11 +518,11 @@ __osm_sa_pir_check_physp( /********************************************************************** **********************************************************************/ -void +static void __osm_sa_pir_by_comp_mask( IN osm_pir_rcv_t* const p_rcv, IN const osm_port_t* const p_port, - osm_pir_search_ctxt_t* const p_ctxt ) + osm_pir_search_ctxt_t* const p_ctxt ) { const ib_portinfo_record_t* p_rcvd_rec; ib_net64_t comp_mask; @@ -558,13 +576,13 @@ __osm_sa_pir_by_comp_mask( /********************************************************************** **********************************************************************/ -void +static void __osm_sa_pir_by_comp_mask_cb( IN cl_map_item_t* const p_map_item, - IN void* context ) + IN void* context ) { const osm_port_t* const p_port = (osm_port_t*)p_map_item; - osm_pir_search_ctxt_t* const p_ctxt = (osm_pir_search_ctxt_t *)context; + osm_pir_search_ctxt_t* const p_ctxt = (osm_pir_search_ctxt_t *)context; __osm_sa_pir_by_comp_mask( p_ctxt->p_rcv, p_port, p_ctxt ); } @@ -578,21 +596,21 @@ osm_pir_rcv_process( { const ib_sa_mad_t* p_rcvd_mad; const ib_portinfo_record_t* p_rcvd_rec; - const cl_ptr_vector_t* p_tbl; + const cl_ptr_vector_t* p_tbl; const osm_port_t* p_port = NULL; const ib_port_info_t* p_pi; cl_qlist_t rec_list; osm_madw_t* p_resp_madw; - ib_sa_mad_t* p_resp_sa_mad; + ib_sa_mad_t* p_resp_sa_mad; ib_portinfo_record_t* p_resp_rec; - uint32_t num_rec, pre_trim_num_rec; + uint32_t num_rec, pre_trim_num_rec; #ifndef VENDOR_RMPP_SUPPORT - uint32_t trim_num_rec; + uint32_t trim_num_rec; #endif - uint32_t i; + uint32_t i; osm_pir_search_ctxt_t context; osm_pir_item_t* p_rec_item; - ib_api_status_t status; + ib_api_status_t status = IB_SUCCESS; ib_net64_t comp_mask; osm_physp_t* p_req_physp; boolean_t trusted_req = TRUE; @@ -609,6 +627,18 @@ osm_pir_rcv_process( CL_ASSERT( p_rcvd_mad->attr_id == IB_MAD_ATTR_PORTINFO_RECORD ); + /* we only support SubnAdmGet and SubnAdmGetTable methods */ + if ( (p_rcvd_mad->method != IB_MAD_METHOD_GET) && + (p_rcvd_mad->method != IB_MAD_METHOD_GETTABLE) ) + { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "osm_pir_rcv_process: ERR 2105: " + "Unsupported Method (%s)\n", + ib_get_sa_method_str( p_rcvd_mad->method ) ); + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_MAD_STATUS_UNSUP_METHOD_ATTR ); + goto Exit; + } + /* update the requester physical port. */ p_req_physp = osm_get_physp_by_mad_addr(p_rcv->p_log, p_rcv->p_subn, @@ -621,17 +651,6 @@ osm_pir_rcv_process( goto Exit; } - if ( (p_rcvd_mad->method != IB_MAD_METHOD_GET) && - (p_rcvd_mad->method != IB_MAD_METHOD_GETTABLE) ) - { - osm_log( p_rcv->p_log, OSM_LOG_ERROR, - "osm_pir_rcv_process: ERR 2105: " - "Unsupported Method (%s)\n", - ib_get_sa_method_str( p_rcvd_mad->method ) ); - osm_sa_send_error( p_rcv->p_resp, p_madw, IB_SA_MAD_STATUS_REQ_INVALID); - goto Exit; - } - if ( osm_log_is_active( p_rcv->p_log, OSM_LOG_DEBUG ) ) osm_dump_portinfo_record( p_rcv->p_log, p_rcvd_rec, OSM_LOG_DEBUG ); @@ -645,6 +664,7 @@ osm_pir_rcv_process( context.comp_mask = p_rcvd_mad->comp_mask; context.p_rcv = p_rcv; context.p_req_physp = p_req_physp; + context.is_enhanced_comp_mask = cl_ntoh32(p_rcvd_mad->attr_mod) & (1 << 31); cl_plock_acquire( p_rcv->p_lock ); @@ -656,16 +676,14 @@ osm_pir_rcv_process( */ if( comp_mask & IB_PIR_COMPMASK_LID ) { - if ((uint16_t)cl_ptr_vector_get_size(p_tbl) > cl_ntoh16(p_rcvd_rec->lid)) - { - p_port = cl_ptr_vector_get( p_tbl, cl_ntoh16(p_rcvd_rec->lid) ); - } - else + status = osm_get_port_by_base_lid( p_rcv->p_subn, p_rcvd_rec->lid, &p_port ); + if ( ( status != IB_SUCCESS ) || ( p_port == NULL ) ) { + status = IB_NOT_FOUND; osm_log( p_rcv->p_log, OSM_LOG_ERROR, - "osm_pir_rcv_process: " - "Given LID (%u) is out of range:%u\n", - cl_ntoh16(p_rcvd_rec->lid), cl_ptr_vector_get_size(p_tbl)); + "osm_pir_rcv_process: ERR 2109: " + "No port found with LID 0x%x\n", + cl_ntoh16(p_rcvd_rec->lid) ); } } else @@ -678,21 +696,25 @@ osm_pir_rcv_process( } else { + status = IB_NOT_FOUND; osm_log( p_rcv->p_log, OSM_LOG_ERROR, - "osm_pir_rcv_process: " - "Given LID (%u) is out of range:%u\n", + "osm_pir_rcv_process: ERR 2103: " + "Given LID (0x%X) is out of range:0x%X\n", cl_ntoh16(p_pi->base_lid), cl_ptr_vector_get_size(p_tbl)); } } } - if( p_port ) - __osm_sa_pir_by_comp_mask( p_rcv, p_port, &context ); - else + if ( status == IB_SUCCESS ) { - cl_qmap_apply_func( &p_rcv->p_subn->port_guid_tbl, - __osm_sa_pir_by_comp_mask_cb, - &context ); + if( p_port ) + __osm_sa_pir_by_comp_mask( p_rcv, p_port, &context ); + else + { + cl_qmap_apply_func( &p_rcv->p_subn->port_guid_tbl, + __osm_sa_pir_by_comp_mask_cb, + &context ); + } } cl_plock_release( p_rcv->p_lock ); @@ -703,24 +725,32 @@ osm_pir_rcv_process( * C15-0.1.30: * If we do a SubnAdmGet and got more than one record it is an error ! */ - if ( (p_rcvd_mad->method == IB_MAD_METHOD_GET) && - (num_rec > 1)) { - osm_log( p_rcv->p_log, OSM_LOG_ERROR, - "osm_pir_rcv_process: " - "Got more than one record for SubnAdmGet (%u)\n", - num_rec ); - osm_sa_send_error( p_rcv->p_resp, p_madw, - IB_SA_MAD_STATUS_TOO_MANY_RECORDS); - - /* need to set the mem free ... */ - p_rec_item = (osm_pir_item_t*)cl_qlist_remove_head( &rec_list ); - while( p_rec_item != (osm_pir_item_t*)cl_qlist_end( &rec_list ) ) + if (p_rcvd_mad->method == IB_MAD_METHOD_GET) + { + if (num_rec == 0) { - cl_qlock_pool_put( &p_rcv->pool, &p_rec_item->pool_item ); - p_rec_item = (osm_pir_item_t*)cl_qlist_remove_head( &rec_list ); + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_SA_MAD_STATUS_NO_RECORDS ); + goto Exit; } + if (num_rec > 1) + { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "osm_pir_rcv_process: ERR 2108: " + "Got more than one record for SubnAdmGet (%u)\n", + num_rec ); + osm_sa_send_error( p_rcv->p_resp, p_madw, + IB_SA_MAD_STATUS_TOO_MANY_RECORDS); - goto Exit; + /* need to set the mem free ... */ + p_rec_item = (osm_pir_item_t*)cl_qlist_remove_head( &rec_list ); + while( p_rec_item != (osm_pir_item_t*)cl_qlist_end( &rec_list ) ) + { + cl_qlock_pool_put( &p_rcv->pool, &p_rec_item->pool_item ); + p_rec_item = (osm_pir_item_t*)cl_qlist_remove_head( &rec_list ); + } + + goto Exit; + } } pre_trim_num_rec = num_rec; @@ -781,9 +811,9 @@ osm_pir_rcv_process( Then copy all records from the list into the response payload. */ - cl_memcpy( p_resp_sa_mad, p_rcvd_mad, IB_SA_MAD_HDR_SIZE ); - p_resp_sa_mad->method = (uint8_t)(p_resp_sa_mad->method | 0x80); - /* C15-0.1.5 - always return SM_Key = 0 (table 151 p 782) */ + memcpy( p_resp_sa_mad, p_rcvd_mad, IB_SA_MAD_HDR_SIZE ); + p_resp_sa_mad->method |= IB_MAD_METHOD_RESP_MASK; + /* C15-0.1.5 - always return SM_Key = 0 (table 185 p 884) */ p_resp_sa_mad->sm_key = 0; /* Fill in the offset (paylen will be done by the rmpp SAR) */ p_resp_sa_mad->attr_offset = @@ -807,7 +837,7 @@ osm_pir_rcv_process( #endif /* - p819 - The M_Key returned shall be zero, except in the case of a + p922 - The M_Key returned shall be zero, except in the case of a trusted request. Note: In the mad controller we check that the SM_Key received on the mad is valid. Meaning - is either zero or equal to the local @@ -833,11 +863,11 @@ osm_pir_rcv_process( CL_ASSERT( cl_is_qlist_empty( &rec_list ) ); status = osm_vendor_send( p_resp_madw->h_bind, p_resp_madw, FALSE); - if(status != IB_SUCCESS) + if (status != IB_SUCCESS) { osm_log(p_rcv->p_log, OSM_LOG_ERROR, "osm_pir_rcv_process: ERR 2107: " - "osm_vendor_send. status = %s\n", + "osm_vendor_send status = %s\n", ib_get_err_str(status)); goto Exit; } @@ -845,3 +875,4 @@ osm_pir_rcv_process( Exit: OSM_LOG_EXIT( p_rcv->p_log ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_sa_portinfo_record_ctrl.c b/trunk/ulp/opensm/user/opensm/osm_sa_portinfo_record_ctrl.c index bed575c5..a097cb14 100644 --- a/trunk/ulp/opensm/user/opensm/osm_sa_portinfo_record_ctrl.c +++ b/trunk/ulp/opensm/user/opensm/osm_sa_portinfo_record_ctrl.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Implementation of osm_pir_rcv_ctrl_t. @@ -44,15 +45,11 @@ * $Revision: 1.5 $ */ -/* - Next available error code: 0x203 -*/ - #if HAVE_CONFIG_H # include #endif /* HAVE_CONFIG_H */ -#include +#include #include #include @@ -74,7 +71,7 @@ void osm_pir_rcv_ctrl_construct( IN osm_pir_rcv_ctrl_t* const p_ctrl ) { - cl_memclr( p_ctrl, sizeof(*p_ctrl) ); + memset( p_ctrl, 0, sizeof(*p_ctrl) ); p_ctrl->h_disp = CL_DISP_INVALID_HANDLE; } @@ -125,3 +122,4 @@ osm_pir_rcv_ctrl_init( OSM_LOG_EXIT( p_log ); return( status ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_sa_response.c b/trunk/ulp/opensm/user/opensm/osm_sa_response.c index 7f149065..9106aa1f 100644 --- a/trunk/ulp/opensm/user/opensm/osm_sa_response.c +++ b/trunk/ulp/opensm/user/opensm/osm_sa_response.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -35,7 +35,7 @@ /* * Abstract: * Implementation of osm_sa_resp_t. - * This object represents the generic attribute respuester. + * This object represents the SA query responder. * This object is part of the opensm family of objects. * * Environment: @@ -44,16 +44,12 @@ * $Revision: 1.6 $ */ -/* - Next available error code: 0x300 -*/ - #if HAVE_CONFIG_H # include #endif /* HAVE_CONFIG_H */ +#include #include -#include #include #include #include @@ -66,7 +62,7 @@ void osm_sa_resp_construct( IN osm_sa_resp_t* const p_resp ) { - cl_memclr( p_resp, sizeof(*p_resp) ); + memset( p_resp, 0, sizeof(*p_resp) ); } /********************************************************************** @@ -105,11 +101,11 @@ void osm_sa_send_error( IN osm_sa_resp_t* const p_resp, IN const osm_madw_t* const p_madw, - IN const ib_net16_t sa_status ) + IN const ib_net16_t sa_status ) { osm_madw_t* p_resp_madw; - ib_sa_mad_t* p_resp_sa_mad; - ib_sa_mad_t* p_sa_mad; + ib_sa_mad_t* p_resp_sa_mad; + ib_sa_mad_t* p_sa_mad; ib_api_status_t status; OSM_LOG_ENTER( p_resp->p_log, osm_sa_send_error ); @@ -118,7 +114,7 @@ osm_sa_send_error( if (osm_exit_flag) { osm_log( p_resp->p_log, OSM_LOG_DEBUG, - "osm_sa_send_error: ", + "osm_sa_send_error: " "Ignoring requested send after exit\n" ); goto Exit; } @@ -147,10 +143,17 @@ osm_sa_send_error( p_resp_sa_mad->method |= IB_MAD_METHOD_RESP_MASK; /* - * C15-0.1.5 - always return SM_Key = 0 (table 151 p 782) + * C15-0.1.5 - always return SM_Key = 0 (table 185 p 884) */ p_resp_sa_mad->sm_key = 0; + /* + * o15-0.2.7 - The PathRecord Attribute ID shall be used in + * the response (to a SubnAdmGetMulti(MultiPathRecord) + */ + if( p_resp_sa_mad->attr_id == IB_MAD_ATTR_MULTIPATH_RECORD ) + p_resp_sa_mad->attr_id = IB_MAD_ATTR_PATH_RECORD; + if( osm_log_is_active( p_resp->p_log, OSM_LOG_FRAMES ) ) osm_dump_sa_mad( p_resp->p_log, p_resp_sa_mad, OSM_LOG_FRAMES ); @@ -169,3 +172,4 @@ osm_sa_send_error( Exit: OSM_LOG_EXIT( p_resp->p_log ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_sa_service_record.c b/trunk/ulp/opensm/user/opensm/osm_sa_service_record.c index 90fc71c2..44ab006f 100644 --- a/trunk/ulp/opensm/user/opensm/osm_sa_service_record.c +++ b/trunk/ulp/opensm/user/opensm/osm_sa_service_record.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -48,8 +48,8 @@ # include #endif /* HAVE_CONFIG_H */ +#include #include -#include #include #include #include @@ -71,8 +71,7 @@ typedef struct _osm_sr_item { cl_pool_item_t pool_item; - ib_service_record_t service_rec; - + ib_service_record_t service_rec; } osm_sr_item_t; typedef struct osm_sr_match_item { @@ -95,7 +94,7 @@ void osm_sr_rcv_construct( IN osm_sr_rcv_t* const p_rcv ) { - cl_memclr( p_rcv, sizeof(*p_rcv) ); + memset( p_rcv, 0, sizeof(*p_rcv) ); cl_qlock_pool_construct( &p_rcv->sr_pool ); cl_timer_construct(&p_rcv->sr_timer ); } @@ -124,8 +123,8 @@ osm_sr_rcv_init( IN osm_log_t* const p_log, IN cl_plock_t* const p_lock ) { - ib_api_status_t status = IB_ERROR; - cl_status_t cl_status; + ib_api_status_t status = IB_ERROR; + cl_status_t cl_status; OSM_LOG_ENTER( p_log, osm_sr_rcv_init ); @@ -160,23 +159,22 @@ osm_sr_rcv_init( /********************************************************************** **********************************************************************/ -static -boolean_t +static boolean_t __match_service_pkey_with_ports_pkey( IN osm_sr_rcv_t* const p_rcv, IN const osm_madw_t* const p_madw, ib_service_record_t * const p_service_rec, - ib_net64_t const comp_mask) + ib_net64_t const comp_mask ) { - boolean_t valid = TRUE; - osm_physp_t *p_req_physp; - ib_net64_t service_guid; - osm_port_t *service_port; + boolean_t valid = TRUE; + osm_physp_t * p_req_physp; + ib_net64_t service_guid; + osm_port_t * service_port; /* update the requester physical port. */ p_req_physp = osm_get_physp_by_mad_addr(p_rcv->p_log, p_rcv->p_subn, - osm_madw_get_mad_addr_ptr(p_madw) ); + osm_madw_get_mad_addr_ptr(p_madw)); if (p_req_physp == NULL) { osm_log( p_rcv->p_log, OSM_LOG_ERROR, @@ -191,7 +189,7 @@ __match_service_pkey_with_ports_pkey( /* We have a ServiceP_Key - check matching on requester port, and ServiceGid port (if such exists) */ /* Make sure it matches the p_req_physp */ - if (!osm_physp_has_pkey(p_rcv->p_log, p_service_rec->service_pkey, p_req_physp )) + if (!osm_physp_has_pkey(p_rcv->p_log, p_service_rec->service_pkey, p_req_physp)) { valid = FALSE; goto Exit; @@ -214,7 +212,7 @@ __match_service_pkey_with_ports_pkey( /* check on the table of the default physical port of the service port */ if ( !osm_physp_has_pkey( p_rcv->p_log, p_service_rec->service_pkey, - osm_port_get_default_phys_ptr(service_port) )) + osm_port_get_default_phys_ptr(service_port) ) ) { valid = FALSE; goto Exit; @@ -230,21 +228,20 @@ __match_service_pkey_with_ports_pkey( **********************************************************************/ boolean_t __match_name_to_key_association( - IN osm_sr_rcv_t* const p_rcv, + IN osm_sr_rcv_t* const p_rcv, ib_service_record_t* p_service_rec, - ib_net64_t comp_mask) + ib_net64_t comp_mask ) { UNUSED_PARAM( p_service_rec ); UNUSED_PARAM( p_rcv ); + if( (comp_mask & (IB_SR_COMPMASK_SKEY | IB_SR_COMPMASK_SNAME)) == (IB_SR_COMPMASK_SKEY | IB_SR_COMPMASK_SNAME) ) { - /* For now we are not maintaining the ServiceAssociation record - * just return TRUE + /* For now, we are not maintaining the ServiceAssociation record + * so just return TRUE */ - return TRUE; - } return TRUE; @@ -252,15 +249,14 @@ __match_name_to_key_association( /********************************************************************** **********************************************************************/ -static -boolean_t +static boolean_t __validate_sr( IN osm_sr_rcv_t* const p_rcv, IN const osm_madw_t* const p_madw ) { - boolean_t valid = TRUE; - ib_sa_mad_t *p_sa_mad; - ib_service_record_t* p_recvd_service_rec; + boolean_t valid = TRUE; + ib_sa_mad_t * p_sa_mad; + ib_service_record_t* p_recvd_service_rec; OSM_LOG_ENTER( p_rcv->p_log, __validate_sr ); @@ -272,13 +268,13 @@ __validate_sr( p_rcv, p_madw, p_recvd_service_rec, - p_sa_mad->comp_mask); + p_sa_mad->comp_mask ); if(!valid) { osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "__validate_sr: " - "No Match for Service Pkey\n"); + "No Match for Service Pkey\n" ); valid = FALSE; goto Exit; } @@ -286,13 +282,13 @@ __validate_sr( valid = __match_name_to_key_association( p_rcv, p_recvd_service_rec, - p_sa_mad->comp_mask); + p_sa_mad->comp_mask ); if(!valid) { osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "__validate_sr: " - "Service Record Name to key matching failed\n"); + "Service Record Name to key matching failed\n" ); valid = FALSE; goto Exit; } @@ -312,16 +308,16 @@ __osm_sr_rcv_respond( { osm_madw_t* p_resp_madw; const ib_sa_mad_t* p_sa_mad; - ib_sa_mad_t* p_resp_sa_mad; + ib_sa_mad_t* p_resp_sa_mad; uint32_t num_rec, num_copied; #ifndef VENDOR_RMPP_SUPPORT - uint32_t trim_num_rec; + uint32_t trim_num_rec; #endif ib_service_record_t* p_resp_sr; ib_api_status_t status; - osm_sr_item_t* p_sr_item; - const ib_sa_mad_t* p_rcvd_mad = osm_madw_get_sa_mad_ptr( p_madw ); - boolean_t trusted_req = TRUE; + osm_sr_item_t* p_sr_item; + const ib_sa_mad_t* p_rcvd_mad = osm_madw_get_sa_mad_ptr( p_madw ); + boolean_t trusted_req = TRUE; OSM_LOG_ENTER( p_rcv->p_log, __osm_sr_rcv_respond ); @@ -396,7 +392,7 @@ __osm_sr_rcv_respond( p_sa_mad = osm_madw_get_sa_mad_ptr( p_madw ); p_resp_sa_mad = osm_madw_get_sa_mad_ptr( p_resp_madw ); - cl_memcpy( p_resp_sa_mad, p_sa_mad, IB_SA_MAD_HDR_SIZE ); + memcpy( p_resp_sa_mad, p_sa_mad, IB_SA_MAD_HDR_SIZE ); /* but what if it was a SET ? setting the response bit is not enough */ if (p_rcvd_mad->method == IB_MAD_METHOD_SET) @@ -404,7 +400,7 @@ __osm_sr_rcv_respond( p_resp_sa_mad->method = IB_MAD_METHOD_GET; } p_resp_sa_mad->method |= IB_MAD_METHOD_RESP_MASK; - /* C15-0.1.5 - always return SM_Key = 0 (table 151 p 782) */ + /* C15-0.1.5 - always return SM_Key = 0 (table 185 p 884) */ p_resp_sa_mad->sm_key = 0; /* Fill in the offset (paylen will be done by the rmpp SAR) */ @@ -431,12 +427,12 @@ __osm_sr_rcv_respond( (num_rec == 0)) { p_resp_sa_mad->status = IB_SA_MAD_STATUS_NO_RECORDS; - cl_memclr( p_resp_sr, sizeof(*p_resp_sr) ); + memset( p_resp_sr, 0, sizeof(*p_resp_sr) ); } else { /* - p819 - The ServiceKey shall be set to 0, except in the case of a trusted + p923 - The ServiceKey shall be set to 0, except in the case of a trusted request. Note: In the mad controller we check that the SM_Key received on the mad is valid. Meaning - is either zero or equal to the local @@ -458,7 +454,7 @@ __osm_sr_rcv_respond( { *p_resp_sr = p_sr_item->service_rec; if (trusted_req == FALSE) - cl_memclr(p_resp_sr->service_key, sizeof(p_resp_sr->service_key)); + memset(p_resp_sr->service_key, 0, sizeof(p_resp_sr->service_key)); num_copied++; } @@ -485,18 +481,17 @@ __osm_sr_rcv_respond( /********************************************************************** **********************************************************************/ -static -void +static void __get_matching_sr( IN cl_list_item_t* const p_list_item, IN void* context ) { osm_sr_search_ctxt_t* const p_ctxt = (osm_sr_search_ctxt_t*)context; - osm_svcr_t *p_svcr = (osm_svcr_t*)p_list_item; - osm_sr_item_t* p_sr_pool_item; - osm_sr_match_item_t* p_sr_item =p_ctxt->p_sr_item; - ib_net64_t comp_mask = p_sr_item->comp_mask; - const osm_physp_t* p_req_physp = p_ctxt->p_req_physp; + osm_svcr_t * p_svcr = (osm_svcr_t*)p_list_item; + osm_sr_item_t* p_sr_pool_item; + osm_sr_match_item_t* p_sr_item =p_ctxt->p_sr_item; + ib_net64_t comp_mask = p_sr_item->comp_mask; + const osm_physp_t* p_req_physp = p_ctxt->p_req_physp; if((comp_mask & IB_SR_COMPMASK_SID) == IB_SR_COMPMASK_SID) { @@ -507,9 +502,9 @@ __get_matching_sr( if((comp_mask & IB_SR_COMPMASK_SGID) == IB_SR_COMPMASK_SGID) { if( - cl_memcmp(&p_sr_item->p_service_rec->service_gid, - &p_svcr->service_record.service_gid, - sizeof(p_svcr->service_record.service_gid)) != 0) + memcmp(&p_sr_item->p_service_rec->service_gid, + &p_svcr->service_record.service_gid, + sizeof(p_svcr->service_record.service_gid)) != 0) return; } if((comp_mask & IB_SR_COMPMASK_SPKEY) == IB_SR_COMPMASK_SPKEY ) @@ -521,17 +516,17 @@ __get_matching_sr( if((comp_mask & IB_SR_COMPMASK_SKEY) == IB_SR_COMPMASK_SKEY) { - if(cl_memcmp(p_sr_item->p_service_rec->service_key , - p_svcr->service_record.service_key, - 16*sizeof(uint8_t))) + if(memcmp(p_sr_item->p_service_rec->service_key , + p_svcr->service_record.service_key, + 16*sizeof(uint8_t))) return; } if((comp_mask & IB_SR_COMPMASK_SNAME) == IB_SR_COMPMASK_SNAME) { if( - cl_memcmp(p_sr_item->p_service_rec->service_name, - p_svcr->service_record.service_name, - sizeof(p_svcr->service_record.service_name)) != 0 + memcmp(p_sr_item->p_service_rec->service_name, + p_svcr->service_record.service_name, + sizeof(p_svcr->service_record.service_name)) != 0 ) return; } @@ -747,7 +742,7 @@ __get_matching_sr( { osm_log( p_sr_item->p_rcv->p_log, OSM_LOG_ERROR, "__get_matching_sr: ERR 2408: " - "Unable to acquire Service Record from pool\n"); + "Unable to acquire Service Record from pool\n" ); goto Exit; } @@ -762,17 +757,16 @@ __get_matching_sr( /********************************************************************** **********************************************************************/ -static -void +static void osm_sr_rcv_process_get_method( IN osm_sr_rcv_t* const p_rcv, IN const osm_madw_t* const p_madw ) { - ib_sa_mad_t *p_sa_mad; - ib_service_record_t* p_recvd_service_rec; - osm_sr_match_item_t sr_match_item; - osm_sr_search_ctxt_t context; - osm_physp_t* p_req_physp; + ib_sa_mad_t * p_sa_mad; + ib_service_record_t* p_recvd_service_rec; + osm_sr_match_item_t sr_match_item; + osm_sr_search_ctxt_t context; + osm_physp_t* p_req_physp; OSM_LOG_ENTER( p_rcv->p_log, osm_sr_rcv_process_get_method ); @@ -816,23 +810,21 @@ osm_sr_rcv_process_get_method( __get_matching_sr, &context); + cl_plock_release(p_rcv->p_lock); + if ((p_sa_mad->method == IB_MAD_METHOD_GET) && (cl_qlist_count( &sr_match_item.sr_list ) == 0)) { - cl_plock_release(p_rcv->p_lock); - osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "osm_sr_rcv_process_get_method: " "No records matched the Service Record query\n"); - osm_sa_send_error( p_rcv->p_resp, p_madw, - IB_SA_MAD_STATUS_NO_RECORDS ); + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_SA_MAD_STATUS_NO_RECORDS ); goto Exit; } - cl_plock_release(p_rcv->p_lock); - __osm_sr_rcv_respond( p_rcv, p_madw, &sr_match_item.sr_list ); + Exit: OSM_LOG_EXIT( p_rcv->p_log ); return; @@ -840,19 +832,18 @@ osm_sr_rcv_process_get_method( /********************************************************************** **********************************************************************/ -static -void +static void osm_sr_rcv_process_set_method( IN osm_sr_rcv_t* const p_rcv, IN const osm_madw_t* const p_madw ) { - ib_sa_mad_t *p_sa_mad; - ib_net16_t sa_status = IB_SA_MAD_STATUS_REQ_INVALID; - ib_service_record_t* p_recvd_service_rec; - ib_net64_t comp_mask; - osm_svcr_t* p_svcr; - osm_sr_item_t* p_sr_item; - cl_qlist_t sr_list; + ib_sa_mad_t * p_sa_mad; + ib_net16_t sa_status = IB_SA_MAD_STATUS_REQ_INVALID; + ib_service_record_t* p_recvd_service_rec; + ib_net64_t comp_mask; + osm_svcr_t* p_svcr; + osm_sr_item_t* p_sr_item; + cl_qlist_t sr_list; OSM_LOG_ENTER( p_rcv->p_log, osm_sr_rcv_process_set_method ); @@ -898,7 +889,7 @@ osm_sr_rcv_process_set_method( p_svcr = osm_svcr_get_by_rid( p_rcv->p_subn, p_rcv->p_log, - p_recvd_service_rec); + p_recvd_service_rec ); if(p_svcr == NULL) { @@ -912,33 +903,31 @@ osm_sr_rcv_process_set_method( "osm_sr_rcv_process_set_method: ERR 2411: " "osm_svcr_get_by_rid failed\n" ); - osm_sa_send_error( - p_rcv->p_resp, - p_madw, - IB_SA_MAD_STATUS_NO_RESOURCES ); - + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_SA_MAD_STATUS_NO_RESOURCES ); goto Exit; - } + /* Add this new osm_svcr_t object to subnet object */ osm_svcr_insert_to_db( p_rcv->p_subn, p_rcv->p_log, - p_svcr); + p_svcr ); - } else + } + else { - /* Update the old instance of the osm_svcr_t object */ osm_svcr_init(p_svcr, p_recvd_service_rec); - } + cl_plock_release(p_rcv->p_lock); if( p_recvd_service_rec->service_lease != 0xFFFFFFFF ) { - /* cl_timer_trim(&p_rcv->sr_timer, */ - /* p_recvd_service_rec->service_lease * 1000 ); */ +#if 0 + cl_timer_trim(&p_rcv->sr_timer, + p_recvd_service_rec->service_lease * 1000); +#endif /* This was a bug since no check was made to see if too long */ /* just make sure the timer works - get a call back within a second */ cl_timer_trim(&p_rcv->sr_timer, 1000); @@ -951,8 +940,7 @@ osm_sr_rcv_process_set_method( osm_log( p_rcv->p_log, OSM_LOG_ERROR, "osm_sr_rcv_process_set_method: ERR 2412: " "Unable to acquire Service record\n" ); - osm_sa_send_error( p_rcv->p_resp, p_madw, - IB_SA_MAD_STATUS_NO_RESOURCES ); + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_SA_MAD_STATUS_NO_RESOURCES ); goto Exit; } @@ -968,6 +956,7 @@ osm_sr_rcv_process_set_method( cl_qlist_insert_tail( &sr_list, (cl_list_item_t*)&p_sr_item->pool_item ); __osm_sr_rcv_respond( p_rcv, p_madw, &sr_list ); + Exit: OSM_LOG_EXIT( p_rcv->p_log ); return; @@ -975,18 +964,17 @@ osm_sr_rcv_process_set_method( /********************************************************************** **********************************************************************/ -static -void +static void osm_sr_rcv_process_delete_method( IN osm_sr_rcv_t* const p_rcv, IN const osm_madw_t* const p_madw ) { - ib_sa_mad_t *p_sa_mad; - ib_service_record_t* p_recvd_service_rec; - ib_net64_t comp_mask; - osm_svcr_t* p_svcr; - osm_sr_item_t* p_sr_item; - cl_qlist_t sr_list; + ib_sa_mad_t * p_sa_mad; + ib_service_record_t* p_recvd_service_rec; + ib_net64_t comp_mask; + osm_svcr_t* p_svcr; + osm_sr_item_t* p_sr_item; + cl_qlist_t sr_list; OSM_LOG_ENTER( p_rcv->p_log, osm_sr_rcv_process_delete_method ); @@ -1012,7 +1000,7 @@ osm_sr_rcv_process_delete_method( p_svcr = osm_svcr_get_by_rid( p_rcv->p_subn, p_rcv->p_log, - p_recvd_service_rec); + p_recvd_service_rec ); if(p_svcr == NULL) { @@ -1020,15 +1008,14 @@ osm_sr_rcv_process_delete_method( osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "osm_sr_rcv_process_delete_method: " "No records matched the RID\n"); - osm_sa_send_error( p_rcv->p_resp, p_madw, - IB_SA_MAD_STATUS_NO_RECORDS ); + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_SA_MAD_STATUS_NO_RECORDS ); goto Exit; } else { osm_svcr_remove_from_db(p_rcv->p_subn, p_rcv->p_log, - p_svcr); + p_svcr ); } cl_plock_release(p_rcv->p_lock); @@ -1039,8 +1026,7 @@ osm_sr_rcv_process_delete_method( osm_log( p_rcv->p_log, OSM_LOG_ERROR, "osm_sr_rcv_process_delete_method: ERR 2413: " "Unable to acquire Service record\n"); - osm_sa_send_error( p_rcv->p_resp, p_madw, - IB_SA_MAD_STATUS_NO_RESOURCES ); + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_SA_MAD_STATUS_NO_RESOURCES ); goto Exit; } @@ -1050,9 +1036,11 @@ osm_sr_rcv_process_delete_method( cl_qlist_insert_tail( &sr_list, (cl_list_item_t*)&p_sr_item->pool_item ); - if(p_svcr) osm_svcr_destroy(p_svcr); + if(p_svcr) + osm_svcr_destroy(p_svcr); __osm_sr_rcv_respond( p_rcv, p_madw, &sr_list ); + Exit: OSM_LOG_EXIT( p_rcv->p_log ); return; @@ -1065,19 +1053,17 @@ osm_sr_rcv_process( IN osm_sr_rcv_t* const p_rcv, IN const osm_madw_t* const p_madw ) { - ib_sa_mad_t *p_sa_mad; - ib_net16_t sa_status = IB_SA_MAD_STATUS_REQ_INVALID; - ib_service_record_t* p_recvd_service_rec; - boolean_t valid; - + ib_sa_mad_t * p_sa_mad; + ib_net16_t sa_status = IB_SA_MAD_STATUS_REQ_INVALID; + boolean_t valid; OSM_LOG_ENTER( p_rcv->p_log, osm_sr_rcv_process ); CL_ASSERT( p_madw ); p_sa_mad = osm_madw_get_sa_mad_ptr( p_madw ); - p_recvd_service_rec = - (ib_service_record_t*)ib_sa_mad_get_payload_ptr( p_sa_mad ); + + CL_ASSERT( p_sa_mad->attr_id == IB_MAD_ATTR_SERVICE_RECORD ); switch (p_sa_mad->method) { @@ -1087,8 +1073,8 @@ osm_sr_rcv_process( { osm_log( p_rcv->p_log, OSM_LOG_VERBOSE, "osm_sr_rcv_process: " - "Component Mask check failed\n"); - osm_sa_send_error( p_rcv->p_resp, p_madw, sa_status); + "Component Mask check failed for set request\n" ); + osm_sa_send_error( p_rcv->p_resp, p_madw, sa_status ); goto Exit; } osm_sr_rcv_process_set_method(p_rcv, p_madw); @@ -1099,8 +1085,8 @@ osm_sr_rcv_process( { osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "osm_sr_rcv_process: " - "Component Mask check failed\n"); - osm_sa_send_error( p_rcv->p_resp, p_madw, sa_status); + "Component Mask check failed for delete request\n" ); + osm_sa_send_error( p_rcv->p_resp, p_madw, sa_status ); goto Exit; } osm_sr_rcv_process_delete_method(p_rcv, p_madw); @@ -1112,8 +1098,9 @@ osm_sr_rcv_process( default: osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "osm_sr_rcv_process: " - "Bad Method (%s)\n", ib_get_sa_method_str( p_sa_mad->method )); - osm_sa_send_error( p_rcv->p_resp, p_madw, sa_status ); + "Unsupported Method (%s)\n", + ib_get_sa_method_str( p_sa_mad->method ) ); + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_MAD_STATUS_UNSUP_METHOD_ATTR ); break; } @@ -1126,15 +1113,15 @@ osm_sr_rcv_process( **********************************************************************/ void osm_sr_rcv_lease_cb( - IN void* context ) + IN void* context ) { osm_sr_rcv_t* p_rcv = (osm_sr_rcv_t*)context; cl_list_item_t* p_list_item; cl_list_item_t* p_next_list_item; - osm_svcr_t* p_svcr; - uint32_t curr_time; - uint32_t elapsed_time; - uint32_t trim_time = 20; /* maxiaml timer refresh is 20 seconds */ + osm_svcr_t* p_svcr; + uint32_t curr_time; + uint32_t elapsed_time; + uint32_t trim_time = 20; /* maxiaml timer refresh is 20 seconds */ OSM_LOG_ENTER( p_rcv->p_log, osm_sr_rcv_lease_cb ); @@ -1209,11 +1196,9 @@ osm_sr_rcv_lease_cb( if(trim_time != 0xFFFFFFFF) { cl_timer_trim(&p_rcv->sr_timer, - trim_time * 1000 ); /* Convert to milli seconds */ + trim_time * 1000); /* Convert to milli seconds */ } OSM_LOG_EXIT( p_rcv->p_log ); } -/********************************************************************** - **********************************************************************/ diff --git a/trunk/ulp/opensm/user/opensm/osm_sa_service_record_ctrl.c b/trunk/ulp/opensm/user/opensm/osm_sa_service_record_ctrl.c index 82bb91a5..003a1f45 100644 --- a/trunk/ulp/opensm/user/opensm/osm_sa_service_record_ctrl.c +++ b/trunk/ulp/opensm/user/opensm/osm_sa_service_record_ctrl.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Implementation of osm_sr_rcv_ctrl_t. @@ -48,7 +49,7 @@ # include #endif /* HAVE_CONFIG_H */ -#include +#include #include #include @@ -70,7 +71,7 @@ void osm_sr_rcv_ctrl_construct( IN osm_sr_rcv_ctrl_t* const p_ctrl ) { - cl_memclr( p_ctrl, sizeof(*p_ctrl) ); + memset( p_ctrl, 0, sizeof(*p_ctrl) ); p_ctrl->h_disp = CL_DISP_INVALID_HANDLE; } @@ -121,3 +122,4 @@ osm_sr_rcv_ctrl_init( OSM_LOG_EXIT( p_log ); return( status ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_sa_slvl_record.c b/trunk/ulp/opensm/user/opensm/osm_sa_slvl_record.c index 339a831b..4895b6be 100644 --- a/trunk/ulp/opensm/user/opensm/osm_sa_slvl_record.c +++ b/trunk/ulp/opensm/user/opensm/osm_sa_slvl_record.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -44,16 +44,12 @@ * $Revision: 1.6 $ */ -/* - Next available error code: 0x403 -*/ - #if HAVE_CONFIG_H # include #endif /* HAVE_CONFIG_H */ +#include #include -#include #include #include #include @@ -66,24 +62,22 @@ #include #define OSM_SLVL_REC_RCV_POOL_MIN_SIZE 32 -#define OSM_SLVL_REC_RCV_POOL_GROW_SIZE 32 +#define OSM_SLVL_REC_RCV_POOL_GROW_SIZE 32 typedef struct _osm_slvl_item { cl_pool_item_t pool_item; - ib_slvl_table_record_t rec; - + ib_slvl_table_record_t rec; } osm_slvl_item_t; typedef struct _osm_slvl_search_ctxt { - const ib_slvl_table_record_t* p_rcvd_rec; + const ib_slvl_table_record_t* p_rcvd_rec; ib_net64_t comp_mask; uint8_t in_port_num; cl_qlist_t* p_list; osm_slvl_rec_rcv_t* p_rcv; - const osm_physp_t* p_req_physp; - + const osm_physp_t* p_req_physp; } osm_slvl_search_ctxt_t; /********************************************************************** @@ -92,7 +86,7 @@ void osm_slvl_rec_rcv_construct( IN osm_slvl_rec_rcv_t* const p_rcv ) { - cl_memclr( p_rcv, sizeof(*p_rcv) ); + memset( p_rcv, 0, sizeof(*p_rcv) ); cl_qlock_pool_construct( &p_rcv->pool ); } @@ -111,9 +105,9 @@ osm_slvl_rec_rcv_destroy( **********************************************************************/ ib_api_status_t osm_slvl_rec_rcv_init( - IN osm_slvl_rec_rcv_t* const p_rcv, + IN osm_slvl_rec_rcv_t* const p_rcv, IN osm_sa_resp_t* const p_resp, - IN osm_mad_pool_t* const p_mad_pool, + IN osm_mad_pool_t* const p_mad_pool, IN const osm_subn_t* const p_subn, IN osm_log_t* const p_log, IN cl_plock_t* const p_lock ) @@ -146,26 +140,17 @@ osm_slvl_rec_rcv_init( **********************************************************************/ void __osm_sa_slvl_create( - IN osm_slvl_rec_rcv_t* const p_rcv, - IN const osm_physp_t* const p_physp, + IN osm_slvl_rec_rcv_t* const p_rcv, + IN const osm_physp_t* const p_physp, IN osm_slvl_search_ctxt_t* const p_ctxt, - IN uint8_t in_port_idx) + IN uint8_t in_port_idx ) { osm_slvl_item_t* p_rec_item; uint16_t lid; - ib_api_status_t status = IB_SUCCESS; + ib_api_status_t status = IB_SUCCESS; OSM_LOG_ENTER( p_rcv->p_log, __osm_sa_slvl_create ); - if (p_physp->p_node->node_info.node_type != IB_NODE_TYPE_SWITCH) - { - lid = osm_physp_get_port_info_ptr( p_physp )->base_lid; - } - else - { - lid = osm_node_get_base_lid( p_physp->p_node, 0 ); - } - p_rec_item = (osm_slvl_item_t*)cl_qlock_pool_get( &p_rcv->pool ); if( p_rec_item == NULL ) { @@ -176,9 +161,18 @@ __osm_sa_slvl_create( goto Exit; } + if (p_physp->p_node->node_info.node_type != IB_NODE_TYPE_SWITCH) + { + lid = osm_physp_get_port_info_ptr( p_physp )->base_lid; + } + else + { + lid = osm_node_get_base_lid( p_physp->p_node, 0 ); + } + if( osm_log_is_active( p_rcv->p_log, OSM_LOG_DEBUG ) ) { - osm_log( p_rcv->p_log, OSM_LOG_ERROR, + osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "__osm_sa_slvl_create: " "New SLtoVL Map for: OUT port 0x%016" PRIx64 ", lid 0x%X, port# 0x%X to In Port:%u\n", @@ -188,7 +182,7 @@ __osm_sa_slvl_create( ); } - cl_memclr( &p_rec_item->rec, sizeof( p_rec_item->rec ) ); + memset( &p_rec_item->rec, 0, sizeof( p_rec_item->rec ) ); p_rec_item->rec.lid = lid; p_rec_item->rec.out_port_num = osm_physp_get_port_num( p_physp ); @@ -206,25 +200,27 @@ __osm_sa_slvl_create( void __osm_sa_slvl_by_comp_mask( IN osm_slvl_rec_rcv_t* const p_rcv, - IN const osm_port_t* const p_port, - osm_slvl_search_ctxt_t* const p_ctxt ) + IN const osm_port_t* const p_port, + osm_slvl_search_ctxt_t* const p_ctxt ) { const ib_slvl_table_record_t* p_rcvd_rec; - ib_net64_t comp_mask; - const osm_physp_t* p_out_physp, *p_in_physp; - uint8_t in_port_num, out_port_num; - uint8_t num_ports; - uint8_t in_port_start, in_port_end; - uint8_t out_port_start, out_port_end; - const osm_physp_t* p_req_physp; + ib_net64_t comp_mask; + const osm_physp_t* p_out_physp, *p_in_physp; + uint8_t in_port_num, out_port_num; + uint8_t num_ports; + uint8_t in_port_start, in_port_end; + uint8_t out_port_start, out_port_end; + const osm_physp_t* p_req_physp; OSM_LOG_ENTER( p_rcv->p_log, __osm_sa_slvl_by_comp_mask ); p_rcvd_rec = p_ctxt->p_rcvd_rec; comp_mask = p_ctxt->comp_mask; num_ports = osm_port_get_num_physp( p_port ); - in_port_start = 0; in_port_end = num_ports; - out_port_start = 0; out_port_end = num_ports; + in_port_start = 0; + in_port_end = num_ports; + out_port_start = 0; + out_port_end = num_ports; p_req_physp = p_ctxt->p_req_physp; if ( p_port->p_node->node_info.node_type != IB_NODE_TYPE_SWITCH ) @@ -232,11 +228,11 @@ __osm_sa_slvl_by_comp_mask( osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "__osm_sa_slvl_by_comp_mask: " "Using Physical Default Port Number: 0x%X (for End Node)\n", - p_port->default_port_num); - p_out_physp = osm_port_get_phys_ptr( p_port, p_port->default_port_num); + p_port->default_port_num ); + p_out_physp = osm_port_get_phys_ptr( p_port, p_port->default_port_num ); /* check that the p_out_physp and the p_req_physp share a pkey */ - if (osm_physp_share_pkey(p_rcv->p_log, p_req_physp, p_out_physp)) - __osm_sa_slvl_create(p_rcv, p_out_physp, p_ctxt, 0); + if (osm_physp_share_pkey( p_rcv->p_log, p_req_physp, p_out_physp )) + __osm_sa_slvl_create( p_rcv, p_out_physp, p_ctxt, 0 ); } else { @@ -249,7 +245,6 @@ __osm_sa_slvl_by_comp_mask( in_port_start = in_port_end = p_rcvd_rec->in_port_num; } - for( out_port_num = out_port_start; out_port_num <= out_port_end; out_port_num++ ) { p_out_physp = osm_port_get_phys_ptr( p_port, out_port_num ); if( p_out_physp == NULL ) @@ -259,8 +254,10 @@ __osm_sa_slvl_by_comp_mask( continue; for( in_port_num = in_port_start; in_port_num <= in_port_end; in_port_num++ ) { - /* if (out_port_num && out_port_num == in_port_num) */ - /* continue; */ +#if 0 + if (out_port_num && out_port_num == in_port_num) + continue; +#endif p_in_physp = osm_port_get_phys_ptr( p_port, in_port_num ); if( p_in_physp == NULL ) @@ -286,10 +283,10 @@ __osm_sa_slvl_by_comp_mask( void __osm_sa_slvl_by_comp_mask_cb( IN cl_map_item_t* const p_map_item, - IN void* context ) + IN void* context ) { const osm_port_t* const p_port = (osm_port_t*)p_map_item; - osm_slvl_search_ctxt_t* const p_ctxt = (osm_slvl_search_ctxt_t *)context; + osm_slvl_search_ctxt_t* const p_ctxt = (osm_slvl_search_ctxt_t *)context; __osm_sa_slvl_by_comp_mask( p_ctxt->p_rcv, p_port, p_ctxt ); } @@ -299,27 +296,27 @@ __osm_sa_slvl_by_comp_mask_cb( void osm_slvl_rec_rcv_process( IN osm_slvl_rec_rcv_t* const p_rcv, - IN const osm_madw_t* const p_madw ) + IN const osm_madw_t* const p_madw ) { - const ib_sa_mad_t* p_rcvd_mad; + const ib_sa_mad_t* p_rcvd_mad; const ib_slvl_table_record_t* p_rcvd_rec; - const cl_ptr_vector_t* p_tbl; - const osm_port_t* p_port = NULL; - const ib_slvl_table_t* p_slvl_tbl; - cl_qlist_t rec_list; - osm_madw_t* p_resp_madw; - ib_sa_mad_t* p_resp_sa_mad; - ib_slvl_table_record_t* p_resp_rec; - uint32_t num_rec, pre_trim_num_rec; + const cl_ptr_vector_t* p_tbl; + const osm_port_t* p_port = NULL; + const ib_slvl_table_t* p_slvl_tbl; + cl_qlist_t rec_list; + osm_madw_t* p_resp_madw; + ib_sa_mad_t* p_resp_sa_mad; + ib_slvl_table_record_t* p_resp_rec; + uint32_t num_rec, pre_trim_num_rec; #ifndef VENDOR_RMPP_SUPPORT - uint32_t trim_num_rec; + uint32_t trim_num_rec; #endif - uint32_t i; - osm_slvl_search_ctxt_t context; - osm_slvl_item_t* p_rec_item; - ib_api_status_t status; - ib_net64_t comp_mask; - osm_physp_t* p_req_physp; + uint32_t i; + osm_slvl_search_ctxt_t context; + osm_slvl_item_t* p_rec_item; + ib_api_status_t status = IB_SUCCESS; + ib_net64_t comp_mask; + osm_physp_t* p_req_physp; CL_ASSERT( p_rcv ); @@ -333,6 +330,18 @@ osm_slvl_rec_rcv_process( CL_ASSERT( p_rcvd_mad->attr_id == IB_MAD_ATTR_SLVL_RECORD ); + /* we only support SubnAdmGet and SubnAdmGetTable methods */ + if ( (p_rcvd_mad->method != IB_MAD_METHOD_GET) && + (p_rcvd_mad->method != IB_MAD_METHOD_GETTABLE) ) + { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "osm_slvl_rec_rcv_process: ERR 2604: " + "Unsupported Method (%s)\n", + ib_get_sa_method_str( p_rcvd_mad->method ) ); + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_MAD_STATUS_UNSUP_METHOD_ATTR ); + goto Exit; + } + /* update the requester physical port. */ p_req_physp = osm_get_physp_by_mad_addr(p_rcv->p_log, p_rcv->p_subn, @@ -345,18 +354,6 @@ osm_slvl_rec_rcv_process( goto Exit; } - if ( (p_rcvd_mad->method != IB_MAD_METHOD_GET) && - (p_rcvd_mad->method != IB_MAD_METHOD_GETTABLE) ) - { - osm_log( p_rcv->p_log, OSM_LOG_ERROR, - "osm_slvl_rec_rcv_process: ERR 2604: " - "Unsupported Method (%s)\n", - ib_get_sa_method_str( p_rcvd_mad->method ) ); - osm_sa_send_error( p_rcv->p_resp, p_madw, IB_SA_MAD_STATUS_REQ_INVALID); - goto Exit; - } - - p_tbl = &p_rcv->p_subn->port_lid_tbl; p_slvl_tbl = (ib_slvl_table_t*)ib_sa_mad_get_payload_ptr( p_rcvd_mad ); cl_qlist_init( &rec_list ); @@ -373,9 +370,9 @@ osm_slvl_rec_rcv_process( osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "osm_slvl_rec_rcv_process: " "Got Query Lid:0x%04X(%02X), In-Port:0x%02X(%02X), Out-Port:0x%02X(%02X)\n", - cl_ntoh16(p_rcvd_rec->lid), (comp_mask &IB_SLVL_COMPMASK_LID) != 0, - p_rcvd_rec->in_port_num, (comp_mask &IB_SLVL_COMPMASK_IN_PORT) != 0, - p_rcvd_rec->out_port_num, (comp_mask &IB_SLVL_COMPMASK_OUT_PORT) != 0) ; + cl_ntoh16(p_rcvd_rec->lid), (comp_mask & IB_SLVL_COMPMASK_LID) != 0, + p_rcvd_rec->in_port_num, (comp_mask & IB_SLVL_COMPMASK_IN_PORT) != 0, + p_rcvd_rec->out_port_num, (comp_mask & IB_SLVL_COMPMASK_OUT_PORT) != 0 ); /* If the user specified a LID, it obviously narrows our @@ -384,30 +381,33 @@ osm_slvl_rec_rcv_process( if( comp_mask & IB_SLVL_COMPMASK_LID ) { + p_tbl = &p_rcv->p_subn->port_lid_tbl; + CL_ASSERT( cl_ptr_vector_get_size(p_tbl) < 0x10000 ); - if ((uint16_t)cl_ptr_vector_get_size(p_tbl) > cl_ntoh16(p_rcvd_rec->lid)) + status = osm_get_port_by_base_lid( p_rcv->p_subn, p_rcvd_rec->lid, &p_port ); + if ( ( status != IB_SUCCESS ) || ( p_port == NULL ) ) { - p_port = cl_ptr_vector_get( p_tbl, cl_ntoh16(p_rcvd_rec->lid) ); - } - else - { /* port out of range */ + status = IB_NOT_FOUND; osm_log( p_rcv->p_log, OSM_LOG_ERROR, - "osm_slvl_rec_rcv_process: " - "Given LID (%u) is out of range:%u\n", - cl_ntoh16(p_rcvd_rec->lid), cl_ptr_vector_get_size(p_tbl)); + "osm_slvl_rec_rcv_process: ERR 2608: " + "No port found with LID 0x%x\n", + cl_ntoh16(p_rcvd_rec->lid) ); } } - /* if we have a unique port - no need for a port search */ - if( p_port ) - /* this does the loop on all the port phys ports */ - __osm_sa_slvl_by_comp_mask( p_rcv, p_port, &context ); - else + if ( status == IB_SUCCESS ) { - cl_qmap_apply_func( &p_rcv->p_subn->port_guid_tbl, - __osm_sa_slvl_by_comp_mask_cb, - &context ); + /* if we have a unique port - no need for a port search */ + if( p_port ) + /* this does the loop on all the port phys ports */ + __osm_sa_slvl_by_comp_mask( p_rcv, p_port, &context ); + else + { + cl_qmap_apply_func( &p_rcv->p_subn->port_guid_tbl, + __osm_sa_slvl_by_comp_mask_cb, + &context ); + } } cl_plock_release( p_rcv->p_lock ); @@ -418,24 +418,32 @@ osm_slvl_rec_rcv_process( * C15-0.1.30: * If we do a SubnAdmGet and got more than one record it is an error ! */ - if ( (p_rcvd_mad->method == IB_MAD_METHOD_GET) && - (num_rec > 1)) { - osm_log( p_rcv->p_log, OSM_LOG_ERROR, - "osm_slvl_rec_rcv_process: " - "Got more than one record for SubnAdmGet (%u)\n", - num_rec ); - osm_sa_send_error( p_rcv->p_resp, p_madw, - IB_SA_MAD_STATUS_TOO_MANY_RECORDS); - - /* need to set the mem free ... */ - p_rec_item = (osm_slvl_item_t*)cl_qlist_remove_head( &rec_list ); - while( p_rec_item != (osm_slvl_item_t*)cl_qlist_end( &rec_list ) ) + if (p_rcvd_mad->method == IB_MAD_METHOD_GET) + { + if (num_rec == 0) { - cl_qlock_pool_put( &p_rcv->pool, &p_rec_item->pool_item ); - p_rec_item = (osm_slvl_item_t*)cl_qlist_remove_head( &rec_list ); + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_SA_MAD_STATUS_NO_RECORDS ); + goto Exit; } + if (num_rec > 1) + { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "osm_slvl_rec_rcv_process: ERR 2607: " + "Got more than one record for SubnAdmGet (%u)\n", + num_rec ); + osm_sa_send_error( p_rcv->p_resp, p_madw, + IB_SA_MAD_STATUS_TOO_MANY_RECORDS ); - goto Exit; + /* need to set the mem free ... */ + p_rec_item = (osm_slvl_item_t*)cl_qlist_remove_head( &rec_list ); + while( p_rec_item != (osm_slvl_item_t*)cl_qlist_end( &rec_list ) ) + { + cl_qlock_pool_put( &p_rcv->pool, &p_rec_item->pool_item ); + p_rec_item = (osm_slvl_item_t*)cl_qlist_remove_head( &rec_list ); + } + + goto Exit; + } } pre_trim_num_rec = num_rec; @@ -457,8 +465,7 @@ osm_slvl_rec_rcv_process( if ((p_rcvd_mad->method == IB_MAD_METHOD_GET) && (num_rec == 0)) { - osm_sa_send_error( p_rcv->p_resp, p_madw, - IB_SA_MAD_STATUS_NO_RECORDS ); + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_SA_MAD_STATUS_NO_RECORDS ); goto Exit; } @@ -472,9 +479,9 @@ osm_slvl_rec_rcv_process( if( !p_resp_madw ) { - osm_log(p_rcv->p_log, OSM_LOG_ERROR, - "osm_slvl_rec_rcv_process: ERR 2605: " - "osm_mad_pool_get failed\n" ); + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "osm_slvl_rec_rcv_process: ERR 2605: " + "osm_mad_pool_get failed\n" ); for( i = 0; i < num_rec; i++ ) { @@ -482,9 +489,7 @@ osm_slvl_rec_rcv_process( cl_qlock_pool_put( &p_rcv->pool, &p_rec_item->pool_item ); } - osm_sa_send_error( p_rcv->p_resp, p_madw, - IB_SA_MAD_STATUS_NO_RESOURCES ); - + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_SA_MAD_STATUS_NO_RESOURCES ); goto Exit; } @@ -496,9 +501,9 @@ osm_slvl_rec_rcv_process( Then copy all records from the list into the response payload. */ - cl_memcpy( p_resp_sa_mad, p_rcvd_mad, IB_SA_MAD_HDR_SIZE ); - p_resp_sa_mad->method = (uint8_t)(p_resp_sa_mad->method | 0x80); - /* C15-0.1.5 - always return SM_Key = 0 (table 151 p 782) */ + memcpy( p_resp_sa_mad, p_rcvd_mad, IB_SA_MAD_HDR_SIZE ); + p_resp_sa_mad->method |= IB_MAD_METHOD_RESP_MASK; + /* C15-0.1.5 - always return SM_Key = 0 (table 185 p 884) */ p_resp_sa_mad->sm_key = 0; /* Fill in the offset (paylen will be done by the rmpp SAR) */ @@ -539,10 +544,10 @@ osm_slvl_rec_rcv_process( status = osm_vendor_send( p_resp_madw->h_bind, p_resp_madw, FALSE); if(status != IB_SUCCESS) { - osm_log(p_rcv->p_log, OSM_LOG_ERROR, - "osm_slvl_rec_rcv_process: ERR 2606: " - "osm_vendor_send. status = %s\n", - ib_get_err_str(status)); + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "osm_slvl_rec_rcv_process: ERR 2606: " + "osm_vendor_send status = %s\n", + ib_get_err_str(status) ); goto Exit; } diff --git a/trunk/ulp/opensm/user/opensm/osm_sa_slvl_record_ctrl.c b/trunk/ulp/opensm/user/opensm/osm_sa_slvl_record_ctrl.c index a08be54b..5faee333 100644 --- a/trunk/ulp/opensm/user/opensm/osm_sa_slvl_record_ctrl.c +++ b/trunk/ulp/opensm/user/opensm/osm_sa_slvl_record_ctrl.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Implementation of osm_slvl_rec_rcv_ctrl_t. @@ -44,15 +45,11 @@ * $Revision: 1.4 $ */ -/* - Next available error code: 0x203 -*/ - #if HAVE_CONFIG_H # include #endif /* HAVE_CONFIG_H */ -#include +#include #include #include @@ -74,7 +71,7 @@ void osm_slvl_rec_rcv_ctrl_construct( IN osm_slvl_rec_rcv_ctrl_t* const p_ctrl ) { - cl_memclr( p_ctrl, sizeof(*p_ctrl) ); + memset( p_ctrl, 0, sizeof(*p_ctrl) ); p_ctrl->h_disp = CL_DISP_INVALID_HANDLE; } @@ -126,3 +123,4 @@ osm_slvl_rec_rcv_ctrl_init( return( status ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_sa_sminfo_record.c b/trunk/ulp/opensm/user/opensm/osm_sa_sminfo_record.c index f7bd45cc..258cd2a5 100644 --- a/trunk/ulp/opensm/user/opensm/osm_sa_sminfo_record.c +++ b/trunk/ulp/opensm/user/opensm/osm_sa_sminfo_record.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -44,16 +44,12 @@ * $Revision: 1.7 $ */ -/* - Next available error code: 0x403 -*/ - #if HAVE_CONFIG_H # include #endif /* HAVE_CONFIG_H */ +#include #include -#include #include #include #include @@ -70,6 +66,25 @@ #include #include #include +#include + +#define OSM_SMIR_RCV_POOL_MIN_SIZE 32 +#define OSM_SMIR_RCV_POOL_GROW_SIZE 32 + +typedef struct _osm_smir_item +{ + cl_pool_item_t pool_item; + ib_sminfo_record_t rec; +} osm_smir_item_t; + +typedef struct _osm_smir_search_ctxt +{ + const ib_sminfo_record_t* p_rcvd_rec; + ib_net64_t comp_mask; + cl_qlist_t* p_list; + osm_smir_rcv_t* p_rcv; + const osm_physp_t* p_req_physp; +} osm_smir_search_ctxt_t; /********************************************************************** **********************************************************************/ @@ -77,7 +92,8 @@ void osm_smir_rcv_construct( IN osm_smir_rcv_t* const p_rcv ) { - cl_memclr( p_rcv, sizeof(*p_rcv) ); + memset( p_rcv, 0, sizeof(*p_rcv) ); + cl_qlock_pool_construct( &p_rcv->pool ); } /********************************************************************** @@ -89,7 +105,7 @@ osm_smir_rcv_destroy( CL_ASSERT( p_rcv ); OSM_LOG_ENTER( p_rcv->p_log, osm_smir_rcv_destroy ); - + cl_qlock_pool_destroy( &p_rcv->pool ); OSM_LOG_EXIT( p_rcv->p_log ); } @@ -98,12 +114,12 @@ osm_smir_rcv_destroy( ib_api_status_t osm_smir_rcv_init( IN osm_smir_rcv_t* const p_rcv, - IN osm_sa_resp_t* const p_resp, + IN osm_sa_resp_t* const p_resp, IN osm_mad_pool_t* const p_mad_pool, - IN osm_subn_t* const p_subn, - IN osm_stats_t* const p_stats, - IN osm_log_t* const p_log, - IN cl_plock_t* const p_lock ) + IN osm_subn_t* const p_subn, + IN osm_stats_t* const p_stats, + IN osm_log_t* const p_log, + IN cl_plock_t* const p_lock ) { ib_api_status_t status = IB_SUCCESS; @@ -118,26 +134,155 @@ osm_smir_rcv_init( p_rcv->p_stats = p_stats; p_rcv->p_mad_pool = p_mad_pool; + status = cl_qlock_pool_init( &p_rcv->pool, + OSM_SMIR_RCV_POOL_MIN_SIZE, + 0, + OSM_SMIR_RCV_POOL_GROW_SIZE, + sizeof(osm_smir_item_t), + NULL, NULL, NULL ); + + OSM_LOG_EXIT( p_rcv->p_log ); + return( status ); +} + +static ib_api_status_t +__osm_smir_rcv_new_smir( + IN osm_smir_rcv_t* const p_rcv, + IN const osm_port_t* const p_port, + IN cl_qlist_t* const p_list, + IN ib_net64_t const guid, + IN ib_net32_t const act_count, + IN uint8_t const pri_state, + IN const osm_physp_t* const p_req_physp ) +{ + osm_smir_item_t* p_rec_item; + ib_api_status_t status = IB_SUCCESS; + + OSM_LOG_ENTER( p_rcv->p_log, __osm_smir_rcv_new_smir ); + + p_rec_item = (osm_smir_item_t*)cl_qlock_pool_get( &p_rcv->pool ); + if( p_rec_item == NULL ) + { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "__osm_smir_rcv_new_smir: ERR 2801: " + "cl_qlock_pool_get failed\n" ); + status = IB_INSUFFICIENT_RESOURCES; + goto Exit; + } + + if( osm_log_is_active( p_rcv->p_log, OSM_LOG_DEBUG ) ) + { + osm_log( p_rcv->p_log, OSM_LOG_DEBUG, + "__osm_smir_rcv_new_smir: " + "New SMInfo: GUID 0x%016" PRIx64 "\n", + cl_ntoh64( guid ) + ); + } + + memset( &p_rec_item->rec, 0, sizeof(ib_sminfo_record_t) ); + + p_rec_item->rec.lid = osm_port_get_base_lid( p_port ); + p_rec_item->rec.sm_info.guid = guid; + p_rec_item->rec.sm_info.act_count = act_count; + p_rec_item->rec.sm_info.pri_state = pri_state; + + cl_qlist_insert_tail( p_list, (cl_list_item_t*)&p_rec_item->pool_item ); + + Exit: OSM_LOG_EXIT( p_rcv->p_log ); return( status ); } +/********************************************************************** + **********************************************************************/ +static void +__osm_sa_smir_by_comp_mask( + IN osm_smir_rcv_t* const p_rcv, + IN const osm_remote_sm_t* const p_rem_sm, + osm_smir_search_ctxt_t* const p_ctxt ) +{ + const ib_sminfo_record_t* const p_rcvd_rec = p_ctxt->p_rcvd_rec; + const osm_physp_t* const p_req_physp = p_ctxt->p_req_physp; + ib_net64_t const comp_mask = p_ctxt->comp_mask; + + OSM_LOG_ENTER( p_rcv->p_log, __osm_sa_smir_by_comp_mask ); + + if ( comp_mask & IB_SMIR_COMPMASK_GUID ) + { + if ( p_rem_sm->smi.guid != p_rcvd_rec->sm_info.guid ) + goto Exit; + } + + if ( comp_mask & IB_SMIR_COMPMASK_PRIORITY ) + { + if ( ib_sminfo_get_priority( &p_rem_sm->smi ) != + ib_sminfo_get_priority( &p_rcvd_rec->sm_info ) ) + goto Exit; + } + + if ( comp_mask & IB_SMIR_COMPMASK_SMSTATE ) + { + if ( ib_sminfo_get_state( &p_rem_sm->smi ) != + ib_sminfo_get_state( &p_rcvd_rec->sm_info ) ) + goto Exit; + } + + /* Implement any other needed search cases */ + + __osm_smir_rcv_new_smir( p_rcv, p_rem_sm->p_port, p_ctxt->p_list, + p_rem_sm->smi.guid, + p_rem_sm->smi.act_count, + p_rem_sm->smi.pri_state, + p_req_physp ); + + Exit: + OSM_LOG_EXIT( p_rcv->p_log ); +} + +/********************************************************************** + **********************************************************************/ +static void +__osm_sa_smir_by_comp_mask_cb( + IN cl_map_item_t* const p_map_item, + IN void* context ) +{ + const osm_remote_sm_t* const p_rem_sm = (osm_remote_sm_t*)p_map_item; + osm_smir_search_ctxt_t* const p_ctxt = (osm_smir_search_ctxt_t *)context; + + __osm_sa_smir_by_comp_mask( p_ctxt->p_rcv, p_rem_sm, p_ctxt ); +} + /********************************************************************** **********************************************************************/ void osm_smir_rcv_process( - IN osm_smir_rcv_t* const p_rcv, - IN const osm_madw_t* const p_madw ) + IN osm_smir_rcv_t* const p_rcv, + IN const osm_madw_t* const p_madw ) { - const ib_sminfo_record_t* p_sminfo_rec; - ib_sminfo_record_t* p_resp_sminfo_rec; - const ib_sa_mad_t* p_sa_mad; - ib_sa_mad_t* p_resp_sa_mad; - osm_madw_t* p_resp_madw; - ib_api_status_t status; - osm_physp_t* p_req_physp; - ib_net64_t local_guid; - osm_port_t* local_port; + const ib_sa_mad_t* p_rcvd_mad; + const ib_sminfo_record_t* p_rcvd_rec; + const cl_qmap_t* p_tbl; + const osm_port_t* p_port = NULL; + const ib_sm_info_t* p_smi; + cl_qlist_t rec_list; + osm_madw_t* p_resp_madw; + ib_sa_mad_t* p_resp_sa_mad; + ib_sminfo_record_t* p_resp_rec; + uint32_t num_rec, pre_trim_num_rec; +#ifndef VENDOR_RMPP_SUPPORT + uint32_t trim_num_rec; +#endif + uint32_t i; + osm_smir_search_ctxt_t context; + osm_smir_item_t* p_rec_item; + ib_api_status_t status = IB_SUCCESS; + ib_net64_t comp_mask; + ib_net64_t port_guid; + osm_physp_t* p_req_physp; + osm_port_t* local_port; + osm_remote_sm_t* p_rem_sm; + cl_qmap_t* p_sm_guid_tbl; + uint8_t pri_state; CL_ASSERT( p_rcv ); @@ -145,8 +290,23 @@ osm_smir_rcv_process( CL_ASSERT( p_madw ); - p_sa_mad = osm_madw_get_sa_mad_ptr( p_madw ); - p_sminfo_rec = (ib_sminfo_record_t*)ib_sa_mad_get_payload_ptr( p_sa_mad ); + p_rcvd_mad = osm_madw_get_sa_mad_ptr( p_madw ); + p_rcvd_rec = (ib_sminfo_record_t*)ib_sa_mad_get_payload_ptr( p_rcvd_mad ); + comp_mask = p_rcvd_mad->comp_mask; + + CL_ASSERT( p_rcvd_mad->attr_id == IB_MAD_ATTR_SMINFO_RECORD ); + + /* we only support SubnAdmGet and SubnAdmGetTable methods */ + if ( (p_rcvd_mad->method != IB_MAD_METHOD_GET) && + (p_rcvd_mad->method != IB_MAD_METHOD_GETTABLE) ) + { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "osm_smir_rcv_process: ERR 2804: " + "Unsupported Method (%s)\n", + ib_get_sa_method_str( p_rcvd_mad->method ) ); + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_MAD_STATUS_UNSUP_METHOD_ATTR ); + goto Exit; + } /* update the requester physical port. */ p_req_physp = osm_get_physp_by_mad_addr(p_rcv->p_log, @@ -160,79 +320,252 @@ osm_smir_rcv_process( goto Exit; } - CL_ASSERT( p_sa_mad->attr_id == IB_MAD_ATTR_SMINFO_RECORD ); + if ( osm_log_is_active( p_rcv->p_log, OSM_LOG_DEBUG ) ) + osm_dump_sm_info_record( p_rcv->p_log, p_rcvd_rec, OSM_LOG_DEBUG ); + + p_tbl = &p_rcv->p_subn->sm_guid_tbl; + p_smi = &p_rcvd_rec->sm_info; + + cl_qlist_init( &rec_list ); + + context.p_rcvd_rec = p_rcvd_rec; + context.p_list = &rec_list; + context.comp_mask = p_rcvd_mad->comp_mask; + context.p_rcv = p_rcv; + context.p_req_physp = p_req_physp; - if ( (p_sa_mad->method != IB_MAD_METHOD_GET) && - (p_sa_mad->method != IB_MAD_METHOD_GETTABLE) ) + cl_plock_acquire( p_rcv->p_lock ); + + /* + If the user specified a LID, it obviously narrows our + work load, since we don't have to search every port + */ + if( comp_mask & IB_SMIR_COMPMASK_LID ) { - osm_log( p_rcv->p_log, OSM_LOG_ERROR, - "osm_smir_rcv_process: ERR 2804: " - "Unsupported Method (%s)\n", - ib_get_sa_method_str( p_sa_mad->method ) ); - osm_sa_send_error( p_rcv->p_resp, p_madw, IB_SA_MAD_STATUS_REQ_INVALID); - goto Exit; + status = osm_get_port_by_base_lid( p_rcv->p_subn, p_rcvd_rec->lid, &p_port ); + if ( ( status != IB_SUCCESS ) || ( p_port == NULL ) ) + { + status = IB_NOT_FOUND; + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "osm_smir_rcv_process: ERR 2806: " + "No port found with LID 0x%x\n", + cl_ntoh16(p_rcvd_rec->lid) ); + } } - /* - * Get a MAD to reply. Address of Mad is in the received mad_wrapper + if ( status == IB_SUCCESS ) + { + /* Handle our own SM first */ + local_port = osm_get_port_by_guid( p_rcv->p_subn, p_rcv->p_subn->sm_port_guid ); + if ( !local_port ) + { + cl_plock_release( p_rcv->p_lock ); + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "osm_smir_rcv_process: ERR 2809: " + "No port found with GUID 0x%016" PRIx64 "\n", + cl_ntoh64(p_rcv->p_subn->sm_port_guid ) ); + goto Exit; + } + + if ( !p_port || local_port == p_port ) + { + if (FALSE == + osm_physp_share_pkey( p_rcv->p_log, p_req_physp, + osm_port_get_default_phys_ptr( local_port ) ) ) + { + cl_plock_release( p_rcv->p_lock ); + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "osm_smir_rcv_process: ERR 2805: " + "Cannot get SMInfo record due to pkey violation\n" ); + goto Exit; + } + + /* Check that other search components specified match */ + if ( comp_mask & IB_SMIR_COMPMASK_GUID ) + { + if ( p_rcv->p_subn->sm_port_guid != p_smi->guid ) + goto Remotes; + } + if ( comp_mask & IB_SMIR_COMPMASK_PRIORITY ) + { + if ( p_rcv->p_subn->opt.sm_priority != ib_sminfo_get_priority( p_smi ) ) + goto Remotes; + } + if ( comp_mask & IB_SMIR_COMPMASK_SMSTATE ) + { + if ( p_rcv->p_subn->sm_state != ib_sminfo_get_state( p_smi ) ) + goto Remotes; + } + + /* Now, add local SMInfo to list */ + pri_state = p_rcv->p_subn->sm_state & 0x0F; + pri_state |= (p_rcv->p_subn->opt.sm_priority & 0x0F) << 4; + __osm_smir_rcv_new_smir( p_rcv, local_port, context.p_list, + p_rcv->p_subn->sm_port_guid, + cl_ntoh32( p_rcv->p_stats->qp0_mads_sent ), + pri_state, + p_req_physp ); + } + + Remotes: + if( p_port && p_port != local_port ) + { + /* Find remote SM corresponding to p_port */ + port_guid = osm_port_get_guid( p_port ); + p_sm_guid_tbl = &p_rcv->p_subn->sm_guid_tbl; + p_rem_sm = (osm_remote_sm_t*)cl_qmap_get( p_sm_guid_tbl, port_guid ); + if (p_rem_sm != (osm_remote_sm_t*)cl_qmap_end( p_sm_guid_tbl ) ) + __osm_sa_smir_by_comp_mask( p_rcv, p_rem_sm, &context ); + else + { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "osm_smir_rcv_process: ERR 280A: " + "No remote SM for GUID 0x%016" PRIx64 "\n", + cl_ntoh64( port_guid ) ); + } + } + else + { + /* Go over all other known (remote) SMs */ + cl_qmap_apply_func( &p_rcv->p_subn->sm_guid_tbl, + __osm_sa_smir_by_comp_mask_cb, + &context ); + } + } + + cl_plock_release( p_rcv->p_lock ); + + num_rec = cl_qlist_count( &rec_list ); + + /* + * C15-0.1.30: + * If we do a SubnAdmGet and got more than one record it is an error ! */ - p_resp_madw = osm_mad_pool_get(p_rcv->p_mad_pool, - p_madw->h_bind, - sizeof(ib_sminfo_record_t)+IB_SA_MAD_HDR_SIZE, - &p_madw->mad_addr ); - if( !p_resp_madw ) + if (p_rcvd_mad->method == IB_MAD_METHOD_GET) { - osm_log(p_rcv->p_log, OSM_LOG_ERROR, - "osm_smir_rcv_process: ERR 2801: " - "Unable to acquire response MAD\n" ); - goto Exit; + if (num_rec == 0) + { + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_SA_MAD_STATUS_NO_RECORDS ); + goto Exit; + } + if (num_rec > 1) + { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "osm_smir_rcv_process: ERR 2808: " + "Got more than one record for SubnAdmGet (%u)\n", + num_rec ); + osm_sa_send_error( p_rcv->p_resp, p_madw, + IB_SA_MAD_STATUS_TOO_MANY_RECORDS); + + /* need to set the mem free ... */ + p_rec_item = (osm_smir_item_t*)cl_qlist_remove_head( &rec_list ); + while( p_rec_item != (osm_smir_item_t*)cl_qlist_end( &rec_list ) ) + { + cl_qlock_pool_put( &p_rcv->pool, &p_rec_item->pool_item ); + p_rec_item = (osm_smir_item_t*)cl_qlist_remove_head( &rec_list ); + } + + goto Exit; + } } - p_resp_sa_mad = osm_madw_get_sa_mad_ptr( p_resp_madw ); - p_resp_sminfo_rec = - (ib_sminfo_record_t*)ib_sa_mad_get_payload_ptr( p_resp_sa_mad ); + pre_trim_num_rec = num_rec; +#ifndef VENDOR_RMPP_SUPPORT + trim_num_rec = (MAD_BLOCK_SIZE - IB_SA_MAD_HDR_SIZE) / sizeof(ib_sminfo_record_t); + if (trim_num_rec < num_rec) + { + osm_log( p_rcv->p_log, OSM_LOG_VERBOSE, + "osm_smir_rcv_process: " + "Number of records:%u trimmed to:%u to fit in one MAD\n", + num_rec, trim_num_rec ); + num_rec = trim_num_rec; + } +#endif - p_resp_sminfo_rec->resv0 = 0; + osm_log( p_rcv->p_log, OSM_LOG_DEBUG, + "osm_smir_rcv_process: " + "Returning %u records\n", num_rec ); - /* HACK: This handling is incorrect. The record to return is - records of known SMs by our SM, and not just the details of - our SM. */ - /* check the matching of pkeys with the local physp the SM is on. */ - local_guid = p_rcv->p_subn->sm_port_guid; - local_port = (osm_port_t*)cl_qmap_get( &p_rcv->p_subn->port_guid_tbl, local_guid ); - if (FALSE == - osm_physp_share_pkey( p_rcv->p_log, p_req_physp, - osm_port_get_default_phys_ptr(local_port) )) + if ((p_rcvd_mad->method == IB_MAD_METHOD_GET) && (num_rec == 0)) { - osm_log(p_rcv->p_log, OSM_LOG_ERROR, - "osm_smir_rcv_process: ERR 2802: " - "Cannot get sminfo record - pkey violation\n" ); + osm_sa_send_error( p_rcv->p_resp, p_madw, + IB_SA_MAD_STATUS_NO_RECORDS ); goto Exit; } - cl_plock_acquire( p_rcv->p_lock ); + /* + * Get a MAD to reply. Address of Mad is in the received mad_wrapper + */ + p_resp_madw = osm_mad_pool_get( p_rcv->p_mad_pool, + p_madw->h_bind, + num_rec * sizeof(ib_sminfo_record_t) + IB_SA_MAD_HDR_SIZE, + &p_madw->mad_addr ); - /* get our local sm_base_lid to send in the sminfo */ - p_resp_sminfo_rec->lid = p_rcv->p_subn->sm_base_lid; - p_resp_sminfo_rec->sm_info.guid = p_rcv->p_subn->sm_port_guid; - p_resp_sminfo_rec->sm_info.sm_key = p_rcv->p_subn->opt.sm_key; - p_resp_sminfo_rec->sm_info.act_count = - cl_ntoh32(p_rcv->p_stats->qp0_mads_sent); - p_resp_sminfo_rec->sm_info.pri_state = p_rcv->p_subn->sm_state; + if( !p_resp_madw ) + { + osm_log(p_rcv->p_log, OSM_LOG_ERROR, + "osm_smir_rcv_process: ERR 2807: " + "osm_mad_pool_get failed\n" ); - cl_plock_release( p_rcv->p_lock ); + for( i = 0; i < num_rec; i++ ) + { + p_rec_item = (osm_smir_item_t*)cl_qlist_remove_head( &rec_list ); + cl_qlock_pool_put( &p_rcv->pool, &p_rec_item->pool_item ); + } + + osm_sa_send_error( p_rcv->p_resp, p_madw, + IB_SA_MAD_STATUS_NO_RESOURCES ); + + goto Exit; + } + + p_resp_sa_mad = osm_madw_get_sa_mad_ptr( p_resp_madw ); - p_sa_mad = osm_madw_get_sa_mad_ptr( p_madw ); + /* + Copy the MAD header back into the response mad. + Set the 'R' bit and the payload length, + Then copy all records from the list into the response payload. + */ - /* Copy the MAD header back into the response mad */ - cl_memcpy( p_resp_sa_mad, p_sa_mad, IB_SA_MAD_HDR_SIZE ); - p_resp_sa_mad->method = (uint8_t)(p_resp_sa_mad->method | 0x80); + memcpy( p_resp_sa_mad, p_rcvd_mad, IB_SA_MAD_HDR_SIZE ); + p_resp_sa_mad->method |= IB_MAD_METHOD_RESP_MASK; + /* C15-0.1.5 - always return SM_Key = 0 (table 185 p 884) */ + p_resp_sa_mad->sm_key = 0; /* Fill in the offset (paylen will be done by the rmpp SAR) */ p_resp_sa_mad->attr_offset = ib_get_attr_offset( sizeof(ib_sminfo_record_t) ); - /* C15-0.1.5 - always return SM_Key = 0 (table 151 p 782) */ - p_resp_sa_mad->sm_key = 0; + p_resp_rec = (ib_sminfo_record_t*) + ib_sa_mad_get_payload_ptr( p_resp_sa_mad ); + +#ifndef VENDOR_RMPP_SUPPORT + /* we support only one packet RMPP - so we will set the first and + last flags for gettable */ + if (p_resp_sa_mad->method == IB_MAD_METHOD_GETTABLE_RESP) + { + p_resp_sa_mad->rmpp_type = IB_RMPP_TYPE_DATA; + p_resp_sa_mad->rmpp_flags = IB_RMPP_FLAG_FIRST | IB_RMPP_FLAG_LAST | IB_RMPP_FLAG_ACTIVE; + } +#else + /* forcefully define the packet as RMPP one */ + if (p_resp_sa_mad->method == IB_MAD_METHOD_GETTABLE_RESP) + p_resp_sa_mad->rmpp_flags = IB_RMPP_FLAG_ACTIVE; +#endif + + for( i = 0; i < pre_trim_num_rec; i++ ) + { + p_rec_item = (osm_smir_item_t*)cl_qlist_remove_head( &rec_list ); + /* copy only if not trimmed */ + if (i < num_rec) + { + *p_resp_rec = p_rec_item->rec; + p_resp_rec->sm_info.sm_key = 0; + } + cl_qlock_pool_put( &p_rcv->pool, &p_rec_item->pool_item ); + p_resp_rec++; + } + + CL_ASSERT( cl_is_qlist_empty( &rec_list ) ); status = osm_vendor_send( p_resp_madw->h_bind, p_resp_madw, FALSE ); if( status != IB_SUCCESS ) @@ -247,3 +580,4 @@ osm_smir_rcv_process( Exit: OSM_LOG_EXIT( p_rcv->p_log ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_sa_sminfo_record_ctrl.c b/trunk/ulp/opensm/user/opensm/osm_sa_sminfo_record_ctrl.c index bfb09eb0..de6a7c74 100644 --- a/trunk/ulp/opensm/user/opensm/osm_sa_sminfo_record_ctrl.c +++ b/trunk/ulp/opensm/user/opensm/osm_sa_sminfo_record_ctrl.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Implementation of osm_smir_ctrl_t. @@ -44,15 +45,11 @@ * $Revision: 1.5 $ */ -/* - Next available error code: 0x203 -*/ - #if HAVE_CONFIG_H # include #endif /* HAVE_CONFIG_H */ -#include +#include #include #include @@ -74,7 +71,7 @@ void osm_smir_ctrl_construct( IN osm_smir_ctrl_t* const p_ctrl ) { - cl_memclr( p_ctrl, sizeof(*p_ctrl) ); + memset( p_ctrl, 0, sizeof(*p_ctrl) ); p_ctrl->h_disp = CL_DISP_INVALID_HANDLE; } @@ -125,3 +122,4 @@ osm_smir_ctrl_init( OSM_LOG_EXIT( p_log ); return( status ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_sa_sw_info_record.c b/trunk/ulp/opensm/user/opensm/osm_sa_sw_info_record.c new file mode 100644 index 00000000..8c893ad3 --- /dev/null +++ b/trunk/ulp/opensm/user/opensm/osm_sa_sw_info_record.c @@ -0,0 +1,535 @@ +/* + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. + * + * This software is available to you under the OpenIB.org BSD license + * below: + * + * Redistribution and use in source and binary forms, with or + * without modification, are permitted provided that the following + * conditions are met: + * + * - Redistributions of source code must retain the above + * copyright notice, this list of conditions and the following + * disclaimer. + * + * - Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials + * provided with the distribution. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS + * BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN + * ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN + * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + * + * $Id$ + */ + + +/* + * Abstract: + * Implementation of osm_sir_rcv_t. + * This object represents the SwitchInfo Receiver object. + * This object is part of the opensm family of objects. + * + * Environment: + * Linux User Mode + * + */ + +#if HAVE_CONFIG_H +# include +#endif /* HAVE_CONFIG_H */ + +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#define OSM_SIR_RCV_POOL_MIN_SIZE 32 +#define OSM_SIR_RCV_POOL_GROW_SIZE 32 + +typedef struct _osm_sir_item +{ + cl_pool_item_t pool_item; + ib_switch_info_record_t rec; +} osm_sir_item_t; + +typedef struct _osm_sir_search_ctxt +{ + const ib_switch_info_record_t* p_rcvd_rec; + ib_net64_t comp_mask; + cl_qlist_t* p_list; + osm_sir_rcv_t* p_rcv; + const osm_physp_t* p_req_physp; +} osm_sir_search_ctxt_t; + +/********************************************************************** + **********************************************************************/ +void +osm_sir_rcv_construct( + IN osm_sir_rcv_t* const p_rcv ) +{ + memset( p_rcv, 0, sizeof(*p_rcv) ); + cl_qlock_pool_construct( &p_rcv->pool ); +} + +/********************************************************************** + **********************************************************************/ +void +osm_sir_rcv_destroy( + IN osm_sir_rcv_t* const p_rcv ) +{ + OSM_LOG_ENTER( p_rcv->p_log, osm_sir_rcv_destroy ); + cl_qlock_pool_destroy( &p_rcv->pool ); + OSM_LOG_EXIT( p_rcv->p_log ); +} + +/********************************************************************** + **********************************************************************/ +ib_api_status_t +osm_sir_rcv_init( + IN osm_sir_rcv_t* const p_rcv, + IN osm_sa_resp_t* const p_resp, + IN osm_mad_pool_t* const p_mad_pool, + IN osm_subn_t* const p_subn, + IN osm_log_t* const p_log, + IN cl_plock_t* const p_lock ) +{ + ib_api_status_t status; + + OSM_LOG_ENTER( p_log, osm_sir_rcv_init ); + + osm_sir_rcv_construct( p_rcv ); + + p_rcv->p_log = p_log; + p_rcv->p_subn = p_subn; + p_rcv->p_lock = p_lock; + p_rcv->p_resp = p_resp; + p_rcv->p_mad_pool = p_mad_pool; + + status = cl_qlock_pool_init( &p_rcv->pool, + OSM_SIR_RCV_POOL_MIN_SIZE, + 0, + OSM_SIR_RCV_POOL_GROW_SIZE, + sizeof(osm_sir_item_t), + NULL, NULL, NULL ); + + OSM_LOG_EXIT( p_log ); + return( status ); +} + +/********************************************************************** + **********************************************************************/ +static ib_api_status_t +__osm_sir_rcv_new_sir( + IN osm_sir_rcv_t* const p_rcv, + IN const osm_switch_t* const p_sw, + IN cl_qlist_t* const p_list, + IN ib_net16_t const lid ) +{ + osm_sir_item_t* p_rec_item; + ib_api_status_t status = IB_SUCCESS; + + OSM_LOG_ENTER( p_rcv->p_log, __osm_sir_rcv_new_sir ); + + p_rec_item = (osm_sir_item_t*)cl_qlock_pool_get( &p_rcv->pool ); + if( p_rec_item == NULL ) + { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "__osm_sir_rcv_new_sir: ERR 5308: " + "cl_qlock_pool_get failed\n" ); + status = IB_INSUFFICIENT_RESOURCES; + goto Exit; + } + + if( osm_log_is_active( p_rcv->p_log, OSM_LOG_DEBUG ) ) + { + osm_log( p_rcv->p_log, OSM_LOG_DEBUG, + "__osm_sir_rcv_new_sir: " + "New SwitchInfoRecord: lid 0x%X\n", + cl_ntoh16( lid ) + ); + } + + memset( &p_rec_item->rec, 0, sizeof(ib_switch_info_record_t) ); + + p_rec_item->rec.lid = lid; + p_rec_item->rec.switch_info = p_sw->switch_info; + + cl_qlist_insert_tail( p_list, (cl_list_item_t*)&p_rec_item->pool_item ); + + Exit: + OSM_LOG_EXIT( p_rcv->p_log ); + return( status ); +} + +/********************************************************************** + **********************************************************************/ +static osm_port_t* +__osm_sir_get_port_by_guid( + IN osm_sir_rcv_t* const p_rcv, + IN uint64_t port_guid ) +{ + osm_port_t* p_port; + + CL_PLOCK_ACQUIRE(p_rcv->p_lock); + + p_port = (osm_port_t *)cl_qmap_get(&p_rcv->p_subn->port_guid_tbl, + port_guid); + if (p_port == (osm_port_t *)cl_qmap_end(&p_rcv->p_subn->port_guid_tbl)) + { + osm_log( p_rcv->p_log, OSM_LOG_DEBUG, + "__osm_sir_get_port_by_guid ERR 5309: " + "Invalid port GUID 0x%016" PRIx64 "\n", + port_guid ); + p_port = NULL; + } + + CL_PLOCK_RELEASE(p_rcv->p_lock); + return p_port; +} + +/********************************************************************** + **********************************************************************/ +static void +__osm_sir_rcv_create_sir( + IN osm_sir_rcv_t* const p_rcv, + IN const osm_switch_t* const p_sw, + IN cl_qlist_t* const p_list, + IN ib_net16_t const match_lid, + IN const osm_physp_t* const p_req_physp ) +{ + osm_port_t* p_port; + const osm_physp_t* p_physp; + uint16_t match_lid_ho; + ib_net16_t min_lid_ho; + ib_net16_t max_lid_ho; + + OSM_LOG_ENTER( p_rcv->p_log, __osm_sir_rcv_create_sir ); + + if( osm_log_is_active( p_rcv->p_log, OSM_LOG_DEBUG ) ) + { + osm_log( p_rcv->p_log, OSM_LOG_DEBUG, + "__osm_sir_rcv_create_sir: " + "Looking for SwitchInfoRecord with LID: 0x%X\n", + cl_ntoh16( match_lid ) + ); + } + + /* In switches, the port guid is the node guid. */ + p_port = + __osm_sir_get_port_by_guid( p_rcv, p_sw->p_node->node_info.port_guid ); + if (! p_port) + { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "__osm_sir_rcv_create_sir: ERR 530A: " + "Failed to find Port by Node Guid:0x%016" PRIx64 + "\n", + cl_ntoh64( p_sw->p_node->node_info.node_guid ) + ); + goto Exit; + } + + /* check that the requester physp and the current physp are under + the same partition. */ + p_physp = osm_port_get_default_phys_ptr( p_port ); + if (! p_physp) + { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "__osm_sir_rcv_create_sir: ERR 530B: " + "Failed to find default physical Port by Node Guid:0x%016" PRIx64 + "\n", + cl_ntoh64( p_sw->p_node->node_info.node_guid ) + ); + goto Exit; + } + if (! osm_physp_share_pkey( p_rcv->p_log, p_req_physp, p_physp )) + goto Exit; + + /* get the port 0 of the switch */ + osm_port_get_lid_range_ho( p_port, &min_lid_ho, &max_lid_ho ); + + match_lid_ho = cl_ntoh16( match_lid ); + if( match_lid_ho ) + { + /* + We validate that the lid belongs to this switch. + */ + if( osm_log_is_active( p_rcv->p_log, OSM_LOG_DEBUG ) ) + { + osm_log( p_rcv->p_log, OSM_LOG_DEBUG, + "__osm_sir_rcv_create_sir: " + "Comparing LID: 0x%X <= 0x%X <= 0x%X\n", + min_lid_ho, match_lid_ho, max_lid_ho + ); + } + + if ( match_lid_ho < min_lid_ho || match_lid_ho > max_lid_ho ) + goto Exit; + + } + + __osm_sir_rcv_new_sir( p_rcv, p_sw, p_list, osm_port_get_base_lid(p_port) ); + +Exit: + OSM_LOG_EXIT( p_rcv->p_log ); +} + +/********************************************************************** + **********************************************************************/ +static void +__osm_sir_rcv_by_comp_mask( + IN cl_map_item_t* const p_map_item, + IN void* context ) +{ + const osm_sir_search_ctxt_t* const p_ctxt = (osm_sir_search_ctxt_t *)context; + const osm_switch_t* const p_sw = (osm_switch_t*)p_map_item; + const ib_switch_info_record_t* const p_rcvd_rec = p_ctxt->p_rcvd_rec; + const osm_physp_t* const p_req_physp = p_ctxt->p_req_physp; + osm_sir_rcv_t* const p_rcv = p_ctxt->p_rcv; + ib_net64_t const comp_mask = p_ctxt->comp_mask; + ib_net16_t match_lid = 0; + + OSM_LOG_ENTER( p_ctxt->p_rcv->p_log, __osm_sir_rcv_by_comp_mask ); + + osm_dump_switch_info( + p_ctxt->p_rcv->p_log, + &p_sw->switch_info, + OSM_LOG_VERBOSE ); + + if( comp_mask & IB_SWIR_COMPMASK_LID ) + { + match_lid = p_rcvd_rec->lid; + if (!match_lid) + goto Exit; + } + + __osm_sir_rcv_create_sir( p_rcv, p_sw, p_ctxt->p_list, + match_lid, p_req_physp ); + +Exit: + OSM_LOG_EXIT( p_ctxt->p_rcv->p_log ); +} + +/********************************************************************** + **********************************************************************/ +void +osm_sir_rcv_process( + IN osm_sir_rcv_t* const p_rcv, + IN const osm_madw_t* const p_madw ) +{ + const ib_sa_mad_t* p_rcvd_mad; + const ib_switch_info_record_t* p_rcvd_rec; + ib_switch_info_record_t* p_resp_rec; + cl_qlist_t rec_list; + osm_madw_t* p_resp_madw; + ib_sa_mad_t* p_resp_sa_mad; + uint32_t num_rec, pre_trim_num_rec; +#ifndef VENDOR_RMPP_SUPPORT + uint32_t trim_num_rec; +#endif + uint32_t i; + osm_sir_search_ctxt_t context; + osm_sir_item_t* p_rec_item; + ib_api_status_t status; + osm_physp_t* p_req_physp; + + CL_ASSERT( p_rcv ); + + OSM_LOG_ENTER( p_rcv->p_log, osm_sir_rcv_process ); + + CL_ASSERT( p_madw ); + + p_rcvd_mad = osm_madw_get_sa_mad_ptr( p_madw ); + p_rcvd_rec = (ib_switch_info_record_t*)ib_sa_mad_get_payload_ptr( p_rcvd_mad ); + + CL_ASSERT( p_rcvd_mad->attr_id == IB_MAD_ATTR_SWITCH_INFO_RECORD ); + + /* we only support SubnAdmGet and SubnAdmGetTable methods */ + if ( (p_rcvd_mad->method != IB_MAD_METHOD_GET) && + (p_rcvd_mad->method != IB_MAD_METHOD_GETTABLE) ) { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "osm_sir_rcv_process: ERR 5305: " + "Unsupported Method (%s)\n", + ib_get_sa_method_str( p_rcvd_mad->method ) ); + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_MAD_STATUS_UNSUP_METHOD_ATTR ); + goto Exit; + } + + /* update the requester physical port. */ + p_req_physp = osm_get_physp_by_mad_addr(p_rcv->p_log, + p_rcv->p_subn, + osm_madw_get_mad_addr_ptr(p_madw) ); + if (p_req_physp == NULL) + { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "osm_sir_rcv_process: ERR 5304: " + "Cannot find requester physical port\n" ); + goto Exit; + } + + if ( osm_log_is_active( p_rcv->p_log, OSM_LOG_DEBUG ) ) + osm_dump_switch_info_record( p_rcv->p_log, p_rcvd_rec, OSM_LOG_DEBUG ); + + cl_qlist_init( &rec_list ); + + context.p_rcvd_rec = p_rcvd_rec; + context.p_list = &rec_list; + context.comp_mask = p_rcvd_mad->comp_mask; + context.p_rcv = p_rcv; + context.p_req_physp = p_req_physp; + + cl_plock_acquire( p_rcv->p_lock ); + + /* Go over all switches */ + cl_qmap_apply_func( &p_rcv->p_subn->sw_guid_tbl, + __osm_sir_rcv_by_comp_mask, + &context ); + + cl_plock_release( p_rcv->p_lock ); + + num_rec = cl_qlist_count( &rec_list ); + + /* + * C15-0.1.30: + * If we do a SubnAdmGet and got more than one record it is an error ! + */ + if ( (p_rcvd_mad->method == IB_MAD_METHOD_GET) && (num_rec > 1) ) { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "osm_sir_rcv_process: ERR 5303: " + "Got more than one record for SubnAdmGet (%u)\n", + num_rec ); + osm_sa_send_error( p_rcv->p_resp, p_madw, + IB_SA_MAD_STATUS_TOO_MANY_RECORDS ); + + /* need to set the mem free ... */ + p_rec_item = (osm_sir_item_t*)cl_qlist_remove_head( &rec_list ); + while( p_rec_item != (osm_sir_item_t*)cl_qlist_end( &rec_list ) ) + { + cl_qlock_pool_put( &p_rcv->pool, &p_rec_item->pool_item ); + p_rec_item = (osm_sir_item_t*)cl_qlist_remove_head( &rec_list ); + } + + goto Exit; + } + + pre_trim_num_rec = num_rec; +#ifndef VENDOR_RMPP_SUPPORT + /* we limit the number of records to a single packet */ + trim_num_rec = (MAD_BLOCK_SIZE - IB_SA_MAD_HDR_SIZE) / sizeof(ib_switch_info_record_t); + if (trim_num_rec < num_rec) + { + osm_log( p_rcv->p_log, OSM_LOG_VERBOSE, + "osm_sir_rcv_process: " + "Number of records:%u trimmed to:%u to fit in one MAD\n", + num_rec, trim_num_rec ); + num_rec = trim_num_rec; + } +#endif + + osm_log( p_rcv->p_log, OSM_LOG_DEBUG, + "osm_sir_rcv_process: " + "Returning %u records\n", num_rec ); + + if ((p_rcvd_mad->method == IB_MAD_METHOD_GET) && (num_rec == 0)) + { + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_SA_MAD_STATUS_NO_RECORDS ); + goto Exit; + } + + /* + * Get a MAD to reply. Address of Mad is in the received mad_wrapper + */ + p_resp_madw = osm_mad_pool_get( p_rcv->p_mad_pool, + p_madw->h_bind, + num_rec * sizeof(ib_switch_info_record_t) + IB_SA_MAD_HDR_SIZE, + &p_madw->mad_addr ); + + if( !p_resp_madw ) + { + osm_log(p_rcv->p_log, OSM_LOG_ERROR, + "osm_sir_rcv_process: ERR 5306: " + "osm_mad_pool_get failed\n" ); + + for( i = 0; i < num_rec; i++ ) + { + p_rec_item = (osm_sir_item_t*)cl_qlist_remove_head( &rec_list ); + cl_qlock_pool_put( &p_rcv->pool, &p_rec_item->pool_item ); + } + + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_SA_MAD_STATUS_NO_RESOURCES ); + goto Exit; + } + + p_resp_sa_mad = osm_madw_get_sa_mad_ptr( p_resp_madw ); + + /* + Copy the MAD header back into the response mad. + Set the 'R' bit and the payload length, + Then copy all records from the list into the response payload. + */ + + memcpy( p_resp_sa_mad, p_rcvd_mad, IB_SA_MAD_HDR_SIZE ); + p_resp_sa_mad->method |= IB_MAD_METHOD_RESP_MASK; + /* C15-0.1.5 - always return SM_Key = 0 (table 185 p 884) */ + p_resp_sa_mad->sm_key = 0; + /* Fill in the offset (paylen will be done by the rmpp SAR) */ + p_resp_sa_mad->attr_offset = + ib_get_attr_offset( sizeof(ib_switch_info_record_t) ); + + p_resp_rec = (ib_switch_info_record_t*)ib_sa_mad_get_payload_ptr( p_resp_sa_mad ); + +#ifndef VENDOR_RMPP_SUPPORT + /* we support only one packet RMPP - so we will set the first and + last flags for gettable */ + if (p_resp_sa_mad->method == IB_MAD_METHOD_GETTABLE_RESP) + { + p_resp_sa_mad->rmpp_type = IB_RMPP_TYPE_DATA; + p_resp_sa_mad->rmpp_flags = IB_RMPP_FLAG_FIRST | IB_RMPP_FLAG_LAST | IB_RMPP_FLAG_ACTIVE; + } +#else + /* forcefully define the packet as RMPP one */ + if (p_resp_sa_mad->method == IB_MAD_METHOD_GETTABLE_RESP) + p_resp_sa_mad->rmpp_flags = IB_RMPP_FLAG_ACTIVE; +#endif + + for( i = 0; i < pre_trim_num_rec; i++ ) + { + p_rec_item = (osm_sir_item_t*)cl_qlist_remove_head( &rec_list ); + /* copy only if not trimmed */ + if (i < num_rec) + { + *p_resp_rec = p_rec_item->rec; + } + cl_qlock_pool_put( &p_rcv->pool, &p_rec_item->pool_item ); + p_resp_rec++; + } + + CL_ASSERT( cl_is_qlist_empty( &rec_list ) ); + + status = osm_vendor_send( p_resp_madw->h_bind, p_resp_madw, FALSE ); + if (status != IB_SUCCESS) + { + osm_log(p_rcv->p_log, OSM_LOG_ERROR, + "osm_sir_rcv_process: ERR 5307: " + "osm_vendor_send status = %s\n", + ib_get_err_str(status)); + goto Exit; + } + + Exit: + OSM_LOG_EXIT( p_rcv->p_log ); +} + diff --git a/trunk/ulp/opensm/user/opensm/osm_sa_sw_info_record_ctrl.c b/trunk/ulp/opensm/user/opensm/osm_sa_sw_info_record_ctrl.c new file mode 100644 index 00000000..726cd40a --- /dev/null +++ b/trunk/ulp/opensm/user/opensm/osm_sa_sw_info_record_ctrl.c @@ -0,0 +1,123 @@ +/* + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. + * + * This software is available to you under the OpenIB.org BSD license + * below: + * + * Redistribution and use in source and binary forms, with or + * without modification, are permitted provided that the following + * conditions are met: + * + * - Redistributions of source code must retain the above + * copyright notice, this list of conditions and the following + * disclaimer. + * + * - Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials + * provided with the distribution. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS + * BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN + * ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN + * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + * + * $Id$ + */ + + +/* + * Abstract: + * Implementation of osm_sir_rcv_ctrl_t. + * This object represents the SwitchInfo Record controller object. + * This object is part of the opensm family of objects. + * + * Environment: + * Linux User Mode + * + */ + +#if HAVE_CONFIG_H +# include +#endif /* HAVE_CONFIG_H */ + +#include +#include +#include + +/********************************************************************** + **********************************************************************/ +void +__osm_sir_ctrl_disp_callback( + IN void *context, + IN void *p_data ) +{ + /* ignore return status when invoked via the dispatcher */ + osm_sir_rcv_process( ((osm_sir_rcv_ctrl_t*)context)->p_rcv, + (osm_madw_t*)p_data ); +} + +/********************************************************************** + **********************************************************************/ +void +osm_sir_rcv_ctrl_construct( + IN osm_sir_rcv_ctrl_t* const p_ctrl ) +{ + memset( p_ctrl, 0, sizeof(*p_ctrl) ); + p_ctrl->h_disp = CL_DISP_INVALID_HANDLE; +} + +/********************************************************************** + **********************************************************************/ +void +osm_sir_rcv_ctrl_destroy( + IN osm_sir_rcv_ctrl_t* const p_ctrl ) +{ + CL_ASSERT( p_ctrl ); + cl_disp_unregister( p_ctrl->h_disp ); +} + +/********************************************************************** + **********************************************************************/ +ib_api_status_t +osm_sir_rcv_ctrl_init( + IN osm_sir_rcv_ctrl_t* const p_ctrl, + IN osm_sir_rcv_t* const p_rcv, + IN osm_log_t* const p_log, + IN cl_dispatcher_t* const p_disp ) +{ + ib_api_status_t status = IB_SUCCESS; + + OSM_LOG_ENTER( p_log, osm_sir_rcv_ctrl_init ); + + osm_sir_rcv_ctrl_construct( p_ctrl ); + p_ctrl->p_log = p_log; + p_ctrl->p_rcv = p_rcv; + p_ctrl->p_disp = p_disp; + + p_ctrl->h_disp = cl_disp_register( + p_disp, + OSM_MSG_MAD_SWITCH_INFO_RECORD, + __osm_sir_ctrl_disp_callback, + p_ctrl ); + + if( p_ctrl->h_disp == CL_DISP_INVALID_HANDLE ) + { + osm_log( p_log, OSM_LOG_ERROR, + "osm_sir_rcv_ctrl_init: ERR 5301: " + "Dispatcher registration failed\n" ); + status = IB_INSUFFICIENT_RESOURCES; + goto Exit; + } + + Exit: + OSM_LOG_EXIT( p_log ); + return( status ); +} + diff --git a/trunk/ulp/opensm/user/opensm/osm_sa_vlarb_record.c b/trunk/ulp/opensm/user/opensm/osm_sa_vlarb_record.c index f85b7c93..1bad3db6 100644 --- a/trunk/ulp/opensm/user/opensm/osm_sa_vlarb_record.c +++ b/trunk/ulp/opensm/user/opensm/osm_sa_vlarb_record.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -44,16 +44,12 @@ * $Revision: 1.7 $ */ -/* - Next available error code: 0x403 -*/ - #if HAVE_CONFIG_H # include #endif /* HAVE_CONFIG_H */ +#include #include -#include #include #include #include @@ -71,19 +67,17 @@ typedef struct _osm_vl_arb_item { cl_pool_item_t pool_item; - ib_vl_arb_table_record_t rec; - + ib_vl_arb_table_record_t rec; } osm_vl_arb_item_t; typedef struct _osm_vl_arb_search_ctxt { - const ib_vl_arb_table_record_t* p_rcvd_rec; + const ib_vl_arb_table_record_t* p_rcvd_rec; ib_net64_t comp_mask; uint8_t block_num; cl_qlist_t* p_list; - osm_vlarb_rec_rcv_t* p_rcv; + osm_vlarb_rec_rcv_t* p_rcv; const osm_physp_t* p_req_physp; - } osm_vl_arb_search_ctxt_t; /********************************************************************** @@ -92,7 +86,7 @@ void osm_vlarb_rec_rcv_construct( IN osm_vlarb_rec_rcv_t* const p_rcv ) { - cl_memclr( p_rcv, sizeof(*p_rcv) ); + memset( p_rcv, 0, sizeof(*p_rcv) ); cl_qlock_pool_construct( &p_rcv->pool ); } @@ -111,9 +105,9 @@ osm_vlarb_rec_rcv_destroy( **********************************************************************/ ib_api_status_t osm_vlarb_rec_rcv_init( - IN osm_vlarb_rec_rcv_t* const p_rcv, + IN osm_vlarb_rec_rcv_t* const p_rcv, IN osm_sa_resp_t* const p_resp, - IN osm_mad_pool_t* const p_mad_pool, + IN osm_mad_pool_t* const p_mad_pool, IN const osm_subn_t* const p_subn, IN osm_log_t* const p_log, IN cl_plock_t* const p_lock ) @@ -147,25 +141,16 @@ osm_vlarb_rec_rcv_init( void __osm_sa_vl_arb_create( IN osm_vlarb_rec_rcv_t* const p_rcv, - IN osm_physp_t* const p_physp, + IN osm_physp_t* const p_physp, IN osm_vl_arb_search_ctxt_t* const p_ctxt, - IN uint8_t block) + IN uint8_t block ) { - osm_vl_arb_item_t* p_rec_item; - uint16_t lid; - ib_api_status_t status = IB_SUCCESS; + osm_vl_arb_item_t* p_rec_item; + uint16_t lid; + ib_api_status_t status = IB_SUCCESS; OSM_LOG_ENTER( p_rcv->p_log, __osm_sa_vl_arb_create ); - if (p_physp->p_node->node_info.node_type != IB_NODE_TYPE_SWITCH) - { - lid = osm_physp_get_port_info_ptr( p_physp )->base_lid; - } - else - { - lid = osm_node_get_base_lid( p_physp->p_node, 0 ); - } - p_rec_item = (osm_vl_arb_item_t*)cl_qlock_pool_get( &p_rcv->pool ); if( p_rec_item == NULL ) { @@ -176,9 +161,18 @@ __osm_sa_vl_arb_create( goto Exit; } + if (p_physp->p_node->node_info.node_type != IB_NODE_TYPE_SWITCH) + { + lid = osm_physp_get_port_info_ptr( p_physp )->base_lid; + } + else + { + lid = osm_node_get_base_lid( p_physp->p_node, 0 ); + } + if( osm_log_is_active( p_rcv->p_log, OSM_LOG_DEBUG ) ) { - osm_log( p_rcv->p_log, OSM_LOG_ERROR, + osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "__osm_sa_vl_arb_create: " "New VLArbitration for: port 0x%016" PRIx64 ", lid 0x%X, port# 0x%X Block:%u\n", @@ -188,7 +182,7 @@ __osm_sa_vl_arb_create( ); } - cl_memclr( &p_rec_item->rec, sizeof( p_rec_item->rec ) ); + memset( &p_rec_item->rec, 0, sizeof( p_rec_item->rec ) ); p_rec_item->rec.lid = lid; p_rec_item->rec.port_num = osm_physp_get_port_num( p_physp ); @@ -205,16 +199,16 @@ __osm_sa_vl_arb_create( **********************************************************************/ void __osm_sa_vl_arb_check_physp( - IN osm_vlarb_rec_rcv_t* const p_rcv, - IN osm_physp_t* const p_physp, - osm_vl_arb_search_ctxt_t* const p_ctxt ) + IN osm_vlarb_rec_rcv_t* const p_rcv, + IN osm_physp_t* const p_physp, + osm_vl_arb_search_ctxt_t* const p_ctxt ) { - ib_net64_t comp_mask = p_ctxt->comp_mask; - uint8_t block; + ib_net64_t comp_mask = p_ctxt->comp_mask; + uint8_t block; OSM_LOG_ENTER( p_rcv->p_log, __osm_sa_vl_arb_check_physp ); - /* we got here with the phys port - all is left is to get thr right block */ + /* we got here with the phys port - all that's left is to get the right block */ for (block = 1; block <= 4; block++) { if (!(comp_mask & IB_VLA_COMPMASK_BLOCK) || block == p_ctxt->block_num) { @@ -222,7 +216,6 @@ __osm_sa_vl_arb_check_physp( } } - /* Exit: */ OSM_LOG_EXIT( p_rcv->p_log ); } @@ -230,16 +223,16 @@ __osm_sa_vl_arb_check_physp( **********************************************************************/ void __osm_sa_vl_arb_by_comp_mask( - IN osm_vlarb_rec_rcv_t* const p_rcv, + IN osm_vlarb_rec_rcv_t* const p_rcv, IN const osm_port_t* const p_port, osm_vl_arb_search_ctxt_t* const p_ctxt ) { const ib_vl_arb_table_record_t* p_rcvd_rec; - ib_net64_t comp_mask; - osm_physp_t * p_physp; - uint8_t port_num; - uint8_t num_ports; - const osm_physp_t* p_req_physp; + ib_net64_t comp_mask; + osm_physp_t * p_physp; + uint8_t port_num; + uint8_t num_ports; + const osm_physp_t* p_req_physp; OSM_LOG_ENTER( p_rcv->p_log, __osm_sa_vl_arb_by_comp_mask ); @@ -257,7 +250,7 @@ __osm_sa_vl_arb_by_comp_mask( osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "__osm_sa_vl_arb_by_comp_mask: " "Using Physical Default Port Number: 0x%X (for End Node)\n", - port_num); + port_num ); comp_mask |= IB_VLA_COMPMASK_OUT_PORT; } @@ -277,7 +270,7 @@ __osm_sa_vl_arb_by_comp_mask( osm_log( p_rcv->p_log, OSM_LOG_ERROR, "__osm_sa_vl_arb_by_comp_mask: ERR 2A03: " "Given Physical Port Number: 0x%X is out of range should be < 0x%X\n", - port_num, osm_port_get_num_physp( p_port )); + port_num, osm_port_get_num_physp( p_port ) ); goto Exit; } } @@ -309,11 +302,11 @@ __osm_sa_vl_arb_by_comp_mask( **********************************************************************/ void __osm_sa_vl_arb_by_comp_mask_cb( - IN cl_map_item_t* const p_map_item, - IN void* context ) + IN cl_map_item_t* const p_map_item, + IN void* context ) { - const osm_port_t* const p_port = (osm_port_t*)p_map_item; - osm_vl_arb_search_ctxt_t* const p_ctxt = (osm_vl_arb_search_ctxt_t *)context; + const osm_port_t* const p_port = (osm_port_t*)p_map_item; + osm_vl_arb_search_ctxt_t* const p_ctxt = (osm_vl_arb_search_ctxt_t *)context; __osm_sa_vl_arb_by_comp_mask( p_ctxt->p_rcv, p_port, p_ctxt ); } @@ -322,45 +315,33 @@ __osm_sa_vl_arb_by_comp_mask_cb( **********************************************************************/ void osm_vlarb_rec_rcv_process( - IN osm_vlarb_rec_rcv_t* const p_rcv, + IN osm_vlarb_rec_rcv_t* const p_rcv, IN const osm_madw_t* const p_madw ) { const ib_sa_mad_t* p_rcvd_mad; const ib_vl_arb_table_record_t* p_rcvd_rec; - const cl_ptr_vector_t* p_tbl; + const cl_ptr_vector_t* p_tbl; const osm_port_t* p_port = NULL; - const ib_vl_arb_table_t* p_vl_arb; + const ib_vl_arb_table_t* p_vl_arb; cl_qlist_t rec_list; osm_madw_t* p_resp_madw; - ib_sa_mad_t* p_resp_sa_mad; + ib_sa_mad_t* p_resp_sa_mad; ib_vl_arb_table_record_t* p_resp_rec; - uint32_t num_rec, pre_trim_num_rec; + uint32_t num_rec, pre_trim_num_rec; #ifndef VENDOR_RMPP_SUPPORT - uint32_t trim_num_rec; + uint32_t trim_num_rec; #endif - uint32_t i; - osm_vl_arb_search_ctxt_t context; - osm_vl_arb_item_t* p_rec_item; - ib_api_status_t status; - ib_net64_t comp_mask; - osm_physp_t* p_req_physp; + uint32_t i; + osm_vl_arb_search_ctxt_t context; + osm_vl_arb_item_t* p_rec_item; + ib_api_status_t status = IB_SUCCESS; + ib_net64_t comp_mask; + osm_physp_t* p_req_physp; CL_ASSERT( p_rcv ); OSM_LOG_ENTER( p_rcv->p_log, osm_vlarb_rec_rcv_process ); - /* update the requester physical port. */ - p_req_physp = osm_get_physp_by_mad_addr(p_rcv->p_log, - p_rcv->p_subn, - osm_madw_get_mad_addr_ptr(p_madw) ); - if (p_req_physp == NULL) - { - osm_log( p_rcv->p_log, OSM_LOG_ERROR, - "osm_vlarb_rec_rcv_process: ERR 2A04: " - "Cannot find requester physical port\n" ); - goto Exit; - } - CL_ASSERT( p_madw ); p_rcvd_mad = osm_madw_get_sa_mad_ptr( p_madw ); @@ -369,6 +350,7 @@ osm_vlarb_rec_rcv_process( CL_ASSERT( p_rcvd_mad->attr_id == IB_MAD_ATTR_VLARB_RECORD ); + /* we only support SubnAdmGet and SubnAdmGetTable methods */ if ( (p_rcvd_mad->method != IB_MAD_METHOD_GET) && (p_rcvd_mad->method != IB_MAD_METHOD_GETTABLE) ) { @@ -376,11 +358,22 @@ osm_vlarb_rec_rcv_process( "osm_vlarb_rec_rcv_process: ERR 2A05: " "Unsupported Method (%s)\n", ib_get_sa_method_str( p_rcvd_mad->method ) ); - osm_sa_send_error( p_rcv->p_resp, p_madw, IB_SA_MAD_STATUS_REQ_INVALID); + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_MAD_STATUS_UNSUP_METHOD_ATTR ); + goto Exit; + } + + /* update the requester physical port. */ + p_req_physp = osm_get_physp_by_mad_addr(p_rcv->p_log, + p_rcv->p_subn, + osm_madw_get_mad_addr_ptr(p_madw) ); + if (p_req_physp == NULL) + { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "osm_vlarb_rec_rcv_process: ERR 2A04: " + "Cannot find requester physical port\n" ); goto Exit; } - p_tbl = &p_rcv->p_subn->port_lid_tbl; p_vl_arb = (ib_vl_arb_table_t*)ib_sa_mad_get_payload_ptr( p_rcvd_mad ); cl_qlist_init( &rec_list ); @@ -394,10 +387,11 @@ osm_vlarb_rec_rcv_process( osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "osm_vlarb_rec_rcv_process: " - "Got Query Lid:0x%04X(%02X), Port:0x%02X(%02X), Block:0x%02X(%02X)\n", - cl_ntoh16(p_rcvd_rec->lid), (comp_mask &IB_VLA_COMPMASK_LID) != 0, - p_rcvd_rec->port_num, (comp_mask &IB_VLA_COMPMASK_OUT_PORT) != 0, - p_rcvd_rec->block_num, (comp_mask &IB_VLA_COMPMASK_BLOCK) != 0) ; + "Got Query Lid:0x%04X(%02X), Port:0x%02X(%02X), Block:0x%02X(%02X)\n", + cl_ntoh16(p_rcvd_rec->lid), (comp_mask & IB_VLA_COMPMASK_LID) != 0, + p_rcvd_rec->port_num, (comp_mask & IB_VLA_COMPMASK_OUT_PORT) != 0, + p_rcvd_rec->block_num, (comp_mask & IB_VLA_COMPMASK_BLOCK) != 0 ); + cl_plock_acquire( p_rcv->p_lock ); /* @@ -407,29 +401,33 @@ osm_vlarb_rec_rcv_process( if( comp_mask & IB_VLA_COMPMASK_LID ) { + p_tbl = &p_rcv->p_subn->port_lid_tbl; + CL_ASSERT( cl_ptr_vector_get_size(p_tbl) < 0x10000 ); - if ((uint16_t)cl_ptr_vector_get_size(p_tbl) > cl_ntoh16(p_rcvd_rec->lid)) + + status = osm_get_port_by_base_lid( p_rcv->p_subn, p_rcvd_rec->lid, &p_port ); + if ( ( status != IB_SUCCESS ) || ( p_port == NULL ) ) { - p_port = cl_ptr_vector_get( p_tbl, cl_ntoh16(p_rcvd_rec->lid) ); - } - else - { /* port out of range */ + status = IB_NOT_FOUND; osm_log( p_rcv->p_log, OSM_LOG_ERROR, - "osm_vlarb_rec_rcv_process: " - "Given LID (%u) is out of range:%u\n", - cl_ntoh16(p_rcvd_rec->lid), cl_ptr_vector_get_size(p_tbl)); + "osm_vlarb_rec_rcv_process: ERR 2A09: " + "No port found with LID 0x%x\n", + cl_ntoh16(p_rcvd_rec->lid) ); } } - /* if we got a unique port - no need for a port search */ - if( p_port ) - /* this does the loop on all the port phys ports */ - __osm_sa_vl_arb_by_comp_mask( p_rcv, p_port, &context ); - else + if ( status == IB_SUCCESS ) { - cl_qmap_apply_func( &p_rcv->p_subn->port_guid_tbl, - __osm_sa_vl_arb_by_comp_mask_cb, - &context ); + /* if we got a unique port - no need for a port search */ + if( p_port ) + /* this does the loop on all the port phys ports */ + __osm_sa_vl_arb_by_comp_mask( p_rcv, p_port, &context ); + else + { + cl_qmap_apply_func( &p_rcv->p_subn->port_guid_tbl, + __osm_sa_vl_arb_by_comp_mask_cb, + &context ); + } } cl_plock_release( p_rcv->p_lock ); @@ -440,24 +438,32 @@ osm_vlarb_rec_rcv_process( * C15-0.1.30: * If we do a SubnAdmGet and got more than one record it is an error ! */ - if ( (p_rcvd_mad->method == IB_MAD_METHOD_GET) && - (num_rec > 1)) { - osm_log( p_rcv->p_log, OSM_LOG_ERROR, - "osm_vlarb_rec_rcv_process: " - "Got more than one record for SubnAdmGet (%u)\n", - num_rec ); - osm_sa_send_error( p_rcv->p_resp, p_madw, - IB_SA_MAD_STATUS_TOO_MANY_RECORDS); - - /* need to set the mem free ... */ - p_rec_item = (osm_vl_arb_item_t*)cl_qlist_remove_head( &rec_list ); - while( p_rec_item != (osm_vl_arb_item_t*)cl_qlist_end( &rec_list ) ) + if (p_rcvd_mad->method == IB_MAD_METHOD_GET) + { + if (num_rec == 0) { - cl_qlock_pool_put( &p_rcv->pool, &p_rec_item->pool_item ); - p_rec_item = (osm_vl_arb_item_t*)cl_qlist_remove_head( &rec_list ); + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_SA_MAD_STATUS_NO_RECORDS ); + goto Exit; } + if (num_rec > 1) + { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "osm_vlarb_rec_rcv_process: ERR 2A08: " + "Got more than one record for SubnAdmGet (%u)\n", + num_rec ); + osm_sa_send_error( p_rcv->p_resp, p_madw, + IB_SA_MAD_STATUS_TOO_MANY_RECORDS ); - goto Exit; + /* need to set the mem free ... */ + p_rec_item = (osm_vl_arb_item_t*)cl_qlist_remove_head( &rec_list ); + while( p_rec_item != (osm_vl_arb_item_t*)cl_qlist_end( &rec_list ) ) + { + cl_qlock_pool_put( &p_rcv->pool, &p_rec_item->pool_item ); + p_rec_item = (osm_vl_arb_item_t*)cl_qlist_remove_head( &rec_list ); + } + + goto Exit; + } } pre_trim_num_rec = num_rec; @@ -479,8 +485,7 @@ osm_vlarb_rec_rcv_process( if ((p_rcvd_mad->method == IB_MAD_METHOD_GET) && (num_rec == 0)) { - osm_sa_send_error( p_rcv->p_resp, p_madw, - IB_SA_MAD_STATUS_NO_RECORDS ); + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_SA_MAD_STATUS_NO_RECORDS ); goto Exit; } @@ -494,9 +499,9 @@ osm_vlarb_rec_rcv_process( if( !p_resp_madw ) { - osm_log(p_rcv->p_log, OSM_LOG_ERROR, - "osm_vlarb_rec_rcv_process: ERR 2A06: " - "osm_mad_pool_get failed\n" ); + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "osm_vlarb_rec_rcv_process: ERR 2A06: " + "osm_mad_pool_get failed\n" ); for( i = 0; i < num_rec; i++ ) { @@ -504,9 +509,7 @@ osm_vlarb_rec_rcv_process( cl_qlock_pool_put( &p_rcv->pool, &p_rec_item->pool_item ); } - osm_sa_send_error( p_rcv->p_resp, p_madw, - IB_SA_MAD_STATUS_NO_RESOURCES ); - + osm_sa_send_error( p_rcv->p_resp, p_madw, IB_SA_MAD_STATUS_NO_RESOURCES ); goto Exit; } @@ -518,9 +521,9 @@ osm_vlarb_rec_rcv_process( Then copy all records from the list into the response payload. */ - cl_memcpy( p_resp_sa_mad, p_rcvd_mad, IB_SA_MAD_HDR_SIZE ); - p_resp_sa_mad->method = (uint8_t)(p_resp_sa_mad->method | 0x80); - /* C15-0.1.5 - always return SM_Key = 0 (table 151 p 782) */ + memcpy( p_resp_sa_mad, p_rcvd_mad, IB_SA_MAD_HDR_SIZE ); + p_resp_sa_mad->method |= IB_MAD_METHOD_RESP_MASK; + /* C15-0.1.5 - always return SM_Key = 0 (table 185 p 884) */ p_resp_sa_mad->sm_key = 0; /* Fill in the offset (paylen will be done by the rmpp SAR) */ @@ -558,16 +561,17 @@ osm_vlarb_rec_rcv_process( CL_ASSERT( cl_is_qlist_empty( &rec_list ) ); - status = osm_vendor_send( p_resp_madw->h_bind, p_resp_madw, FALSE); + status = osm_vendor_send( p_resp_madw->h_bind, p_resp_madw, FALSE ); if(status != IB_SUCCESS) { - osm_log(p_rcv->p_log, OSM_LOG_ERROR, - "osm_vlarb_rec_rcv_process: ERR 2A07: " - "osm_vendor_send. status = %s\n", - ib_get_err_str(status)); + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "osm_vlarb_rec_rcv_process: ERR 2A07: " + "osm_vendor_send status = %s\n", + ib_get_err_str(status) ); goto Exit; } Exit: OSM_LOG_EXIT( p_rcv->p_log ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_sa_vlarb_record_ctrl.c b/trunk/ulp/opensm/user/opensm/osm_sa_vlarb_record_ctrl.c index 0b219168..94a607a8 100644 --- a/trunk/ulp/opensm/user/opensm/osm_sa_vlarb_record_ctrl.c +++ b/trunk/ulp/opensm/user/opensm/osm_sa_vlarb_record_ctrl.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Implementation of osm_vlarb_rec_rcv_ctrl_t. @@ -44,15 +45,11 @@ * $Revision: 1.4 $ */ -/* - Next available error code: 0x203 -*/ - #if HAVE_CONFIG_H # include #endif /* HAVE_CONFIG_H */ -#include +#include #include #include @@ -74,7 +71,7 @@ void osm_vlarb_rec_rcv_ctrl_construct( IN osm_vlarb_rec_rcv_ctrl_t* const p_ctrl ) { - cl_memclr( p_ctrl, sizeof(*p_ctrl) ); + memset( p_ctrl, 0, sizeof(*p_ctrl) ); p_ctrl->h_disp = CL_DISP_INVALID_HANDLE; } @@ -126,3 +123,4 @@ osm_vlarb_rec_rcv_ctrl_init( return( status ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_service.c b/trunk/ulp/opensm/user/opensm/osm_service.c index e819dae0..2f236b3c 100644 --- a/trunk/ulp/opensm/user/opensm/osm_service.c +++ b/trunk/ulp/opensm/user/opensm/osm_service.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Implementation of service record functions. @@ -46,8 +47,8 @@ # include #endif /* HAVE_CONFIG_H */ +#include #include -#include #include #include @@ -57,7 +58,7 @@ void osm_svcr_construct( IN osm_svcr_t* const p_svcr ) { - cl_memclr( p_svcr, sizeof(*p_svcr) ); + memset( p_svcr, 0, sizeof(*p_svcr) ); } /********************************************************************** @@ -66,7 +67,7 @@ void osm_svcr_destroy( IN osm_svcr_t* const p_svcr ) { - cl_free( p_svcr); + free( p_svcr); } /********************************************************************** @@ -79,7 +80,6 @@ osm_svcr_init( CL_ASSERT( p_svcr ); p_svcr->modified_time = cl_get_time_stamp_sec(); - /* p_svcr->svc_id = p_svc_rec->service_id; */ /* We track the time left for this service in an external field to avoid extra cl_ntoh/hton @@ -98,7 +98,7 @@ osm_svcr_new( CL_ASSERT(p_svc_rec); - p_svcr = (osm_svcr_t*)cl_malloc( sizeof(*p_svcr) ); + p_svcr = (osm_svcr_t*)malloc( sizeof(*p_svcr) ); if( p_svcr ) { osm_svcr_construct( p_svcr ); @@ -121,7 +121,7 @@ __match_rid_of_svc_rec( osm_svcr_t* p_svcr = (osm_svcr_t*)p_list_item; int32_t count; - count = cl_memcmp( + count = memcmp( &p_svcr->service_record, p_svc_rec, sizeof(p_svc_rec->service_id) + @@ -171,7 +171,7 @@ osm_svcr_insert_to_db( osm_log( p_log, OSM_LOG_DEBUG, "osm_svcr_insert_to_db: " - "Inserting a new Service Record into Database\n"); + "Inserting new Service Record into Database\n"); cl_qlist_insert_head(&p_subn->sa_sr_list, &p_svcr->list_item); @@ -199,3 +199,4 @@ osm_svcr_remove_from_db( OSM_LOG_EXIT( p_log ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_slvl_map_rcv.c b/trunk/ulp/opensm/user/opensm/osm_slvl_map_rcv.c index 08fa1d80..7b5623fb 100644 --- a/trunk/ulp/opensm/user/opensm/osm_slvl_map_rcv.c +++ b/trunk/ulp/opensm/user/opensm/osm_slvl_map_rcv.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Implementation of osm_slvl_rcv_t. @@ -48,8 +49,8 @@ # include #endif /* HAVE_CONFIG_H */ +#include #include -#include #include #include #include @@ -71,7 +72,7 @@ void osm_slvl_rcv_construct( IN osm_slvl_rcv_t* const p_rcv ) { - cl_memclr( p_rcv, sizeof(*p_rcv) ); + memset( p_rcv, 0, sizeof(*p_rcv) ); } /********************************************************************** @@ -157,9 +158,9 @@ osm_slvl_rcv_process( cl_plock_release( p_rcv->p_lock ); osm_log( p_rcv->p_log, OSM_LOG_ERROR, "osm_slvl_rcv_process: ERR 2C06: " - "No Port object for port with GUID = 0x%" PRIx64 - "\n\t\t\t\tfor parent node GUID = 0x%" PRIx64 - ", TID = 0x%" PRIx64 "\n", + "No port object for port with GUID 0x%" PRIx64 + "\n\t\t\t\tfor parent node GUID 0x%" PRIx64 + ", TID 0x%" PRIx64 "\n", cl_ntoh64( port_guid ), cl_ntoh64( node_guid ), cl_ntoh64( p_smp->trans_id ) ); @@ -170,7 +171,7 @@ osm_slvl_rcv_process( CL_ASSERT( p_node ); /* in case of a non switch node the attr modifier should be ignored */ - if (osm_node_get_type( p_node ) == IB_NODE_TYPE_SWITCH) + if (osm_node_get_type( p_node ) == IB_NODE_TYPE_SWITCH) { out_port_num = (uint8_t)cl_ntoh32( p_smp->attr_mod & 0xFF000000); in_port_num = (uint8_t)cl_ntoh32( (p_smp->attr_mod & 0x00FF0000) << 8); @@ -193,9 +194,9 @@ osm_slvl_rcv_process( { osm_log( p_rcv->p_log, OSM_LOG_VERBOSE, "osm_slvl_rcv_process: " - "Got SLtoVL get response in_port_num %u out_port_num %u with GUID = 0x%" PRIx64 - " for parent node GUID = 0x%" PRIx64 - ", TID = 0x%" PRIx64 "\n", + "Got SLtoVL get response in_port_num %u out_port_num %u with GUID 0x%" PRIx64 + " for parent node GUID 0x%" PRIx64 + ", TID 0x%" PRIx64 "\n", in_port_num, out_port_num, cl_ntoh64( port_guid ), cl_ntoh64( node_guid ), @@ -208,13 +209,10 @@ osm_slvl_rcv_process( */ if( !osm_physp_is_valid( p_physp ) ) { - if( osm_log_is_active( p_rcv->p_log, OSM_LOG_VERBOSE ) ) - { - osm_log( p_rcv->p_log, OSM_LOG_ERROR, - "osm_slvl_rcv_process: " - "Got invalid port number 0x%X\n", - out_port_num ); - } + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "osm_slvl_rcv_process: " + "Got invalid port number 0x%X\n", + out_port_num ); goto Exit; } @@ -231,3 +229,4 @@ osm_slvl_rcv_process( OSM_LOG_EXIT( p_rcv->p_log ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_slvl_map_rcv_ctrl.c b/trunk/ulp/opensm/user/opensm/osm_slvl_map_rcv_ctrl.c index ad6e3f6d..cb96cbe0 100644 --- a/trunk/ulp/opensm/user/opensm/osm_slvl_map_rcv_ctrl.c +++ b/trunk/ulp/opensm/user/opensm/osm_slvl_map_rcv_ctrl.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Implementation of osm_slvl_rcv_ctrl_t. @@ -44,15 +45,11 @@ * $Revision: 1.4 $ */ -/* - Next available error code: 0x203 -*/ - #if HAVE_CONFIG_H # include #endif /* HAVE_CONFIG_H */ -#include +#include #include #include @@ -74,7 +71,7 @@ void osm_slvl_rcv_ctrl_construct( IN osm_slvl_rcv_ctrl_t* const p_ctrl ) { - cl_memclr( p_ctrl, sizeof(*p_ctrl) ); + memset( p_ctrl, 0, sizeof(*p_ctrl) ); p_ctrl->h_disp = CL_DISP_INVALID_HANDLE; } @@ -127,3 +124,4 @@ osm_slvl_rcv_ctrl_init( return( status ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_sm.c b/trunk/ulp/opensm/user/opensm/osm_sm.c index 3d357e55..ea8352eb 100644 --- a/trunk/ulp/opensm/user/opensm/osm_sm.c +++ b/trunk/ulp/opensm/user/opensm/osm_sm.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -44,15 +44,12 @@ * $Revision: 1.9 $ */ -/* - Next available error code: 0x403 -*/ - #if HAVE_CONFIG_H # include #endif /* HAVE_CONFIG_H */ -#include +#include +#include #include #include #include @@ -63,7 +60,6 @@ #include #include #include -#include #include #include #include @@ -98,7 +94,7 @@ __osm_sm_sweeper( /* * Wait on the event with a timeout. - * Sweeps may be iniated "off schedule" by simply + * Sweeps may be initiated "off schedule" by simply * signaling the event. */ status = cl_event_wait_on( &p_sm->signal, @@ -133,7 +129,7 @@ void osm_sm_construct( IN osm_sm_t * const p_sm ) { - cl_memclr( p_sm, sizeof( *p_sm ) ); + memset( p_sm, 0, sizeof( *p_sm ) ); p_sm->thread_state = OSM_THREAD_STATE_NONE; p_sm->sm_trans_id = OSM_SM_INITIAL_TID_VALUE; cl_event_construct( &p_sm->signal ); @@ -157,7 +153,6 @@ osm_sm_construct( osm_state_mgr_construct( &p_sm->state_mgr ); osm_state_mgr_ctrl_construct( &p_sm->state_mgr_ctrl ); osm_drop_mgr_construct( &p_sm->drop_mgr ); - osm_pkey_mgr_construct( &p_sm->pkey_mgr ); osm_lft_rcv_construct( &p_sm->lft_rcv ); osm_lft_rcv_ctrl_construct( &p_sm->lft_rcv_ctrl ); osm_mft_rcv_construct( &p_sm->mft_rcv ); @@ -247,7 +242,6 @@ osm_sm_destroy( osm_ucast_mgr_destroy( &p_sm->ucast_mgr ); osm_link_mgr_destroy( &p_sm->link_mgr ); osm_drop_mgr_destroy( &p_sm->drop_mgr ); - osm_pkey_mgr_destroy( &p_sm->pkey_mgr ); osm_lft_rcv_destroy( &p_sm->lft_rcv ); osm_mft_rcv_destroy( &p_sm->mft_rcv ); osm_slvl_rcv_destroy( &p_sm->slvl_rcv ); @@ -259,9 +253,6 @@ osm_sm_destroy( cl_event_destroy( &p_sm->signal ); cl_event_destroy( &p_sm->subnet_up_event ); - if( p_sm->p_report_buf != NULL ) - cl_free( p_sm->p_report_buf ); - osm_log( p_sm->p_log, OSM_LOG_SYS, "Exiting SM\n" ); /* Format Waived */ OSM_LOG_EXIT( p_sm->p_log ); } @@ -294,14 +285,6 @@ osm_sm_init( p_sm->p_disp = p_disp; p_sm->p_lock = p_lock; - p_sm->p_report_buf = cl_malloc( OSM_REPORT_BUF_SIZE ); - if( p_sm->p_report_buf == NULL ) - { - osm_log( p_sm->p_log, OSM_LOG_ERROR, - "osm_sm_init: ERR 2E09: " "Can't allocate report buffer\n" ); - status = IB_INSUFFICIENT_MEMORY; - goto Exit; - } status = cl_event_init( &p_sm->signal, FALSE ); if( status != CL_SUCCESS ) goto Exit; @@ -387,7 +370,6 @@ osm_sm_init( status = osm_ucast_mgr_init( &p_sm->ucast_mgr, &p_sm->req, p_sm->p_subn, - p_sm->p_report_buf, p_sm->p_log, p_sm->p_lock ); if( status != IB_SUCCESS ) goto Exit; @@ -405,14 +387,13 @@ osm_sm_init( &p_sm->mcast_mgr, &p_sm->link_mgr, &p_sm->drop_mgr, - &p_sm->pkey_mgr, &p_sm->req, p_stats, &p_sm->sm_state_mgr, &p_sm->mad_ctrl, p_sm->p_lock, &p_sm->subnet_up_event, - p_sm->p_report_buf, p_sm->p_log ); + p_sm->p_log ); if( status != IB_SUCCESS ) goto Exit; @@ -428,12 +409,6 @@ osm_sm_init( if( status != IB_SUCCESS ) goto Exit; - status = osm_pkey_mgr_init( &p_sm->pkey_mgr, - p_sm->p_subn, - p_sm->p_log, &p_sm->req, p_sm->p_lock ); - if( status != IB_SUCCESS ) - goto Exit; - status = osm_lft_rcv_init( &p_sm->lft_rcv, p_subn, p_log, p_lock ); if( status != IB_SUCCESS ) goto Exit; @@ -526,7 +501,6 @@ osm_sm_init( if( status != IB_SUCCESS ) goto Exit; - /* * Now that the component objects are initialized, start * the sweeper thread if the user wants sweeping. @@ -602,8 +576,8 @@ __osm_sm_mgrp_connect( * isn't busy trying to do something else. */ ctx2 = - ( osm_mcast_mgr_ctxt_t * ) cl_malloc( sizeof( osm_mcast_mgr_ctxt_t ) ); - cl_memcpy( &ctx2->mlid, &p_mgrp->mlid, sizeof( p_mgrp->mlid ) ); + ( osm_mcast_mgr_ctxt_t * ) malloc( sizeof( osm_mcast_mgr_ctxt_t ) ); + memcpy( &ctx2->mlid, &p_mgrp->mlid, sizeof( p_mgrp->mlid ) ); ctx2->req_type = req_type; ctx2->port_guid = port_guid; @@ -612,7 +586,6 @@ __osm_sm_mgrp_connect( NULL, &p_sm->mcast_mgr, ( void * )ctx2 ); - /* Exit: */ OSM_LOG_EXIT( p_sm->p_log ); return ( status ); } @@ -635,8 +608,8 @@ __osm_sm_mgrp_disconnect( * isn't busy trying to do something else. */ ctx2 = - ( osm_mcast_mgr_ctxt_t * ) cl_malloc( sizeof( osm_mcast_mgr_ctxt_t ) ); - cl_memcpy( &ctx2->mlid, &p_mgrp->mlid, sizeof( p_mgrp->mlid ) ); + ( osm_mcast_mgr_ctxt_t * ) malloc( sizeof( osm_mcast_mgr_ctxt_t ) ); + memcpy( &ctx2->mlid, &p_mgrp->mlid, sizeof( p_mgrp->mlid ) ); ctx2->req_type = OSM_MCAST_REQ_TYPE_LEAVE; ctx2->port_guid = port_guid; @@ -733,6 +706,7 @@ osm_sm_mcgrp_join( "osm_sm_mcgrp_join: ERR 2E12: " "Port 0x%016" PRIx64 " not in mcast group 0x%X\n", cl_ntoh64( port_guid ), cl_ntoh16( mlid ) ); + status = IB_NOT_FOUND; goto Exit; } } @@ -761,7 +735,7 @@ osm_sm_mcgrp_join( status = osm_port_add_mgrp( p_port, mlid ); if( status != IB_SUCCESS ) { - cl_plock_release( p_sm->p_lock ); + CL_PLOCK_RELEASE( p_sm->p_lock ); osm_log( p_sm->p_log, OSM_LOG_ERROR, "osm_sm_mcgrp_join: ERR 2E03: " "Unable to associate port 0x%" PRIx64 " to mlid 0x%X\n", @@ -801,7 +775,8 @@ osm_sm_mcgrp_leave( /* * Acquire the port object for the port leaving this group. */ - CL_PLOCK_EXCL_ACQUIRE( p_sm->p_lock ); + /* note: p_sm->p_lock is locked by caller, but will be released later + this function */ p_port = ( osm_port_t * ) cl_qmap_get( &p_sm->p_subn->port_guid_tbl, port_guid ); if( p_port == @@ -846,3 +821,4 @@ osm_sm_mcgrp_leave( OSM_LOG_EXIT( p_sm->p_log ); return ( status ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_sm_mad_ctrl.c b/trunk/ulp/opensm/user/opensm/osm_sm_mad_ctrl.c index 29d3354b..a79e50b7 100644 --- a/trunk/ulp/opensm/user/opensm/osm_sm_mad_ctrl.c +++ b/trunk/ulp/opensm/user/opensm/osm_sm_mad_ctrl.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -44,15 +44,11 @@ * $Revision: 1.7 $ */ -/* - Next available error code: 0x203 -*/ - #if HAVE_CONFIG_H # include #endif /* HAVE_CONFIG_H */ -#include +#include #include #include #include @@ -90,7 +86,7 @@ __osm_sm_mad_ctrl_retire_trans_mad( { osm_log( p_ctrl->p_log, OSM_LOG_DEBUG, "__osm_sm_mad_ctrl_retire_trans_mad: " - "Retiring MAD with TID = 0x%" PRIx64 "\n", + "Retiring MAD with TID 0x%" PRIx64 "\n", cl_ntoh64( osm_madw_get_smp_ptr( p_madw )->trans_id ) ); } @@ -254,12 +250,15 @@ __osm_sm_mad_ctrl_process_get_resp( p_smp = osm_madw_get_smp_ptr( p_madw ); - if( !ib_smp_is_d( p_smp ) ) + if( p_smp->mgmt_class == IB_MCLASS_SUBN_DIR ) { - osm_log( p_ctrl->p_log, OSM_LOG_ERROR, - "__osm_sm_mad_ctrl_process_get_resp: ERR 3102: " - "'D' bit not set in returned SMP\n" ); - osm_dump_dr_smp( p_ctrl->p_log, p_smp, OSM_LOG_ERROR ); + if( !ib_smp_is_d( p_smp ) ) + { + osm_log( p_ctrl->p_log, OSM_LOG_ERROR, + "__osm_sm_mad_ctrl_process_get_resp: ERR 3102: " + "'D' bit not set in returned SMP\n" ); + osm_dump_dr_smp( p_ctrl->p_log, p_smp, OSM_LOG_ERROR ); + } } p_old_madw = (osm_madw_t*)transaction_context; @@ -357,13 +356,6 @@ __osm_sm_mad_ctrl_process_get_resp( goto Exit; } } - else - { - /* - We received a response for which there is no recipient!! - */ - CL_ASSERT( FALSE ); - } Exit: OSM_LOG_EXIT( p_ctrl->p_log ); @@ -406,6 +398,7 @@ __osm_sm_mad_ctrl_process_get( "__osm_sm_mad_ctrl_process_get: " "Ignoring SubnGet MAD - unsupported attribute = 0x%X\n", cl_ntoh16( p_smp->attr_id ) ); + break; } if( msg_id != CL_DISP_MSGID_NONE ) @@ -441,7 +434,7 @@ __osm_sm_mad_ctrl_process_get( else { /* - There is a known MAD attribute type for which there is + There is an unknown MAD attribute type for which there is no recipient. Simply retire the MAD here. */ osm_mad_pool_put( p_ctrl->p_mad_pool, p_madw ); @@ -450,7 +443,6 @@ __osm_sm_mad_ctrl_process_get( Exit: OSM_LOG_EXIT( p_ctrl->p_log ); } - /* * PARAMETERS * @@ -499,7 +491,7 @@ __osm_sm_mad_ctrl_process_set( "Unsupported attribute = 0x%X\n", cl_ntoh16( p_smp->attr_id ) ); osm_dump_dr_smp( p_ctrl->p_log, p_smp, OSM_LOG_ERROR ); - + break; } if( msg_id != CL_DISP_MSGID_NONE ) @@ -535,7 +527,7 @@ __osm_sm_mad_ctrl_process_set( else { /* - There is a known MAD attribute type for which there is + There is an unknown MAD attribute type for which there is no recipient. Simply retire the MAD here. */ osm_mad_pool_put( p_ctrl->p_mad_pool, p_madw ); @@ -544,7 +536,6 @@ __osm_sm_mad_ctrl_process_set( Exit: OSM_LOG_EXIT( p_ctrl->p_log ); } - /* * PARAMETERS * @@ -604,7 +595,7 @@ __osm_sm_mad_ctrl_process_trap( "Unsupported attribute = 0x%X\n", cl_ntoh16( p_smp->attr_id ) ); osm_dump_dr_smp( p_ctrl->p_log, p_smp, OSM_LOG_ERROR ); - + break; } if( msg_id != CL_DISP_MSGID_NONE ) @@ -640,7 +631,7 @@ __osm_sm_mad_ctrl_process_trap( else { /* - There is a known MAD attribute type for which there is + There is an unknown MAD attribute type for which there is no recipient. Simply retire the MAD here. */ osm_mad_pool_put( p_ctrl->p_mad_pool, p_madw ); @@ -649,7 +640,6 @@ __osm_sm_mad_ctrl_process_trap( Exit: OSM_LOG_EXIT( p_ctrl->p_log ); } - /* * PARAMETERS * @@ -677,6 +667,7 @@ __osm_sm_mad_ctrl_rcv_callback( { osm_sm_mad_ctrl_t* p_ctrl = (osm_sm_mad_ctrl_t*)bind_context; ib_smp_t* p_smp; + ib_net16_t status; OSM_LOG_ENTER( p_ctrl->p_log, __osm_sm_mad_ctrl_rcv_callback ); @@ -727,11 +718,20 @@ __osm_sm_mad_ctrl_rcv_callback( if( osm_log_is_active( p_ctrl->p_log, OSM_LOG_FRAMES ) ) osm_dump_dr_smp( p_ctrl->p_log, p_smp, OSM_LOG_FRAMES ); - if( ib_smp_get_status( p_smp ) != 0 ) + if( p_smp->mgmt_class == IB_MCLASS_SUBN_DIR ) + { + status = ib_smp_get_status( p_smp ); + } + else + { + status = p_smp->status; + } + + if( status != 0 ) { osm_log( p_ctrl->p_log, OSM_LOG_ERROR, "__osm_sm_mad_ctrl_rcv_callback: ERR 3111: " - "Error status = 0x%X\n", ib_smp_get_status( p_smp ) ); + "Error status = 0x%X\n", status ); osm_dump_dr_smp( p_ctrl->p_log, p_smp, OSM_LOG_ERROR ); } @@ -739,8 +739,7 @@ __osm_sm_mad_ctrl_rcv_callback( { case IB_MAD_METHOD_GET_RESP: CL_ASSERT( p_req_madw != NULL ); - __osm_sm_mad_ctrl_process_get_resp( p_ctrl, - p_madw, p_req_madw ); + __osm_sm_mad_ctrl_process_get_resp( p_ctrl, p_madw, p_req_madw ); break; case IB_MAD_METHOD_GET: @@ -800,7 +799,9 @@ __osm_sm_mad_ctrl_send_err_cb( IN osm_madw_t *p_madw ) { osm_sm_mad_ctrl_t* p_ctrl = (osm_sm_mad_ctrl_t*)bind_context; +#if 0 osm_physp_t* p_physp; +#endif ib_api_status_t status; ib_smp_t* p_smp; @@ -841,25 +842,26 @@ __osm_sm_mad_ctrl_send_err_cb( lid. */ /* For now - do not add the alternate dr path to the release */ - if (0) - if ( p_madw->mad_addr.dest_lid != 0xFFFF ) +#if 0 + if ( p_madw->mad_addr.dest_lid != 0xFFFF ) + { + p_physp = + osm_get_physp_by_mad_addr(p_ctrl->p_log, + p_ctrl->p_subn, + &(p_madw->mad_addr)); + if (!p_physp) { - p_physp = - osm_get_physp_by_mad_addr(p_ctrl->p_log, - p_ctrl->p_subn, - &(p_madw->mad_addr)); - if (! p_physp) - { - osm_log( p_ctrl->p_log, OSM_LOG_ERROR, - "__osm_sm_mad_ctrl_send_err_cb: ERR 3114: " - "Failed to find the corresponding phys port\n"); - } - else - { - osm_physp_replace_dr_path_with_alternate_dr_path( - p_ctrl->p_log, p_ctrl->p_subn, p_physp, p_madw->h_bind ); - } + osm_log( p_ctrl->p_log, OSM_LOG_ERROR, + "__osm_sm_mad_ctrl_send_err_cb: ERR 3114: " + "Failed to find the corresponding phys port\n"); } + else + { + osm_physp_replace_dr_path_with_alternate_dr_path( + p_ctrl->p_log, p_ctrl->p_subn, p_physp, p_madw->h_bind ); + } + } +#endif /* An error occurred. No response was received to a request MAD. @@ -921,7 +923,7 @@ osm_sm_mad_ctrl_construct( IN osm_sm_mad_ctrl_t* const p_ctrl ) { CL_ASSERT( p_ctrl ); - cl_memclr( p_ctrl, sizeof(*p_ctrl) ); + memset( p_ctrl, 0, sizeof(*p_ctrl) ); p_ctrl->h_disp = CL_DISP_INVALID_HANDLE; } diff --git a/trunk/ulp/opensm/user/opensm/osm_sm_state_mgr.c b/trunk/ulp/opensm/user/opensm/osm_sm_state_mgr.c index 6791bf3f..cf37caae 100644 --- a/trunk/ulp/opensm/user/opensm/osm_sm_state_mgr.c +++ b/trunk/ulp/opensm/user/opensm/osm_sm_state_mgr.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,10 +32,11 @@ */ + /* * Abstract: * Implementation of osm_state_mgr_t. - * This file implements the Discovery Done Manager object. + * This file implements the SM State Manager object. * * Environment: * Linux User Mode @@ -47,8 +48,8 @@ # include #endif /* HAVE_CONFIG_H */ +#include #include -#include #include #include #include @@ -146,9 +147,10 @@ __osm_sm_state_mgr_notactive_msg( } } +#if 0 /********************************************************************** **********************************************************************/ -void +static void __osm_sm_state_mgr_send_local_port_info_req( IN osm_sm_state_mgr_t * p_sm_mgr ) { @@ -163,7 +165,7 @@ __osm_sm_state_mgr_send_local_port_info_req( * Send a query of SubnGet(PortInfo) to our own port, in order to * update the master_sm_base_lid of the subnet. */ - cl_memclr( &context, sizeof( context ) ); + memset( &context, 0, sizeof( context ) ); p_port = ( osm_port_t * ) cl_qmap_get( &p_sm_mgr->p_subn->port_guid_tbl, port_guid ); if( p_port == @@ -180,10 +182,11 @@ __osm_sm_state_mgr_send_local_port_info_req( context.pi_context.node_guid = p_port->p_node->node_info.node_guid; context.pi_context.set_method = FALSE; context.pi_context.ignore_errors = FALSE; - /* mark the update_master_sm_base_lid with TRUE - we want to update it */ - /* with the new master lid value. */ + /* mark the update_master_sm_base_lid with TRUE - we want to update it */ + /* with the new master lid value. */ context.pi_context.update_master_sm_base_lid = TRUE; context.pi_context.light_sweep = FALSE; + context.pi_context.active_transition = FALSE; status = osm_req_get( p_sm_mgr->p_req, osm_physp_get_dr_path_ptr @@ -203,10 +206,11 @@ __osm_sm_state_mgr_send_local_port_info_req( Exit: OSM_LOG_EXIT( p_sm_mgr->p_log ); } +#endif /********************************************************************** **********************************************************************/ -void +static void __osm_sm_state_mgr_send_master_sm_info_req( IN osm_sm_state_mgr_t * p_sm_mgr ) { @@ -217,7 +221,7 @@ __osm_sm_state_mgr_send_master_sm_info_req( OSM_LOG_ENTER( p_sm_mgr->p_log, __osm_sm_state_mgr_send_master_sm_info_req ); - cl_memclr( &context, sizeof( context ) ); + memset( &context, 0, sizeof( context ) ); if( p_sm_mgr->p_subn->sm_state == IB_SMINFO_STATE_STANDBY ) { /* @@ -241,7 +245,8 @@ __osm_sm_state_mgr_send_master_sm_info_req( { osm_log( p_sm_mgr->p_log, OSM_LOG_ERROR, "__osm_sm_state_mgr_send_master_sm_info_req: ERR 3203: " - "No port object for guid 0x%X\n", p_sm_mgr->master_guid ); + "No port object for GUID 0x%016" PRIx64 "\n", + cl_ntoh64(p_sm_mgr->master_guid) ); goto Exit; } @@ -267,7 +272,7 @@ __osm_sm_state_mgr_send_master_sm_info_req( /********************************************************************** **********************************************************************/ -void +static void __osm_sm_state_mgr_start_polling( IN osm_sm_state_mgr_t * p_sm_mgr ) { @@ -283,13 +288,13 @@ __osm_sm_state_mgr_start_polling( p_sm_mgr->retry_number = 0; /* - * Send a SubnGet(SMInfo) query to the found current (or new) master. + * Send a SubnGet(SMInfo) query to the current (or new) master found. */ __osm_sm_state_mgr_send_master_sm_info_req( p_sm_mgr ); /* * Start a timer that will wake up every sminfo_polling_timeout milliseconds. - * The callback of the timer will send a SubnGet(SMInfo) to the Master SM, + * The callback of the timer will send a SubnGet(SMInfo) to the Master SM * and restart the timer */ cl_status = cl_timer_start( &p_sm_mgr->polling_timer, @@ -306,7 +311,7 @@ __osm_sm_state_mgr_start_polling( /********************************************************************** **********************************************************************/ -void +static void __osm_sm_state_mgr_polling_callback( IN void *context ) { @@ -331,11 +336,11 @@ __osm_sm_state_mgr_polling_callback( } /* - * If we are a STANDBY sm, and the osm_exit_flag is 1, then let's signal - * the subnet_up. This is relevant for the case of running only once. It that - * case - the program is stuck until this signal is received. In other cases - - * it is not relevant whether or not the signal is on - since we are currently - * in exit flow + * If we are a STANDBY sm and the osm_exit_flag is 1, then let's signal + * the subnet_up. This is relevant for the case of running only once. In that + * case - the program is stuck until this signal is received. In other + * cases - it is not relevant whether or not the signal is on - since we are + * currently in exit flow */ if( p_sm_mgr->p_subn->sm_state == IB_SMINFO_STATE_STANDBY && osm_exit_flag == 1 ) @@ -385,14 +390,13 @@ __osm_sm_state_mgr_polling_callback( return; } - /********************************************************************** **********************************************************************/ void osm_sm_state_mgr_construct( IN osm_sm_state_mgr_t * const p_sm_mgr ) { - cl_memclr( p_sm_mgr, sizeof( *p_sm_mgr ) ); + memset( p_sm_mgr, 0, sizeof( *p_sm_mgr ) ); cl_spinlock_construct( &p_sm_mgr->state_lock ); cl_timer_construct( &p_sm_mgr->polling_timer ); } @@ -629,7 +633,7 @@ osm_sm_state_mgr_process( if( p_sm_mgr->p_subn->first_time_master_sweep == FALSE ) p_sm_mgr->p_subn->first_time_master_sweep = TRUE; /* Turn on the force_immediate_heavy_sweep - we want a - * heavy sweep to occure on the first sweep of this SM. */ + * heavy sweep to occur on the first sweep of this SM. */ p_sm_mgr->p_subn->force_immediate_heavy_sweep = TRUE; p_sm_mgr->p_subn->sm_state = IB_SMINFO_STATE_MASTER; @@ -699,7 +703,7 @@ osm_sm_state_mgr_process( osm_log( p_sm_mgr->p_log, OSM_LOG_VERBOSE, "osm_sm_state_mgr_process: " "Forcing immediate heavy sweep. " - "Received OSM_SM_SIGNAL_HANDOVER\n" ); + "Received OSM_SM_SIGNAL_HANDOVER or OSM_SM_SIGNAL_POLLING_TIMEOUT\n" ); p_sm_mgr->p_polling_sm = NULL; p_sm_mgr->p_subn->force_immediate_heavy_sweep = TRUE; osm_state_mgr_process( p_sm_mgr->p_state_mgr, OSM_SIGNAL_SWEEP ); @@ -719,7 +723,7 @@ osm_sm_state_mgr_process( * to handover the mastership to us. Need to start polling * on that SM, to make sure it is alive, if it isn't - then * we should move back to discovering, since something must - * have happend to it. + * have happened to it. */ __osm_sm_state_mgr_start_polling( p_sm_mgr ); break; @@ -865,3 +869,4 @@ osm_sm_state_mgr_check_legality( OSM_LOG_EXIT( p_sm_mgr->p_log ); return ( status ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_sminfo_rcv.c b/trunk/ulp/opensm/user/opensm/osm_sminfo_rcv.c index 20df8b6b..770b0ca9 100755 --- a/trunk/ulp/opensm/user/opensm/osm_sminfo_rcv.c +++ b/trunk/ulp/opensm/user/opensm/osm_sminfo_rcv.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -48,8 +48,9 @@ # include #endif /* HAVE_CONFIG_H */ +#include +#include #include -#include #include #include #include @@ -68,7 +69,7 @@ void osm_sminfo_rcv_construct( IN osm_sminfo_rcv_t* const p_rcv ) { - cl_memclr( p_rcv, sizeof(*p_rcv) ); + memset( p_rcv, 0, sizeof(*p_rcv) ); } /********************************************************************** @@ -121,8 +122,8 @@ osm_sminfo_rcv_init( By higher - we mean: SM with higher priority or with same priority and lower GUID. **********************************************************************/ -inline boolean_t -__osm_sminfo_rcv_remote_sm_is_higher ( +static inline boolean_t +__osm_sminfo_rcv_remote_sm_is_higher( IN const osm_sminfo_rcv_t* p_rcv, IN const ib_sm_info_t* p_remote_sm ) { @@ -136,13 +137,13 @@ __osm_sminfo_rcv_remote_sm_is_higher ( /********************************************************************** **********************************************************************/ -void +static void __osm_sminfo_rcv_process_get_request( IN const osm_sminfo_rcv_t* const p_rcv, IN const osm_madw_t* const p_madw ) { uint8_t payload[IB_SMP_DATA_SIZE]; - ib_smp_t* p_smp; + ib_smp_t* p_smp; ib_sm_info_t* p_smi = (ib_sm_info_t*)payload; ib_api_status_t status; ib_sm_info_t* p_remote_smi; @@ -154,7 +155,7 @@ __osm_sminfo_rcv_process_get_request( /* No real need to grab the lock for this function. */ - cl_memclr( payload, sizeof( payload ) ); + memset( payload, 0, sizeof( payload ) ); p_smp = osm_madw_get_smp_ptr( p_madw ); @@ -209,7 +210,7 @@ __osm_sminfo_rcv_process_get_request( * FUTURE - TO DO: * Check that the SM_Key is matching. **********************************************************************/ -ib_api_status_t +static ib_api_status_t __osm_sminfo_rcv_check_set_req_legality( IN const ib_smp_t* const p_smp ) { @@ -240,18 +241,18 @@ __osm_sminfo_rcv_check_set_req_legality( /********************************************************************** **********************************************************************/ -void +static void __osm_sminfo_rcv_process_set_request( IN const osm_sminfo_rcv_t* const p_rcv, - IN const osm_madw_t* const p_madw ) + IN const osm_madw_t* const p_madw ) { - uint8_t payload[IB_SMP_DATA_SIZE]; - ib_smp_t* p_smp; - ib_sm_info_t* p_smi = (ib_sm_info_t*)payload; + uint8_t payload[IB_SMP_DATA_SIZE]; + ib_smp_t* p_smp; + ib_sm_info_t* p_smi = (ib_sm_info_t*)payload; ib_sm_info_t* p_rcv_smi; - ib_api_status_t status; + ib_api_status_t status; osm_sm_signal_t sm_signal; - ib_sm_info_t* p_remote_smi; + ib_sm_info_t* p_remote_smi; OSM_LOG_ENTER( p_rcv->p_log, __osm_sminfo_rcv_process_set_request ); @@ -260,7 +261,7 @@ __osm_sminfo_rcv_process_set_request( /* No real need to grab the lock for this function. */ - cl_memclr( payload, sizeof( payload ) ); + memset( payload, 0, sizeof( payload ) ); /* get the lock */ CL_PLOCK_EXCL_ACQUIRE( p_rcv->p_lock ); @@ -303,7 +304,7 @@ __osm_sminfo_rcv_process_set_request( p_smi->sm_key = 0; } - /* Check the legality of the packet */ + /* Check the legality of the packet */ status = __osm_sminfo_rcv_check_set_req_legality( p_smp ); if ( status != IB_SUCCESS ) { @@ -312,7 +313,7 @@ __osm_sminfo_rcv_process_set_request( "Check legality failed. AttributeModifier:0x%X RemoteState:%s\n", p_smp->attr_mod, osm_get_sm_mgr_state_str(ib_sminfo_get_state( p_rcv_smi ) ) ); - /* send a response with error code */ + /* send a response with error code */ status = osm_resp_send( p_rcv->p_resp, p_madw, 7, payload ); if( status != IB_SUCCESS ) { @@ -325,7 +326,7 @@ __osm_sminfo_rcv_process_set_request( goto Exit; } - /* translate from IB_SMINFO_ATTR to OSM_SM_SIGNAL */ + /* translate from IB_SMINFO_ATTR to OSM_SM_SIGNAL */ switch (p_smp->attr_mod) { case IB_SMINFO_ATTR_MOD_HANDOVER: @@ -355,7 +356,7 @@ __osm_sminfo_rcv_process_set_request( goto Exit; } - /* check legality of the needed transition in the SM state machine */ + /* check legality of the needed transition in the SM state machine */ status = osm_sm_state_mgr_check_legality( p_rcv->p_sm_state_mgr, sm_signal ); if ( status != IB_SUCCESS ) @@ -365,7 +366,7 @@ __osm_sminfo_rcv_process_set_request( "Check legality of SM needed transition. AttributeModifier:0x%X RemoteState:%s\n", p_smp->attr_mod, osm_get_sm_mgr_state_str(ib_sminfo_get_state( p_rcv_smi ) ) ); - /* send a response with error code */ + /* send a response with error code */ status = osm_resp_send( p_rcv->p_resp, p_madw, 7, payload ); if( status != IB_SUCCESS ) { @@ -378,7 +379,7 @@ __osm_sminfo_rcv_process_set_request( goto Exit; } - /* the SubnSet (SMInfo) command is ok. Send a response. */ + /* the SubnSet(SMInfo) command is ok. Send a response. */ status = osm_resp_send( p_rcv->p_resp, p_madw, 0, payload ); if( status != IB_SUCCESS ) { @@ -388,25 +389,25 @@ __osm_sminfo_rcv_process_set_request( ib_get_err_str( status ) ); } - /* it is a legal packet - act according to it */ + /* it is a legal packet - act according to it */ - /* if the AttributeModifier is STANDBY - need to save on the */ - /* p_sm_state_mgr in the master_guid variable - the guid of the */ - /* current master. */ - if ( p_smp->attr_mod == IB_SMINFO_ATTR_MOD_STANDBY) + /* if the AttributeModifier is STANDBY - need to save on the */ + /* p_sm_state_mgr in the master_guid variable - the guid of the */ + /* current master. */ + if ( p_smp->attr_mod == IB_SMINFO_ATTR_MOD_STANDBY ) { osm_log( p_rcv->p_log, OSM_LOG_VERBOSE, "__osm_sminfo_rcv_process_set_request: " "Received a STANDBY signal. Updating " - "sm_state_mgr master_guid: 0x%X\n", - p_rcv_smi->guid ); + "sm_state_mgr master_guid: 0x%016" PRIx64 "\n", + cl_ntoh64(p_rcv_smi->guid) ); p_rcv->p_sm_state_mgr->master_guid = p_rcv_smi->guid; } - /* call osm_sm_state_mgr_process with the received signal. */ + /* call osm_sm_state_mgr_process with the received signal. */ CL_PLOCK_RELEASE( p_rcv->p_lock ); status = osm_sm_state_mgr_process( p_rcv->p_sm_state_mgr, - sm_signal); + sm_signal ); if( status != IB_SUCCESS ) { @@ -426,7 +427,7 @@ __osm_sminfo_rcv_process_set_request( * and thus cannot call osm_state_mgr_process (that locks the state_lock). * If return OSM_SIGNAL_NONE - do not call osm_state_mgr_process. **********************************************************************/ -osm_signal_t +static osm_signal_t __osm_sminfo_rcv_process_get_sm( IN const osm_sminfo_rcv_t* const p_rcv, IN const osm_remote_sm_t* const p_sm ) @@ -461,7 +462,7 @@ __osm_sminfo_rcv_process_get_sm( break; case IB_SMINFO_STATE_MASTER: ret_val = OSM_SIGNAL_MASTER_OR_HIGHER_SM_DETECTED; - /* save on the p_sm_state_mgr the guid of the current master. */ + /* save on the p_sm_state_mgr the guid of the current master. */ osm_log( p_rcv->p_log, OSM_LOG_VERBOSE, "__osm_sminfo_rcv_process_get_sm: " "Found master SM. Updating sm_state_mgr master_guid: 0x%016" PRIx64 "\n", @@ -472,14 +473,15 @@ __osm_sminfo_rcv_process_get_sm( case IB_SMINFO_STATE_STANDBY: if ( __osm_sminfo_rcv_remote_sm_is_higher(p_rcv, p_smi) == TRUE ) { - /* the remote is a higher sm - need to stop sweeping */ + /* the remote is a higher sm - need to stop sweeping */ ret_val = OSM_SIGNAL_MASTER_OR_HIGHER_SM_DETECTED; - /* save on the p_sm_state_mgr the guid of the higher SM we found - */ - /* we will poll it - as long as it lives - we should be in Standby. */ + /* save on the p_sm_state_mgr the guid of the higher SM we found - */ + /* we will poll it - as long as it lives - we should be in Standby. */ osm_log( p_rcv->p_log, OSM_LOG_VERBOSE, "__osm_sminfo_rcv_process_get_sm: " - "Found higher SM. Updating sm_state_mgr master_guid: 0x%X\n", - p_sm->p_port->guid ); + "Found higher SM. Updating sm_state_mgr master_guid:" + " 0x%016" PRIx64 "\n", + cl_ntoh64(p_sm->p_port->guid) ); p_rcv->p_sm_state_mgr->master_guid = p_sm->p_port->guid; } break; @@ -489,18 +491,17 @@ __osm_sminfo_rcv_process_get_sm( break; case IB_SMINFO_STATE_STANDBY: - /* if the guid of the SM that sent us this response is equal to the */ - /* p_sm_mgr->master_guid - then this is a signal that the polling */ - /* */ + /* if the guid of the SM that sent us this response is equal to the */ + /* p_sm_mgr->master_guid - then this is a signal that the polling */ switch( ib_sminfo_get_state( p_smi ) ) { case IB_SMINFO_STATE_MASTER: - /* This means the master is alive */ - /* Signal that to the SM state mgr */ + /* This means the master is alive */ + /* Signal that to the SM state mgr */ osm_sm_state_mgr_signal_master_is_alive( p_rcv->p_sm_state_mgr ); break; case IB_SMINFO_STATE_STANDBY: - /* This should be the response from the sm we are polling. */ + /* This should be the response from the sm we are polling. */ /* If it is - then signal master is alive */ if (p_rcv->p_sm_state_mgr->master_guid == p_sm->p_port->guid) { @@ -513,7 +514,7 @@ __osm_sminfo_rcv_process_get_sm( } break; default: - /* any other state - do nothing */ + /* any other state - do nothing */ break; } break; @@ -537,7 +538,7 @@ __osm_sminfo_rcv_process_get_sm( } break; default: - /* any other state - do nothing */ + /* any other state - do nothing */ break; } break; @@ -552,19 +553,18 @@ __osm_sminfo_rcv_process_get_sm( /********************************************************************** **********************************************************************/ -void +static void __osm_sminfo_rcv_process_get_response( IN const osm_sminfo_rcv_t* const p_rcv, IN const osm_madw_t* const p_madw ) { const ib_smp_t* p_smp; - const ib_sm_info_t* p_smi; + const ib_sm_info_t* p_smi; cl_qmap_t* p_sm_tbl; cl_qmap_t* p_port_tbl; osm_port_t* p_port; ib_net64_t port_guid; osm_remote_sm_t* p_sm; - ib_api_status_t status; osm_signal_t process_get_sm_ret_val = OSM_SIGNAL_NONE; OSM_LOG_ENTER( p_rcv->p_log, __osm_sminfo_rcv_process_get_response ); @@ -615,7 +615,7 @@ __osm_sminfo_rcv_process_get_response( { osm_log( p_rcv->p_log, OSM_LOG_ERROR, "__osm_sminfo_rcv_process_get_response: ERR 2F12: " - "No Port object for this SM\n" ); + "No port object for this SM\n" ); goto Exit; } @@ -634,7 +634,7 @@ __osm_sminfo_rcv_process_get_response( p_sm = (osm_remote_sm_t*)cl_qmap_get( p_sm_tbl, port_guid ); if( p_sm == (osm_remote_sm_t*)cl_qmap_end( p_sm_tbl ) ) { - p_sm = cl_malloc( sizeof(*p_sm) ); + p_sm = malloc( sizeof(*p_sm) ); if( p_sm == NULL ) { osm_log( p_rcv->p_log, OSM_LOG_ERROR, @@ -643,15 +643,7 @@ __osm_sminfo_rcv_process_get_response( goto Exit; } - status = osm_remote_sm_init( p_sm, p_port, p_smi ); - if( status != IB_SUCCESS ) - { - osm_log( p_rcv->p_log, OSM_LOG_ERROR, - "__osm_sminfo_rcv_process_get_response: ERR 2F15: " - "Other SM object initialization failed (%s)\n", - ib_get_err_str( status ) ); - goto Exit; - } + osm_remote_sm_init( p_sm, p_port, p_smi ); cl_qmap_insert( p_sm_tbl, port_guid, &p_sm->map_item ); } @@ -679,7 +671,7 @@ __osm_sminfo_rcv_process_get_response( /********************************************************************** **********************************************************************/ -void +static void __osm_sminfo_rcv_process_set_response( IN const osm_sminfo_rcv_t* const p_rcv, IN const osm_madw_t* const p_madw ) @@ -743,30 +735,30 @@ osm_sminfo_rcv_process( */ if( ib_smp_is_response( p_smp ) ) { - /* Get the context - to see if this is a response to a Get or Set method */ + /* Get the context - to see if this is a response to a Get or Set method */ p_smi_context = osm_madw_get_smi_context_ptr( p_madw ); if ( p_smi_context->set_method == FALSE ) { - /* this is a response to a Get method */ + /* this is a response to a Get method */ __osm_sminfo_rcv_process_get_response( p_rcv, p_madw ); } else { - /* this is a response to a Set method */ + /* this is a response to a Set method */ __osm_sminfo_rcv_process_set_response( p_rcv, p_madw ); } } else { - /* This is a request */ + /* This is a request */ if ( p_smp->method == IB_MAD_METHOD_GET ) { - /* This is a SubnGet request */ + /* This is a SubnGet request */ __osm_sminfo_rcv_process_get_request( p_rcv, p_madw ); } else { - /* This is a SubnSet request */ + /* This is a SubnSet request */ __osm_sminfo_rcv_process_set_request( p_rcv, p_madw ); } } diff --git a/trunk/ulp/opensm/user/opensm/osm_sminfo_rcv_ctrl.c b/trunk/ulp/opensm/user/opensm/osm_sminfo_rcv_ctrl.c index f8fe47b4..61f444f0 100644 --- a/trunk/ulp/opensm/user/opensm/osm_sminfo_rcv_ctrl.c +++ b/trunk/ulp/opensm/user/opensm/osm_sminfo_rcv_ctrl.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Implementation of osm_sminfo_rcv_ctrl_t. @@ -48,7 +49,7 @@ # include #endif /* HAVE_CONFIG_H */ -#include +#include #include #include @@ -70,7 +71,7 @@ void osm_sminfo_rcv_ctrl_construct( IN osm_sminfo_rcv_ctrl_t* const p_ctrl ) { - cl_memclr( p_ctrl, sizeof(*p_ctrl) ); + memset( p_ctrl, 0, sizeof(*p_ctrl) ); p_ctrl->h_disp = CL_DISP_INVALID_HANDLE; } @@ -123,3 +124,4 @@ osm_sminfo_rcv_ctrl_init( return( status ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_state_mgr.c b/trunk/ulp/opensm/user/opensm/osm_state_mgr.c index 79cf8b06..19ec46f0 100644 --- a/trunk/ulp/opensm/user/opensm/osm_state_mgr.c +++ b/trunk/ulp/opensm/user/opensm/osm_state_mgr.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -35,7 +35,7 @@ /* * Abstract: * Implementation of osm_state_mgr_t. - * This file implements the Discovery Done Manager object. + * This file implements the State Manager object. * * Environment: * Linux User Mode @@ -47,9 +47,10 @@ # include #endif /* HAVE_CONFIG_H */ +#include #include +#include #include -#include #include #include #include @@ -61,17 +62,22 @@ #include #include #include +#include #include #include #include +#define SUBNET_LIST_FILENAME "/osm-subnet.lst" + +osm_signal_t osm_qos_setup(IN osm_opensm_t * p_osm); + /********************************************************************** **********************************************************************/ void osm_state_mgr_construct( IN osm_state_mgr_t * const p_mgr ) { - cl_memclr( p_mgr, sizeof( *p_mgr ) ); + memset( p_mgr, 0, sizeof( *p_mgr ) ); cl_spinlock_construct( &p_mgr->state_lock ); cl_spinlock_construct( &p_mgr->idle_lock ); p_mgr->state = OSM_SM_STATE_INIT; @@ -105,14 +111,12 @@ osm_state_mgr_init( IN osm_mcast_mgr_t * const p_mcast_mgr, IN osm_link_mgr_t * const p_link_mgr, IN osm_drop_mgr_t * const p_drop_mgr, - IN osm_pkey_mgr_t * const p_pkey_mgr, IN osm_req_t * const p_req, IN osm_stats_t * const p_stats, IN osm_sm_state_mgr_t * const p_sm_state_mgr, IN const osm_sm_mad_ctrl_t * const p_mad_ctrl, IN cl_plock_t * const p_lock, IN cl_event_t * const p_subnet_up_event, - IN char *const p_report_buf, IN osm_log_t * const p_log ) { cl_status_t status; @@ -125,13 +129,11 @@ osm_state_mgr_init( CL_ASSERT( p_mcast_mgr ); CL_ASSERT( p_link_mgr ); CL_ASSERT( p_drop_mgr ); - CL_ASSERT( p_pkey_mgr ); CL_ASSERT( p_req ); CL_ASSERT( p_stats ); CL_ASSERT( p_sm_state_mgr ); CL_ASSERT( p_mad_ctrl ); CL_ASSERT( p_lock ); - CL_ASSERT( p_report_buf ); osm_state_mgr_construct( p_mgr ); @@ -142,7 +144,6 @@ osm_state_mgr_init( p_mgr->p_mcast_mgr = p_mcast_mgr; p_mgr->p_link_mgr = p_link_mgr; p_mgr->p_drop_mgr = p_drop_mgr; - p_mgr->p_pkey_mgr = p_pkey_mgr; p_mgr->p_mad_ctrl = p_mad_ctrl; p_mgr->p_req = p_req; p_mgr->p_stats = p_stats; @@ -150,7 +151,6 @@ osm_state_mgr_init( p_mgr->state = OSM_SM_STATE_IDLE; p_mgr->p_lock = p_lock; p_mgr->p_subnet_up_event = p_subnet_up_event; - p_mgr->p_report_buf = p_report_buf; p_mgr->state_step_mode = OSM_STATE_STEP_CONTINUOUS; p_mgr->next_stage_signal = OSM_SIGNAL_NONE; @@ -194,6 +194,10 @@ __osm_state_mgr_up_msg( /* clear the signal */ p_mgr->p_subn->moved_to_master_state = FALSE; } + else + { + osm_log( p_mgr->p_log, OSM_LOG_INFO, "SUBNET UP\n" ); /* Format Waived */ + } if( p_mgr->p_subn->opt.sweep_interval ) { @@ -469,33 +473,33 @@ __osm_state_mgr_sweep_light_msg( /********************************************************************** **********************************************************************/ -void +static void __osm_state_mgr_signal_warning( IN const osm_state_mgr_t * const p_mgr, IN const osm_signal_t signal ) { osm_log( p_mgr->p_log, OSM_LOG_VERBOSE, "__osm_state_mgr_signal_warning: " - "Invalid signal %s(%d) in state %s\n", + "Invalid signal %s(%lu) in state %s\n", osm_get_sm_signal_str( signal ), signal, osm_get_sm_state_str( p_mgr->state ) ); } /********************************************************************** **********************************************************************/ -void +static void __osm_state_mgr_signal_error( IN const osm_state_mgr_t * const p_mgr, IN const osm_signal_t signal ) { /* the Request for IDLE processing can come async to the state so it - * really just a verbose ... */ + * really is just verbose ... */ if( signal == OSM_SIGNAL_IDLE_TIME_PROCESS_REQUEST ) __osm_state_mgr_signal_warning( p_mgr, signal ); else osm_log( p_mgr->p_log, OSM_LOG_ERROR, "__osm_state_mgr_signal_error: ERR 3303: " - "Invalid signal %s(%d) in state %s\n", + "Invalid signal %s(%lu) in state %s\n", osm_get_sm_signal_str( signal ), signal, osm_get_sm_state_str( p_mgr->state ) ); } @@ -582,7 +586,7 @@ __osm_state_mgr_get_sw_info( p_node = osm_switch_get_node_ptr( p_sw ); p_dr_path = osm_node_get_any_dr_path_ptr( p_node ); - cl_memclr( &context, sizeof( context ) ); + memset( &context, 0, sizeof( context ) ); mad_context.si_context.node_guid = osm_node_get_node_guid( p_node ); mad_context.si_context.set_method = FALSE; @@ -620,10 +624,10 @@ __osm_state_mgr_get_remote_port_info( /* generate a dr path leaving on the physp to the remote node */ p_dr_path = osm_physp_get_dr_path_ptr( p_physp ); - cl_memcpy( &rem_node_dr_path, p_dr_path, sizeof( osm_dr_path_t ) ); + memcpy( &rem_node_dr_path, p_dr_path, sizeof( osm_dr_path_t ) ); osm_dr_path_extend( &rem_node_dr_path, osm_physp_get_port_num( p_physp ) ); - cl_memclr( &mad_context, sizeof( mad_context ) ); + memset( &mad_context, 0, sizeof( mad_context ) ); mad_context.pi_context.node_guid = osm_node_get_node_guid( osm_physp_get_node_ptr( p_physp ) ); @@ -633,6 +637,7 @@ __osm_state_mgr_get_remote_port_info( mad_context.pi_context.light_sweep = TRUE; mad_context.pi_context.ignore_errors = FALSE; mad_context.pi_context.update_master_sm_base_lid = FALSE; + mad_context.pi_context.active_transition = FALSE; /* note that with some negative logic - if the query failed it means that * there is no point in going to heavy sweep */ @@ -667,7 +672,7 @@ __osm_state_mgr_sweep_hop_0( OSM_LOG_ENTER( p_mgr->p_log, __osm_state_mgr_sweep_hop_0 ); - cl_memclr( path_array, sizeof( path_array ) ); + memset( path_array, 0, sizeof( path_array ) ); /* * First, get the bind handle. @@ -678,7 +683,7 @@ __osm_state_mgr_sweep_hop_0( __osm_state_mgr_sweep_heavy_msg( p_mgr ); /* - * Start the sweep by clearning the port counts, then + * Start the sweep by clearing the port counts, then * get our own NodeInfo at 0 hops. */ CL_PLOCK_ACQUIRE( p_mgr->p_lock ); @@ -702,7 +707,7 @@ __osm_state_mgr_sweep_hop_0( CL_PLOCK_RELEASE( p_mgr->p_lock ); - cl_memclr( &ni_context, sizeof( ni_context ) ); + memset( &ni_context, 0, sizeof( ni_context ) ); osm_dr_path_init( &dr_path, h_bind, 0, path_array ); status = osm_req_get( p_mgr->p_req, &dr_path, @@ -735,7 +740,6 @@ static ib_api_status_t __osm_state_mgr_clean_known_lids( IN osm_state_mgr_t * const p_mgr ) { - ib_api_status_t status = IB_SUCCESS; cl_ptr_vector_t *p_vec = &( p_mgr->p_subn->port_lid_tbl ); uint32_t i; @@ -752,7 +756,6 @@ __osm_state_mgr_clean_known_lids( OSM_LOG_EXIT( p_mgr->p_log ); return ( status ); - } /********************************************************************** @@ -798,8 +801,8 @@ __osm_state_mgr_notify_lid_change( } /********************************************************************** - Returns true if the SM port is down. - The SM's port object must exist in the port_guid table. + Returns true if the SM port is down. + The SM's port object must exist in the port_guid table. **********************************************************************/ static boolean_t __osm_state_mgr_is_sm_port_down( @@ -928,12 +931,13 @@ __osm_state_mgr_sweep_hop_1( CL_ASSERT( h_bind != OSM_BIND_INVALID_HANDLE ); - cl_memclr( path_array, sizeof( path_array ) ); + memset( path_array, 0, sizeof( path_array ) ); /* the hop_1 operations depend on the type of our node. * Currently - legal nodes that can host SM are SW and CA */ switch ( osm_node_get_type( p_node ) ) { case IB_NODE_TYPE_CA: + case IB_NODE_TYPE_ROUTER: context.ni_context.node_guid = osm_node_get_node_guid( p_node ); context.ni_context.port_num = port_num; @@ -995,8 +999,8 @@ __osm_state_mgr_sweep_hop_1( default: osm_log( p_mgr->p_log, OSM_LOG_ERROR, - "__osm_state_mgr_sweep_hop_1: ERR 3313: " - " Supported node type that hosts SM is CA or SW only\n" ); + "__osm_state_mgr_sweep_hop_1: ERR 3313: Unknown node type %d\n", + osm_node_get_type( p_node ) ); } Exit: @@ -1005,7 +1009,7 @@ __osm_state_mgr_sweep_hop_1( } /********************************************************************** - Initiates a light-weight sweep of the subnet. + Initiates a lightweight sweep of the subnet. Used during normal sweeps after the subnet is up. **********************************************************************/ static ib_api_status_t @@ -1017,14 +1021,13 @@ __osm_state_mgr_light_sweep_start( cl_qmap_t *p_sw_tbl; cl_list_t *p_no_rem_port_list; cl_list_iterator_t list_iter; - uint8_t path_array[IB_SUBNET_PATH_HOPS_MAX]; OSM_LOG_ENTER( p_mgr->p_log, __osm_state_mgr_light_sweep_start ); p_sw_tbl = &p_mgr->p_subn->sw_guid_tbl; - cl_memclr( path_array, sizeof( path_array ) ); + memset( path_array, 0, sizeof( path_array ) ); /* * First, get the bind handle. @@ -1065,30 +1068,31 @@ __osm_state_mgr_light_sweep_start( /********************************************************************** **********************************************************************/ static void -osm_topology_file_create( +__osm_topology_file_create( IN osm_state_mgr_t * const p_mgr ) { - const osm_node_t *p_node; char *file_name; FILE *rc; + char desc[IB_NODE_DESCRIPTION_SIZE + 1]; - OSM_LOG_ENTER( p_mgr->p_log, osm_topology_file_create ); + OSM_LOG_ENTER( p_mgr->p_log, __osm_topology_file_create ); CL_PLOCK_ACQUIRE( p_mgr->p_lock ); file_name = - ( char * )cl_malloc( strlen( p_mgr->p_subn->opt.dump_files_dir ) + 12 ); + ( char * )malloc( strlen( p_mgr->p_subn->opt.dump_files_dir ) + + strlen(SUBNET_LIST_FILENAME) + 1 ); CL_ASSERT( file_name ); strcpy( file_name, p_mgr->p_subn->opt.dump_files_dir ); - strcat( file_name, "/subnet.lst" ); + strcat( file_name, SUBNET_LIST_FILENAME ); if( ( rc = fopen( file_name, "w" ) ) == NULL ) { osm_log( p_mgr->p_log, OSM_LOG_DEBUG, - "osm_topology_file_create: " + "__osm_topology_file_create: " "fopen failed for file:%s\n", file_name ); CL_PLOCK_RELEASE( p_mgr->p_lock ); @@ -1126,7 +1130,6 @@ osm_topology_file_create( if( p_node->node_info.node_type == IB_NODE_TYPE_SWITCH ) { - p_default_physp = osm_node_get_physp_ptr( p_node, 0 ); } else @@ -1134,11 +1137,15 @@ osm_topology_file_create( p_default_physp = p_physp; } + memcpy(desc, p_node->node_desc.description, + IB_NODE_DESCRIPTION_SIZE); + desc[IB_NODE_DESCRIPTION_SIZE] = '\0'; + fprintf( rc, "{ %s%s Ports:%02X" " SystemGUID:%016" PRIx64 " NodeGUID:%016" PRIx64 " PortGUID:%016" PRIx64 - " VenID:%08X DevID:%04X Rev:%08X {%s} LID:%04X PN:%02X } ", + " VenID:%06X DevID:%04X Rev:%08X {%s} LID:%04X PN:%02X } ", ( p_node->node_info.node_type == IB_NODE_TYPE_SWITCH ) ? "SW" : ( p_node->node_info. node_type == @@ -1154,9 +1161,9 @@ osm_topology_file_create( cl_ntoh64( p_physp->port_guid ), cl_ntoh32( ib_node_info_get_vendor_id ( &p_node->node_info ) ), - cl_ntoh32( p_node->node_info.device_id ), + cl_ntoh16( p_node->node_info.device_id ), cl_ntoh32( p_node->node_info.revision ), - p_node->node_desc.description, + desc, cl_ntoh16( p_default_physp->port_info.base_lid ), cPort ); @@ -1164,7 +1171,6 @@ osm_topology_file_create( if( p_nbnode->node_info.node_type == IB_NODE_TYPE_SWITCH ) { - p_default_physp = osm_node_get_physp_ptr( p_nbnode, 0 ); } else @@ -1172,6 +1178,9 @@ osm_topology_file_create( p_default_physp = p_rphysp; } + memcpy(desc, p_nbnode->node_desc.description, + IB_NODE_DESCRIPTION_SIZE); + desc[IB_NODE_DESCRIPTION_SIZE] = '\0'; fprintf( rc, "{ %s%s Ports:%02X" " SystemGUID:%016" PRIx64 @@ -1195,7 +1204,7 @@ osm_topology_file_create( ( &p_nbnode->node_info ) ), cl_ntoh32( p_nbnode->node_info.device_id ), cl_ntoh32( p_nbnode->node_info.revision ), - p_nbnode->node_desc.description, + desc, cl_ntoh16( p_default_physp->port_info.base_lid ), p_rphysp->port_num ); @@ -1224,7 +1233,7 @@ osm_topology_file_create( fclose( rc ); Exit: - cl_free( file_name ); + free( file_name ); OSM_LOG_EXIT( p_mgr->p_log ); } @@ -1243,16 +1252,19 @@ __osm_state_mgr_report( uint8_t port_num; uint8_t start_port; uint32_t num_ports; - char line[OSM_REPORT_LINE_SIZE]; uint8_t node_type; - uint32_t line_num = 0; + + if( !osm_log_is_active( p_mgr->p_log, OSM_LOG_VERBOSE ) ) + return; OSM_LOG_ENTER( p_mgr->p_log, __osm_state_mgr_report ); - if( !osm_log_is_active( p_mgr->p_log, OSM_LOG_VERBOSE ) ) - { - goto Exit; - } + osm_log_printf( p_mgr->p_log, OSM_LOG_VERBOSE, + "\n===================================================" + "====================================================" + "\nVendor : Ty " + ": # : Sta : LID : LMC : MTU : LWA : LSA : Port GUID " + " : Neighbor Port (Port #)\n" ); p_tbl = &p_mgr->p_subn->port_guid_tbl; @@ -1282,29 +1294,16 @@ __osm_state_mgr_report( num_ports = osm_port_get_num_physp( p_port ); for( port_num = start_port; port_num < num_ports; port_num++ ) { - if( line_num == 0 ) - { - strcpy( p_mgr->p_report_buf, - "\n===================================================" - "====================================================" ); - strcat( p_mgr->p_report_buf, - "\nVendor : Ty " - ": # : Sta : LID : LMC : MTU : LWA : LSA : Port GUID " - " : Neighbor Port (Port #)\n" ); - line_num++; - } - p_physp = osm_port_get_phys_ptr( p_port, port_num ); if( ( p_physp == NULL ) || ( !osm_physp_is_valid( p_physp ) ) ) continue; - sprintf( line, "%s : %s : %02X :", - osm_get_manufacturer_str( cl_ntoh64 - ( osm_node_get_node_guid - ( p_node ) ) ), - osm_get_node_type_str_fixed_width( node_type ), port_num ); - - strcat( p_mgr->p_report_buf, line ); + osm_log_printf( p_mgr->p_log, OSM_LOG_VERBOSE, "%s : %s : %02X :", + osm_get_manufacturer_str( cl_ntoh64 + ( osm_node_get_node_guid + ( p_node ) ) ), + osm_get_node_type_str_fixed_width( node_type ), + port_num ); p_pi = osm_physp_get_port_info_ptr( p_physp ); @@ -1312,61 +1311,40 @@ __osm_state_mgr_report( * Port state is not defined for switch port 0 */ if( port_num == 0 ) - strcat( p_mgr->p_report_buf, " :" ); + osm_log_printf( p_mgr->p_log, OSM_LOG_VERBOSE, " :" ); else - { - sprintf( line, " %s :", - osm_get_port_state_str_fixed_width - ( ib_port_info_get_port_state( p_pi ) ) ); - strcat( p_mgr->p_report_buf, line ); - } + osm_log_printf( p_mgr->p_log, OSM_LOG_VERBOSE, " %s :", + osm_get_port_state_str_fixed_width + ( ib_port_info_get_port_state( p_pi ) ) ); /* * LID values are only meaningful in select cases. */ - if( ib_port_info_get_port_state( p_pi ) != IB_LINK_DOWN ) - { - if( ( ( node_type == IB_NODE_TYPE_SWITCH ) && ( port_num == 0 ) ) - || ( node_type != IB_NODE_TYPE_SWITCH ) ) - { - sprintf( line, " %04X : %01X :", - cl_ntoh16( p_pi->base_lid ), - ib_port_info_get_lmc( p_pi ) ); - - strcat( p_mgr->p_report_buf, line ); - } - else - strcat( p_mgr->p_report_buf, " : :" ); - } + if( ib_port_info_get_port_state( p_pi ) != IB_LINK_DOWN + && ( ( node_type == IB_NODE_TYPE_SWITCH && port_num == 0 ) + || node_type != IB_NODE_TYPE_SWITCH ) ) + osm_log_printf( p_mgr->p_log, OSM_LOG_VERBOSE, " %04X : %01X :", + cl_ntoh16( p_pi->base_lid ), + ib_port_info_get_lmc( p_pi ) ); else - strcat( p_mgr->p_report_buf, " : :" ); + osm_log_printf( p_mgr->p_log, OSM_LOG_VERBOSE, " : :" ); if( port_num != 0 ) - { - sprintf( line, " %s : %s : %s ", - osm_get_mtu_str( ib_port_info_get_neighbor_mtu( p_pi ) ), - osm_get_lwa_str( p_pi->link_width_active ), - osm_get_lsa_str( ib_port_info_get_link_speed_active - ( p_pi ) ) ); - } + osm_log_printf( p_mgr->p_log, OSM_LOG_VERBOSE, " %s : %s : %s ", + osm_get_mtu_str( ib_port_info_get_neighbor_mtu( p_pi ) ), + osm_get_lwa_str( p_pi->link_width_active ), + osm_get_lsa_str( ib_port_info_get_link_speed_active + ( p_pi ) ) ); else - { - sprintf( line, " %s : %s : %s ", " ", " ", " " ); - } - strcat( p_mgr->p_report_buf, line ); + osm_log_printf( p_mgr->p_log, OSM_LOG_VERBOSE, " : : " ); if( osm_physp_get_port_guid( p_physp ) == p_mgr->p_subn->sm_port_guid ) - { - sprintf( line, "* %016" PRIx64 " *", - cl_ntoh64( osm_physp_get_port_guid( p_physp ) ) ); - } + osm_log_printf( p_mgr->p_log, OSM_LOG_VERBOSE, "* %016" PRIx64 " *", + cl_ntoh64( osm_physp_get_port_guid( p_physp ) ) ); else - { - sprintf( line, ": %016" PRIx64 " :", - cl_ntoh64( osm_physp_get_port_guid( p_physp ) ) ); - } - strcat( p_mgr->p_report_buf, line ); + osm_log_printf( p_mgr->p_log, OSM_LOG_VERBOSE, ": %016" PRIx64 " :", + cl_ntoh64( osm_physp_get_port_guid( p_physp ) ) ); if( port_num && ( ib_port_info_get_port_state( p_pi ) != IB_LINK_DOWN ) ) @@ -1374,36 +1352,26 @@ __osm_state_mgr_report( p_remote_physp = osm_physp_get_remote( p_physp ); if( p_remote_physp && osm_physp_is_valid( p_remote_physp ) ) { - sprintf( line, " %016" PRIx64 " (%02X)", - cl_ntoh64( osm_physp_get_port_guid - ( p_remote_physp ) ), - osm_physp_get_port_num( p_remote_physp ) ); - strcat( p_mgr->p_report_buf, line ); + osm_log_printf( p_mgr->p_log, OSM_LOG_VERBOSE, + " %016" PRIx64 " (%02X)", + cl_ntoh64( osm_physp_get_port_guid + ( p_remote_physp ) ), + osm_physp_get_port_num( p_remote_physp ) ); } else - strcat( p_mgr->p_report_buf, " UNKNOWN" ); + osm_log_printf( p_mgr->p_log, OSM_LOG_VERBOSE, " UNKNOWN" ); } - strcat( p_mgr->p_report_buf, "\n" ); - - if( ++line_num >= OSM_REPORT_BUF_THRESHOLD ) - { - osm_log_raw( p_mgr->p_log, OSM_LOG_VERBOSE, p_mgr->p_report_buf ); - line_num = 0; - } + osm_log_printf( p_mgr->p_log, OSM_LOG_VERBOSE, "\n" ); } - strcat( p_mgr->p_report_buf, - "------------------------------------------------------" - "------------------------------------------------\n" ); + + osm_log_printf( p_mgr->p_log, OSM_LOG_VERBOSE, + "------------------------------------------------------" + "------------------------------------------------\n" ); p_port = ( osm_port_t * ) cl_qmap_next( &p_port->map_item ); } CL_PLOCK_RELEASE( p_mgr->p_lock ); - - if( line_num != 0 ) - osm_log_raw( p_mgr->p_log, OSM_LOG_VERBOSE, p_mgr->p_report_buf ); - - Exit: OSM_LOG_EXIT( p_mgr->p_log ); } @@ -1441,8 +1409,7 @@ __process_idle_time_queue_done( p_process_item->context2 ); } - - cl_free( p_process_item ); + free( p_process_item ); OSM_LOG_EXIT( p_mgr->p_log ); return; @@ -1482,25 +1449,24 @@ __process_idle_time_queue_start( CL_ASSERT( signal != OSM_SIGNAL_NONE ); - OSM_LOG_EXIT( p_mgr->p_log ); return signal; } /********************************************************************** - * Go over all the remote SMs (as update in the sm_guid_tbl). + * Go over all the remote SMs (as updated in the sm_guid_tbl). * Find if there is a remote sm that is a master SM. * If there is a remote master SM - return TRUE, else - return FALSE. **********************************************************************/ -osm_remote_sm_t * -__osm_state_mgr_exists_other_master( +static osm_remote_sm_t * +__osm_state_mgr_exists_other_master_sm( IN osm_state_mgr_t * const p_mgr ) { cl_qmap_t *p_sm_tbl; osm_remote_sm_t *p_sm; osm_remote_sm_t *p_sm_res = NULL; - OSM_LOG_ENTER( p_mgr->p_log, __osm_state_mgr_exists_other_master ); + OSM_LOG_ENTER( p_mgr->p_log, __osm_state_mgr_exists_other_master_sm ); p_sm_tbl = &p_mgr->p_subn->sm_guid_tbl; @@ -1513,9 +1479,9 @@ __osm_state_mgr_exists_other_master( if( ib_sminfo_get_state( &p_sm->smi ) == IB_SMINFO_STATE_MASTER ) { osm_log( p_mgr->p_log, OSM_LOG_VERBOSE, - "__osm_state_mgr_exists_other_master: " - "Found remote master sm with guid:0x%X\n", - p_sm->smi.guid ); + "__osm_state_mgr_exists_other_master_sm: " + "Found remote master SM with guid:0x%016" PRIx64 "\n", + cl_ntoh64(p_sm->smi.guid) ); p_sm_res = p_sm; goto Exit; } @@ -1532,7 +1498,7 @@ __osm_state_mgr_exists_other_master( * Compare this SM to the local SM. If the local SM is higher - * return NULL, if the remote SM is higher - return a pointer to it. **********************************************************************/ -osm_remote_sm_t * +static osm_remote_sm_t * __osm_state_mgr_get_highest_sm( IN osm_state_mgr_t * const p_mgr ) { @@ -1551,13 +1517,13 @@ __osm_state_mgr_get_highest_sm( highest_sm_priority = p_mgr->p_subn->opt.sm_priority; highest_sm_guid = p_mgr->p_subn->sm_port_guid; - /* go over all the remote SMs */ + /* go over all the remote SMs */ for( p_sm = ( osm_remote_sm_t * ) cl_qmap_head( p_sm_tbl ); p_sm != ( osm_remote_sm_t * ) cl_qmap_end( p_sm_tbl ); p_sm = ( osm_remote_sm_t * ) cl_qmap_next( &p_sm->map_item ) ) { - /* If the sm is in NOTACTIVE state - continue */ + /* If the sm is in NOTACTIVE state - continue */ if( ib_sminfo_get_state( &p_sm->smi ) == IB_SMINFO_STATE_NOTACTIVE ) continue; @@ -1565,8 +1531,8 @@ __osm_state_mgr_get_highest_sm( p_sm->smi.guid, highest_sm_priority, highest_sm_guid ) ) { - /* the new p_sm is with higher priority - update the highest_sm */ - /* to this sm */ + /* the new p_sm is with higher priority - update the highest_sm */ + /* to this sm */ p_highest_sm = p_sm; highest_sm_priority = ib_sminfo_get_priority( &p_sm->smi ); highest_sm_guid = p_sm->smi.guid; @@ -1587,9 +1553,9 @@ __osm_state_mgr_get_highest_sm( /********************************************************************** * Send SubnSet(SMInfo) SMP with HANDOVER attribute to the - * remote_sm given. + * remote_sm indicated. **********************************************************************/ -void +static void __osm_state_mgr_send_handover( IN osm_state_mgr_t * const p_mgr, IN osm_remote_sm_t * const p_sm ) @@ -1607,7 +1573,7 @@ __osm_state_mgr_send_handover( { osm_log( p_mgr->p_log, OSM_LOG_ERROR, "__osm_state_mgr_send_handover: ERR 3315: " - "Exit on testablity mode OSM_TEST_MODE_EXIT_BEFORE_SEND_HANDOVER\n" ); + "Exit on testability mode OSM_TEST_MODE_EXIT_BEFORE_SEND_HANDOVER\n" ); osm_exit_flag = TRUE; sleep( 3 ); exit( 1 ); @@ -1617,7 +1583,7 @@ __osm_state_mgr_send_handover( * Send a query of SubnSet(SMInfo) HANDOVER to the remote sm given. */ - cl_memclr( &context, sizeof( context ) ); + memset( &context, 0, sizeof( context ) ); p_port = p_sm->p_port; if( p_port == NULL ) { @@ -1627,11 +1593,11 @@ __osm_state_mgr_send_handover( goto Exit; } - /* update the master_guid in the p_sm_state_mgr object according to */ - /* the guid of the port where the new Master SM should reside. */ + /* update the master_guid in the p_sm_state_mgr object according to */ + /* the guid of the port where the new Master SM should reside. */ osm_log( p_mgr->p_log, OSM_LOG_VERBOSE, "__osm_state_mgr_send_handover: " - "Handover mastership. Updating sm_state_mgr master_guid: %016" + "Handing over mastership. Updating sm_state_mgr master_guid: %016" PRIx64 "\n", cl_ntoh64( p_port->guid ) ); p_mgr->p_sm_state_mgr->master_guid = p_port->guid; @@ -1680,11 +1646,10 @@ __osm_state_mgr_send_handover( OSM_LOG_EXIT( p_mgr->p_log ); } - /********************************************************************** * Send Trap 64 on all ports in new_ports_list. **********************************************************************/ -void +static void __osm_state_mgr_report_new_ports( IN osm_state_mgr_t * const p_mgr ) { @@ -1695,9 +1660,11 @@ __osm_state_mgr_report_new_ports( ib_net64_t port_guid; uint16_t min_lid_ho; uint16_t max_lid_ho; + char desc[IB_NODE_DESCRIPTION_SIZE + 1]; OSM_LOG_ENTER( p_mgr->p_log, __osm_state_mgr_report_new_ports ); + CL_PLOCK_ACQUIRE( p_mgr->p_lock ); p_port = ( osm_port_t * ) ( cl_list_remove_head( &p_mgr->p_subn->new_ports_list ) ); @@ -1708,7 +1675,7 @@ __osm_state_mgr_report_new_ports( /* details of the notice */ notice.generic_type = 0x83; /* is generic subn mgt type */ - ib_notice_set_prod_type( ¬ice, CL_HTON32( 4 ) ); /* A Class Manager generator */ + ib_notice_set_prod_type_ho( ¬ice, 4 ); /* A Class Manager generator */ /* endport becomes to be reachable */ notice.g_or_v.generic.trap_num = CL_HTON16( 64 ); /* The sm_base_lid is saved in network order already. */ @@ -1717,8 +1684,8 @@ __osm_state_mgr_report_new_ports( /* we need to provide the GID */ port_gid.unicast.prefix = p_mgr->p_subn->opt.subnet_prefix; port_gid.unicast.interface_id = port_guid; - cl_memcpy( &( notice.data_details.ntc_64_67.gid ), - &( port_gid ), sizeof( ib_gid_t ) ); + memcpy( &( notice.data_details.ntc_64_67.gid ), + &( port_gid ), sizeof( ib_gid_t ) ); /* According to page 653 - the issuer gid in this case of trap * is the SM gid, since the SM is the initiator of this trap. */ @@ -1735,19 +1702,24 @@ __osm_state_mgr_report_new_ports( ib_get_err_str( status ) ); } osm_port_get_lid_range_ho( p_port, &min_lid_ho, &max_lid_ho ); + if (p_port->p_node) + { + memcpy(desc, p_port->p_node->node_desc.description, + IB_NODE_DESCRIPTION_SIZE); + desc[IB_NODE_DESCRIPTION_SIZE] = '\0'; + } osm_log( p_mgr->p_log, OSM_LOG_INFO, "Discovered new port with GUID:0x%016" PRIx64 " LID range [0x%X,0x%X] of node:%s\n", cl_ntoh64( port_gid.unicast.interface_id ), min_lid_ho, max_lid_ho, - ( p_port->p_node ? - ( char * )( p_port->p_node->node_desc.description ) : - "UNKNOWN" ) ); + p_port->p_node ? desc : "UNKNOWN" ); p_port = ( osm_port_t * ) ( cl_list_remove_head( &p_mgr->p_subn->new_ports_list ) ); } + CL_PLOCK_RELEASE( p_mgr->p_lock ); OSM_LOG_EXIT( p_mgr->p_log ); } @@ -1755,14 +1727,14 @@ __osm_state_mgr_report_new_ports( /********************************************************************** * Make sure that the lid_port_tbl of the subnet has only the ports * that are recognized, and in the correct lid place. There could be - * errors if we wanted to assign to a certain port with lid X, but that + * errors if we wanted to assign a certain port with lid X, but that * request didn't reach the port. In this case port_lid_tbl will have * the port under lid X, though the port isn't updated with this lid. * We will run a new heavy sweep (since there were errors in the * initialization), but here we'll clean the database from incorrect * information. **********************************************************************/ -void +static void __osm_state_mgr_check_tbl_consistency( IN osm_state_mgr_t * const p_mgr ) { @@ -1786,7 +1758,7 @@ __osm_state_mgr_check_tbl_consistency( p_port_guid_tbl = &p_mgr->p_subn->port_guid_tbl; - /* Let's go over all the ports according to port_guid _tbl, + /* Let's go over all the ports according to port_guid_tbl, * and add the port to a reference port_lid_tbl. */ p_next_port = ( osm_port_t * ) cl_qmap_head( p_port_guid_tbl ); while( p_next_port != ( osm_port_t * ) cl_qmap_end( p_port_guid_tbl ) ) @@ -1803,7 +1775,7 @@ __osm_state_mgr_check_tbl_consistency( ref_size = cl_ptr_vector_get_size( &ref_port_lid_tbl ); curr_size = cl_ptr_vector_get_size( p_port_lid_tbl ); - /* They should be the same, but compare it anyways */ + /* They should be the same, but compare it anyway */ max_lid = ( ref_size > curr_size ) ? ref_size : curr_size; for( lid = 1; lid <= max_lid; lid++ ) @@ -1822,14 +1794,14 @@ __osm_state_mgr_check_tbl_consistency( { /* There is an object in the subnet database for this lid, * but no such object exists in the reference port_list_tbl. - * This can occure if we wanted to assign a certain port with some + * This can occur if we wanted to assign a certain port with some * lid (different than the one pre-assigned to it), and the port - * didn't get the portInfo Set request. Due to that, the port - * is updated with its original lid in our data-base, but with the + * didn't get the PortInfo Set request. Due to this, the port + * is updated with its original lid in our database, but with the * new lid we wanted to give it in our port_lid_tbl. */ osm_log( p_mgr->p_log, OSM_LOG_ERROR, "__osm_state_mgr_check_tbl_consistency: ERR 3322: " - "lid 0x%X is wrongly assigned to port 0x%016" PRIx64 + "lid 0x%zX is wrongly assigned to port 0x%016" PRIx64 " in port_lid_tbl\n", lid, cl_ntoh64( osm_port_get_guid( p_port_stored ) ) ); } @@ -1843,7 +1815,7 @@ __osm_state_mgr_check_tbl_consistency( osm_log( p_mgr->p_log, OSM_LOG_ERROR, "__osm_state_mgr_check_tbl_consistency: ERR 3323: " "port 0x%016" PRIx64 " exists in new port_lid_tbl under " - "lid 0x%X, but missing in subnet port_lid_tbl db\n", + "lid 0x%zX, but missing in subnet port_lid_tbl db\n", cl_ntoh64( osm_port_get_guid( p_port_ref ) ), lid ); } else @@ -1854,7 +1826,7 @@ __osm_state_mgr_check_tbl_consistency( * and p_port_ref also didn't get the lid update. */ osm_log( p_mgr->p_log, OSM_LOG_ERROR, "__osm_state_mgr_check_tbl_consistency: ERR 3324: " - "lid 0x%X has port 0x%016" PRIx64 + "lid 0x%zX has port 0x%016" PRIx64 " in new port_lid_tbl db, " "and port 0x%016" PRIx64 " in subnet port_lid_tbl db\n", lid, cl_ntoh64( osm_port_get_guid( p_port_ref ) ), @@ -1880,6 +1852,7 @@ osm_state_mgr_process( { ib_api_status_t status; osm_remote_sm_t *p_remote_sm; + osm_signal_t tmp_signal; CL_ASSERT( p_mgr ); @@ -1970,6 +1943,9 @@ osm_state_mgr_process( * need to unset it. */ p_mgr->p_subn->subnet_initialization_error = FALSE; + /* rescan configuration updates */ + osm_subn_rescan_conf_file(&p_mgr->p_subn->opt); + status = __osm_state_mgr_sweep_hop_0( p_mgr ); if( status == IB_SUCCESS ) { @@ -1978,16 +1954,19 @@ osm_state_mgr_process( } signal = OSM_SIGNAL_NONE; break; + case OSM_SIGNAL_IDLE_TIME_PROCESS_REQUEST: p_mgr->state = OSM_SM_STATE_PROCESS_REQUEST; signal = OSM_SIGNAL_IDLE_TIME_PROCESS; break; + default: __osm_state_mgr_signal_error( p_mgr, signal ); signal = OSM_SIGNAL_NONE; break; } break; + case OSM_SM_STATE_PROCESS_REQUEST: switch ( signal ) { @@ -2003,9 +1982,11 @@ osm_state_mgr_process( p_mgr->state = OSM_SM_STATE_PROCESS_REQUEST_WAIT; signal = OSM_SIGNAL_NONE; break; + case OSM_SIGNAL_DONE: p_mgr->state = OSM_SM_STATE_PROCESS_REQUEST_DONE; break; + default: __osm_state_mgr_signal_error( p_mgr, signal ); signal = OSM_SIGNAL_NONE; @@ -2019,18 +2000,21 @@ osm_state_mgr_process( break; } break; + case OSM_SM_STATE_PROCESS_REQUEST_WAIT: switch ( signal ) { case OSM_SIGNAL_NO_PENDING_TRANSACTIONS: p_mgr->state = OSM_SM_STATE_PROCESS_REQUEST_DONE; break; + default: __osm_state_mgr_signal_error( p_mgr, signal ); signal = OSM_SIGNAL_NONE; break; } break; + case OSM_SM_STATE_PROCESS_REQUEST_DONE: switch ( signal ) { @@ -2047,12 +2031,14 @@ osm_state_mgr_process( signal = OSM_SIGNAL_IDLE_TIME_PROCESS; p_mgr->state = OSM_SM_STATE_PROCESS_REQUEST; break; + default: __osm_state_mgr_signal_error( p_mgr, signal ); signal = OSM_SIGNAL_NONE; break; } break; + case OSM_SM_STATE_SWEEP_LIGHT: switch ( signal ) { @@ -2088,10 +2074,10 @@ osm_state_mgr_process( case OSM_SIGNAL_LIGHT_SWEEP_FAIL: case OSM_SIGNAL_CHANGE_DETECTED: /* - * Nothing to do here. One subnet change typcially - * begets another.... + * Nothing to do here. One subnet change typcially + * begets another.... But needs to wait for all transactions to + * complete */ - signal = OSM_SIGNAL_NONE; break; case OSM_SIGNAL_NO_PENDING_TRANSACTIONS: @@ -2117,8 +2103,8 @@ osm_state_mgr_process( { case OSM_SIGNAL_CHANGE_DETECTED: /* - * Nothing to do here. One subnet change typcially - * begets another.... + * Nothing to do here. One subnet change typcially + * begets another.... But needs to wait for all transactions */ signal = OSM_SIGNAL_NONE; break; @@ -2153,19 +2139,18 @@ osm_state_mgr_process( signal = OSM_SIGNAL_NONE; break; } - break; /* * There is no 'OSM_SM_STATE_SWEEP_HEAVY_WAIT' state since we - * know that there outstanding transaction on the wire already... + * know that there are outstanding transactions on the wire already... */ case OSM_SM_STATE_SWEEP_HEAVY_SUBNET: switch ( signal ) { case OSM_SIGNAL_CHANGE_DETECTED: /* - * Nothing to do here. One subnet change typcially + * Nothing to do here. One subnet change typically * begets another.... */ signal = OSM_SIGNAL_NONE; @@ -2175,7 +2160,6 @@ osm_state_mgr_process( p_mgr->state = OSM_SM_STATE_MASTER_OR_HIGHER_SM_DETECTED; break; - case OSM_SIGNAL_NO_PENDING_TRANSACTIONS: __osm_state_mgr_sweep_heavy_done_msg( p_mgr ); @@ -2200,7 +2184,7 @@ osm_state_mgr_process( { /* We are the highest sm - check to see if there is * a remote SM that is in master state. */ - p_remote_sm = __osm_state_mgr_exists_other_master( p_mgr ); + p_remote_sm = __osm_state_mgr_exists_other_master_sm( p_mgr ); if( p_remote_sm != NULL ) { /* There is a remote SM that is master. @@ -2232,7 +2216,19 @@ osm_state_mgr_process( OSM_SM_SIGNAL_DISCOVERY_COMPLETED ); /* the returned signal might be DONE or DONE_PENDING */ - signal = osm_pkey_mgr_process( p_mgr->p_pkey_mgr ); + signal = osm_pkey_mgr_process( p_mgr->p_subn->p_osm ); + + /* the returned signal is always DONE */ + tmp_signal = osm_qos_setup(p_mgr->p_subn->p_osm); + + if (tmp_signal == OSM_SIGNAL_DONE_PENDING) + signal = OSM_SIGNAL_DONE_PENDING; + + /* try to restore SA DB (this should be before lid_mgr + because we may want to disable clients reregistration + when SA DB is restored) */ + osm_sa_db_file_load(p_mgr->p_subn->p_osm); + break; default: @@ -2284,7 +2280,6 @@ osm_state_mgr_process( { case OSM_SIGNAL_NO_PENDING_TRANSACTIONS: case OSM_SIGNAL_DONE: - p_mgr->state = OSM_SM_STATE_SET_SM_UCAST_LID; signal = osm_lid_mgr_process_sm( p_mgr->p_lid_mgr ); break; @@ -2294,7 +2289,6 @@ osm_state_mgr_process( signal = OSM_SIGNAL_NONE; break; } - break; case OSM_SM_STATE_SET_SM_UCAST_LID: @@ -2620,7 +2614,7 @@ osm_state_mgr_process( * The LINK_PORTS state is required since we can not count on * the port state change MADs to succeed. This is an artifact * of the spec defining state change from state X to state X - * as an error. The Hardware then is not required to process + * as an error. The hardware then is not required to process * other parameters provided by the Set(PortInfo) Packet. */ case OSM_SM_STATE_SET_LINK_PORTS: @@ -2818,9 +2812,12 @@ osm_state_mgr_process( p_mgr->p_subn->first_time_master_sweep = FALSE; } - osm_topology_file_create( p_mgr ); + __osm_topology_file_create( p_mgr ); __osm_state_mgr_report( p_mgr ); __osm_state_mgr_up_msg( p_mgr ); + + if( osm_log_is_active(p_mgr->p_log, OSM_LOG_VERBOSE) ) + osm_sa_db_file_dump(p_mgr->p_subn->p_osm); } p_mgr->state = OSM_SM_STATE_PROCESS_REQUEST; signal = OSM_SIGNAL_IDLE_TIME_PROCESS; @@ -2844,20 +2841,19 @@ osm_state_mgr_process( } break; - case OSM_SM_STATE_MASTER_OR_HIGHER_SM_DETECTED: switch ( signal ) { case OSM_SIGNAL_CHANGE_DETECTED: /* - * Nothing to do here. One subnet change typcially + * Nothing to do here. One subnet change typically * begets another.... */ break; case OSM_SIGNAL_MASTER_OR_HIGHER_SM_DETECTED: /* - * If we lost once, we might lose again. Nothing to do. + * If we lost once, we might lose again. Nothing to do. */ break; @@ -2879,7 +2875,6 @@ osm_state_mgr_process( signal = OSM_SIGNAL_NONE; break; - case OSM_SM_STATE_STANDBY: switch ( signal ) { @@ -2893,12 +2888,14 @@ osm_state_mgr_process( __osm_state_mgr_clean_known_lids( p_mgr ); p_mgr->state = OSM_SM_STATE_IDLE; break; + case OSM_SIGNAL_NO_PENDING_TRANSACTIONS: /* * Nothing to do here - need to stay at this state */ signal = OSM_SIGNAL_NONE; break; + default: __osm_state_mgr_signal_error( p_mgr, signal ); signal = OSM_SIGNAL_NONE; @@ -2961,7 +2958,7 @@ osm_state_mgr_process_idle( OSM_LOG_ENTER( p_mgr->p_log, osm_state_mgr_process_idle ); - p_idle_item = cl_zalloc( sizeof( osm_idle_item_t ) ); + p_idle_item = malloc( sizeof( osm_idle_item_t ) ); if( p_idle_item == NULL ) { osm_log( p_mgr->p_log, OSM_LOG_ERROR, @@ -2970,6 +2967,7 @@ osm_state_mgr_process_idle( return IB_ERROR; } + memset( p_idle_item, 0, sizeof( osm_idle_item_t ) ); p_idle_item->pfn_start = pfn_start; p_idle_item->pfn_done = pfn_done; p_idle_item->context1 = context1; @@ -2985,3 +2983,4 @@ osm_state_mgr_process_idle( return IB_SUCCESS; } + diff --git a/trunk/ulp/opensm/user/opensm/osm_state_mgr_ctrl.c b/trunk/ulp/opensm/user/opensm/osm_state_mgr_ctrl.c index 6eba8969..21aed85f 100644 --- a/trunk/ulp/opensm/user/opensm/osm_state_mgr_ctrl.c +++ b/trunk/ulp/opensm/user/opensm/osm_state_mgr_ctrl.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Implementation of osm_state_mgr_ctrl_t. @@ -44,15 +45,11 @@ * $Revision: 1.5 $ */ -/* - Next available error code: 0x1601 -*/ - #if HAVE_CONFIG_H # include #endif /* HAVE_CONFIG_H */ -#include +#include #include #include @@ -74,7 +71,7 @@ void osm_state_mgr_ctrl_construct( IN osm_state_mgr_ctrl_t* const p_ctrl ) { - cl_memclr( p_ctrl, sizeof(*p_ctrl) ); + memset( p_ctrl, 0, sizeof(*p_ctrl) ); p_ctrl->h_disp = CL_DISP_INVALID_HANDLE; } @@ -127,3 +124,4 @@ osm_state_mgr_ctrl_init( return( status ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_subnet.c b/trunk/ulp/opensm/user/opensm/osm_subnet.c index 0d4ed6aa..5d3cb3e1 100644 --- a/trunk/ulp/opensm/user/opensm/osm_subnet.c +++ b/trunk/ulp/opensm/user/opensm/osm_subnet.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -48,17 +48,20 @@ # include #endif /* HAVE_CONFIG_H */ +#include +#include #include #include +#include #include #include #include #include #include +#include #include #include #include -#include /********************************************************************** **********************************************************************/ @@ -66,7 +69,7 @@ void osm_subn_construct( IN osm_subn_t* const p_subn ) { - cl_memclr( p_subn, sizeof(*p_subn) ); + memset( p_subn, 0, sizeof(*p_subn) ); cl_ptr_vector_construct( &p_subn->node_lid_tbl ); cl_ptr_vector_construct( &p_subn->port_lid_tbl ); cl_qmap_init( &p_subn->sw_guid_tbl ); @@ -94,6 +97,7 @@ osm_subn_destroy( osm_port_t *p_port, *p_next_port; osm_switch_t *p_sw, *p_next_sw; osm_remote_sm_t *p_rsm, *p_next_rsm; + osm_prtn_t *p_prtn, *p_next_prtn; osm_mgrp_t *p_mgrp, *p_next_mgrp; osm_infr_t *p_infr, *p_next_infr; @@ -129,7 +133,15 @@ osm_subn_destroy( { p_rsm = p_next_rsm; p_next_rsm = (osm_remote_sm_t*)cl_qmap_next( &p_rsm->map_item ); - cl_free( p_rsm ); + free( p_rsm ); + } + + p_next_prtn = (osm_prtn_t*)cl_qmap_head( &p_subn->prtn_pkey_tbl ); + while( p_next_prtn != (osm_prtn_t*)cl_qmap_end( &p_subn->prtn_pkey_tbl ) ) + { + p_prtn = p_next_prtn; + p_next_prtn = (osm_prtn_t*)cl_qmap_next( &p_prtn->map_item ); + osm_prtn_delete( &p_prtn ); } p_next_mgrp = (osm_mgrp_t*)cl_qmap_head( &p_subn->mgrp_mlid_tbl ); @@ -164,10 +176,13 @@ osm_subn_destroy( ib_api_status_t osm_subn_init( IN osm_subn_t* const p_subn, + IN osm_opensm_t * const p_osm, IN const osm_subn_opt_t* const p_opt ) { cl_status_t status; + p_subn->p_osm = p_osm; + status = cl_ptr_vector_init( &p_subn->node_lid_tbl, OSM_SUBNET_VECTOR_MIN_SIZE, OSM_SUBNET_VECTOR_GROW_SIZE ); @@ -203,10 +218,10 @@ osm_subn_init( p_subn->min_ca_mtu = IB_MAX_MTU; p_subn->min_ca_rate = IB_MAX_RATE; - /* note that insert and remove are part of the port_profile thing. */ + /* note that insert and remove are part of the port_profile thing */ cl_map_init(&(p_subn->opt.port_prof_ignore_guids), 10); - /* ignore_existing_lfts follows the reassign_lfts on first sweep */ + /* ignore_existing_lfts follows reassign_lfts on first sweep */ p_subn->ignore_existing_lfts = p_subn->opt.reassign_lfts; /* we assume master by default - so we only need to set it true if STANDBY */ @@ -217,16 +232,24 @@ osm_subn_init( /********************************************************************** **********************************************************************/ -ib_gid_t +ib_api_status_t osm_get_gid_by_mad_addr( IN osm_log_t* p_log, IN const osm_subn_t *p_subn, - IN const osm_mad_addr_t *p_mad_addr ) + IN const osm_mad_addr_t *p_mad_addr, + OUT ib_gid_t *p_gid) { const cl_ptr_vector_t* p_tbl; const osm_port_t* p_port = NULL; const osm_physp_t* p_physp = NULL; - ib_gid_t request_gid; + + if ( p_gid == NULL ) + { + osm_log( p_log, OSM_LOG_ERROR, + "osm_get_gid_by_mad_addr: ERR 7505: " + "Provided output GID is NULL\n"); + return(IB_INVALID_PARAMETER); + } /* Find the port gid of the request in the subnet */ p_tbl = &p_subn->port_lid_tbl; @@ -237,21 +260,31 @@ osm_get_gid_by_mad_addr( cl_ntoh16(p_mad_addr->dest_lid)) { p_port = cl_ptr_vector_get( p_tbl, cl_ntoh16(p_mad_addr->dest_lid) ); + if ( p_port == NULL ) + { + osm_log( p_log, OSM_LOG_DEBUG, + "osm_get_gid_by_mad_addr: " + "Did not find any port with LID: 0x%X\n", + cl_ntoh16(p_mad_addr->dest_lid) + ); + return(IB_INVALID_PARAMETER); + } p_physp = osm_port_get_phys_ptr( p_port, p_port->default_port_num); - request_gid.unicast.interface_id = p_physp->port_guid; - request_gid.unicast.prefix = p_subn->opt.subnet_prefix; + p_gid->unicast.interface_id = p_physp->port_guid; + p_gid->unicast.prefix = p_subn->opt.subnet_prefix; } else { /* The dest_lid is not in the subnet table - this is an error */ osm_log( p_log, OSM_LOG_ERROR, - "osm_get_gid_by_mad_addr: ERR 7501 " - "Lid is out of range: 0x%X\n", + "osm_get_gid_by_mad_addr: ERR 7501: " + "LID is out of range: 0x%X\n", cl_ntoh16(p_mad_addr->dest_lid) ); + return(IB_INVALID_PARAMETER); } - return request_gid; + return( IB_SUCCESS ); } /********************************************************************** @@ -279,7 +312,7 @@ osm_get_physp_by_mad_addr( { /* The port is not in the port_lid table - this is an error */ osm_log( p_log, OSM_LOG_ERROR, - "osm_get_physp_by_mad_addr: ERR 7502 " + "osm_get_physp_by_mad_addr: ERR 7502: " "Cannot locate port object by lid: 0x%X\n", cl_ntoh16(p_mad_addr->dest_lid) ); @@ -292,12 +325,10 @@ osm_get_physp_by_mad_addr( { /* The dest_lid is not in the subnet table - this is an error */ osm_log( p_log, OSM_LOG_ERROR, - "osm_get_physp_by_mad_addr: ERR 7503 " + "osm_get_physp_by_mad_addr: ERR 7503: " "Lid is out of range: 0x%X\n", cl_ntoh16(p_mad_addr->dest_lid) ); - - goto Exit; } Exit: @@ -330,14 +361,12 @@ osm_get_port_by_mad_addr( { /* The dest_lid is not in the subnet table - this is an error */ osm_log( p_log, OSM_LOG_ERROR, - "osm_get_port_by_mad_addr: ERR 7504 " + "osm_get_port_by_mad_addr: ERR 7504: " "Lid is out of range: 0x%X\n", cl_ntoh16(p_mad_addr->dest_lid) ); - goto Exit; } - Exit: return p_port; } @@ -349,6 +378,7 @@ osm_get_switch_by_guid( IN uint64_t guid) { osm_switch_t *p_switch; + p_switch = (osm_switch_t*)cl_qmap_get( &(p_subn->sw_guid_tbl), guid ); if( p_switch == (osm_switch_t*)cl_qmap_end( &(p_subn->sw_guid_tbl)) ) p_switch = NULL; @@ -363,6 +393,7 @@ osm_get_node_by_guid( IN uint64_t guid) { osm_node_t *p_node; + p_node = (osm_node_t*)cl_qmap_get( &(p_subn->node_guid_tbl), guid ); if( p_node == (osm_node_t*)cl_qmap_end( &(p_subn->node_guid_tbl)) ) p_node = NULL; @@ -377,19 +408,33 @@ osm_get_port_by_guid( IN uint64_t guid) { osm_port_t *p_port; + p_port = (osm_port_t*)cl_qmap_get( &(p_subn->port_guid_tbl), guid ); if( p_port == (osm_port_t*)cl_qmap_end( &(p_subn->port_guid_tbl)) ) p_port = NULL; return p_port; } +/********************************************************************** + **********************************************************************/ +static void +subn_set_default_qos_options( + IN osm_qos_options_t *opt) +{ + opt->max_vls = 15; + opt->high_limit = 0; + opt->vlarb_high = "0:4,1:0,2:0,3:0,4:0,5:0,6:0,7:0,8:0,9:0,10:0,11:0,12:0,13:0,14:0"; + opt->vlarb_low = "0:0,1:4,2:4,3:4,4:4,5:4,6:4,7:4,8:4,9:4,10:4,11:4,12:4,13:4,14:4"; + opt->sl2vl = "0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,7"; +} + /********************************************************************** **********************************************************************/ void osm_subn_set_default_opt( IN osm_subn_opt_t* const p_opt ) { - cl_memclr(p_opt, sizeof(osm_subn_opt_t)); + memset(p_opt, 0, sizeof(osm_subn_opt_t)); p_opt->guid = 0; p_opt->m_key = OSM_DEFAULT_M_KEY; p_opt->sm_key = OSM_DEFAULT_SM_KEY; @@ -403,7 +448,9 @@ osm_subn_set_default_opt( p_opt->max_msg_fifo_timeout = 50*OSM_DEFAULT_TRANS_TIMEOUT_MILLISEC; p_opt->sm_priority = OSM_DEFAULT_SM_PRIORITY; p_opt->lmc = OSM_DEFAULT_LMC; + p_opt->lmc_esp0 = FALSE; p_opt->max_op_vls = OSM_DEFAULT_MAX_OP_VLS; + p_opt->force_link_speed = 0; p_opt->reassign_lids = FALSE; p_opt->reassign_lfts = TRUE; p_opt->ignore_other_sm = FALSE; @@ -413,35 +460,48 @@ osm_subn_set_default_opt( p_opt->force_log_flush = FALSE; p_opt->subnet_timeout = OSM_DEFAULT_SUBNET_TIMEOUT; p_opt->packet_life_time = OSM_DEFAULT_SWITCH_PACKET_LIFE; + p_opt->vl_stall_count = OSM_DEFAULT_VL_STALL_COUNT; + p_opt->leaf_vl_stall_count = OSM_DEFAULT_LEAF_VL_STALL_COUNT; p_opt->head_of_queue_lifetime = OSM_DEFAULT_HEAD_OF_QUEUE_LIFE; p_opt->leaf_head_of_queue_lifetime = OSM_DEFAULT_LEAF_HEAD_OF_QUEUE_LIFE; p_opt->local_phy_errors_threshold = OSM_DEFAULT_ERROR_THRESHOLD; p_opt->overrun_errors_threshold = OSM_DEFAULT_ERROR_THRESHOLD; p_opt->sminfo_polling_timeout = OSM_SM_DEFAULT_POLLING_TIMEOUT_MILLISECS; - p_opt->polling_retry_number = 4; + p_opt->polling_retry_number = OSM_SM_DEFAULT_POLLING_RETRY_NUMBER; p_opt->force_heavy_sweep = FALSE; p_opt->log_flags = 0; p_opt->honor_guid2lid_file = FALSE; p_opt->dump_files_dir = getenv("OSM_TMP_DIR"); - if (!p_opt->dump_files_dir) + if (!p_opt->dump_files_dir || !(*p_opt->dump_files_dir)) p_opt->dump_files_dir = OSM_DEFAULT_TMP_DIR; p_opt->log_file = OSM_DEFAULT_LOG_FILE; + p_opt->log_max_size = 0; + p_opt->partition_config_file = OSM_DEFAULT_PARTITION_CONFIG_FILE; + p_opt->no_partition_enforcement = FALSE; + p_opt->no_qos = TRUE; p_opt->accum_log_file = TRUE; p_opt->port_profile_switch_nodes = FALSE; - p_opt->max_port_profile = 0xffffffff; p_opt->pfn_ui_pre_lid_assign = NULL; p_opt->ui_pre_lid_assign_ctx = NULL; - p_opt->pfn_ui_ucast_fdb_assign = NULL; - p_opt->ui_ucast_fdb_assign_ctx = NULL; p_opt->pfn_ui_mcast_fdb_assign = NULL; p_opt->ui_mcast_fdb_assign_ctx = NULL; p_opt->sweep_on_trap = TRUE; p_opt->testability_mode = OSM_TEST_MODE_NONE; - p_opt->updn_activate = FALSE; + p_opt->routing_engine_name = NULL; + p_opt->lid_matrix_dump_file = NULL; + p_opt->ucast_dump_file = NULL; p_opt->updn_guid_file = NULL; + p_opt->sa_db_file = NULL; p_opt->exit_on_fatal = TRUE; + p_opt->enable_quirks = FALSE; + p_opt->no_clients_rereg = FALSE; + subn_set_default_qos_options(&p_opt->qos_options); + subn_set_default_qos_options(&p_opt->qos_ca_options); + subn_set_default_qos_options(&p_opt->qos_sw0_options); + subn_set_default_qos_options(&p_opt->qos_swe_options); + subn_set_default_qos_options(&p_opt->qos_rtr_options); } /********************************************************************** @@ -589,19 +649,119 @@ __osm_subn_opts_unpack_charp( { if (!strcmp(p_req_key, p_key) && p_val_str) { - if (strcmp(p_val_str, *p_val)) + if ((*p_val == NULL) || strcmp(p_val_str, *p_val)) { char buff[128]; sprintf(buff, " Using Cached Option:%s = %s\n", p_key, p_val_str); printf(buff); cl_log_event("OpenSM", LOG_INFO, buff, NULL, 0); - *p_val = (char *)cl_malloc( strlen(p_val_str) +1 ); + + /* + Ignore the possible memory leak here; + the pointer may be to a static default. + */ + *p_val = (char *)malloc( strlen(p_val_str) +1 ); strcpy( *p_val, p_val_str); } } } +/********************************************************************** + **********************************************************************/ +static void +subn_parse_qos_options( + IN const char *prefix, + IN char *p_key, + IN char *p_val_str, + IN osm_qos_options_t *opt) +{ + char name[256]; + + snprintf(name, sizeof(name), "%s_max_vls", prefix); + __osm_subn_opts_unpack_uint32(name, p_key, p_val_str, &opt->max_vls); + snprintf(name, sizeof(name), "%s_high_limit", prefix); + __osm_subn_opts_unpack_uint32(name, p_key, p_val_str, &opt->high_limit); + snprintf(name, sizeof(name), "%s_vlarb_high", prefix); + __osm_subn_opts_unpack_charp(name, p_key, p_val_str, &opt->vlarb_high); + snprintf(name, sizeof(name), "%s_vlarb_low", prefix); + __osm_subn_opts_unpack_charp(name, p_key, p_val_str, &opt->vlarb_low); + snprintf(name, sizeof(name), "%s_sl2vl", prefix); + __osm_subn_opts_unpack_charp(name, p_key, p_val_str, &opt->sl2vl); +} + +static int +subn_dump_qos_options( + FILE *file, + const char *set_name, + const char *prefix, + osm_qos_options_t *opt) +{ + return fprintf(file, "# %s\n" + "%s_max_vls %u\n" + "%s_high_limit %u\n" + "%s_vlarb_high %s\n" + "%s_vlarb_low %s\n" + "%s_sl2vl %s\n", + set_name, + prefix, opt->max_vls, + prefix, opt->high_limit, + prefix, opt->vlarb_high, + prefix, opt->vlarb_low, + prefix, opt->sl2vl); +} + +/********************************************************************** + **********************************************************************/ +void +osm_subn_rescan_conf_file( + IN osm_subn_opt_t* const p_opts ) +{ + char *p_cache_dir = getenv("OSM_CACHE_DIR"); + char file_name[256]; + FILE *opts_file; + char line[1024]; + char *p_key, *p_val ,*p_last; + + /* try to open the options file from the cache dir */ + if (!p_cache_dir || !(*p_cache_dir)) + p_cache_dir = OSM_DEFAULT_CACHE_DIR; + + strcpy(file_name, p_cache_dir); + strcat(file_name, "opensm.opts"); + + opts_file = fopen(file_name, "r"); + if (!opts_file) + return; + + while (fgets(line, 1023, opts_file) != NULL) + { + /* get the first token */ + p_key = strtok_r(line, " \t\n", &p_last); + if (p_key) + { + p_val = strtok_r(NULL, " \t\n", &p_last); + + subn_parse_qos_options("qos", + p_key, p_val, &p_opts->qos_options); + + subn_parse_qos_options("qos_ca", + p_key, p_val, &p_opts->qos_ca_options); + + subn_parse_qos_options("qos_sw0", + p_key, p_val, &p_opts->qos_sw0_options); + + subn_parse_qos_options("qos_swe", + p_key, p_val, &p_opts->qos_swe_options); + + subn_parse_qos_options("qos_rtr", + p_key, p_val, &p_opts->qos_rtr_options); + + } + } + fclose(opts_file); +} + /********************************************************************** **********************************************************************/ void @@ -615,10 +775,11 @@ osm_subn_parse_conf_file( char *p_key, *p_val ,*p_last; /* try to open the options file from the cache dir */ - if (! p_cache_dir) p_cache_dir = OSM_DEFAULT_CACHE_DIR; + if (!p_cache_dir || !(*p_cache_dir)) + p_cache_dir = OSM_DEFAULT_CACHE_DIR; strcpy(file_name, p_cache_dir); - strcat(file_name,"opensm.opts"); + strcat(file_name, "opensm.opts"); opts_file = fopen(file_name, "r"); if (!opts_file) return; @@ -630,8 +791,8 @@ osm_subn_parse_conf_file( if (p_key) { p_val = strtok_r(NULL, " \t\n", &p_last); - - __osm_subn_opts_unpack_net64( + + __osm_subn_opts_unpack_net64( "guid", p_key, p_val, &p_opts->guid); __osm_subn_opts_unpack_net64( @@ -642,7 +803,7 @@ osm_subn_parse_conf_file( __osm_subn_opts_unpack_net64( "subnet_prefix", - p_key, p_val, &p_opts->subnet_prefix ); + p_key, p_val, &p_opts->subnet_prefix); __osm_subn_opts_unpack_net16( "m_key_lease_period", @@ -672,10 +833,18 @@ osm_subn_parse_conf_file( "lmc", p_key, p_val, &p_opts->lmc); + __osm_subn_opts_unpack_boolean( + "lmc_esp0", + p_key, p_val, &p_opts->lmc_esp0); + __osm_subn_opts_unpack_uint8( "max_op_vls", p_key, p_val, &p_opts->max_op_vls); + __osm_subn_opts_unpack_uint8( + "force_link_speed", + p_key, p_val, &p_opts->force_link_speed); + __osm_subn_opts_unpack_boolean( "reassign_lids", p_key, p_val, &p_opts->reassign_lids); @@ -712,6 +881,14 @@ osm_subn_parse_conf_file( "packet_life_time", p_key, p_val, &p_opts->packet_life_time); + __osm_subn_opts_unpack_uint8( + "vl_stall_count", + p_key, p_val, &p_opts->vl_stall_count); + + __osm_subn_opts_unpack_uint8( + "leaf_vl_stall_count", + p_key, p_val, &p_opts->leaf_vl_stall_count); + __osm_subn_opts_unpack_uint8( "head_of_queue_lifetime", p_key, p_val, &p_opts->head_of_queue_lifetime); @@ -752,25 +929,53 @@ osm_subn_parse_conf_file( "sweep_on_trap", p_key, p_val, &p_opts->sweep_on_trap); - __osm_subn_opts_unpack_boolean( - "updn_activate", - p_key, p_val, &p_opts->updn_activate); + __osm_subn_opts_unpack_charp( + "routing_engine", + p_key, p_val, &p_opts->routing_engine_name); __osm_subn_opts_unpack_charp( - "log_file" , p_key, p_val, &p_opts->log_file); + "log_file", p_key, p_val, &p_opts->log_file); + + __osm_subn_opts_unpack_uint32( + "log_max_size", + p_key, p_val, (uint32_t *)&p_opts->log_max_size); + + __osm_subn_opts_unpack_charp( + "partition_config_file", + p_key, p_val, &p_opts->partition_config_file); + + __osm_subn_opts_unpack_boolean( + "no_partition_enforcement", + p_key, p_val, &p_opts->no_partition_enforcement); + + __osm_subn_opts_unpack_boolean( + "no_qos", + p_key, p_val, &p_opts->no_qos); __osm_subn_opts_unpack_boolean( "accum_log_file", p_key, p_val, &p_opts->accum_log_file); __osm_subn_opts_unpack_charp( - "dump_files_dir" , + "dump_files_dir", p_key, p_val, &p_opts->dump_files_dir); + __osm_subn_opts_unpack_charp( + "lid_matrix_dump_file", + p_key, p_val, &p_opts->lid_matrix_dump_file); + + __osm_subn_opts_unpack_charp( + "ucast_dump_file", + p_key, p_val, &p_opts->ucast_dump_file); + __osm_subn_opts_unpack_charp( - "updn_guid_file" , + "updn_guid_file", p_key, p_val, &p_opts->updn_guid_file); + __osm_subn_opts_unpack_charp( + "sa_db_file", + p_key, p_val, &p_opts->sa_db_file); + __osm_subn_opts_unpack_boolean( "exit_on_fatal", p_key, p_val, &p_opts->exit_on_fatal); @@ -779,6 +984,25 @@ osm_subn_parse_conf_file( "honor_guid2lid_file", p_key, p_val, &p_opts->honor_guid2lid_file); + subn_parse_qos_options("qos", + p_key, p_val, &p_opts->qos_options); + + subn_parse_qos_options("qos_ca", + p_key, p_val, &p_opts->qos_ca_options); + + subn_parse_qos_options("qos_sw0", + p_key, p_val, &p_opts->qos_sw0_options); + + subn_parse_qos_options("qos_swe", + p_key, p_val, &p_opts->qos_swe_options); + + subn_parse_qos_options("qos_rtr", + p_key, p_val, &p_opts->qos_rtr_options); + + __osm_subn_opts_unpack_boolean( + "enable_quirks", + p_key, p_val, &p_opts->enable_quirks); + } } fclose(opts_file); @@ -795,10 +1019,11 @@ osm_subn_write_conf_file( FILE *opts_file; /* try to open the options file from the cache dir */ - if (! p_cache_dir) p_cache_dir = OSM_DEFAULT_CACHE_DIR; + if (!p_cache_dir || !(*p_cache_dir)) + p_cache_dir = OSM_DEFAULT_CACHE_DIR; strcpy(file_name, p_cache_dir); - strcat(file_name,"opensm.opts"); + strcat(file_name, "opensm.opts"); opts_file = fopen(file_name, "w"); if (!opts_file) return; @@ -806,9 +1031,9 @@ osm_subn_write_conf_file( fprintf( opts_file, "#\n# DEVICE ATTRIBUTES OPTIONS\n#\n" - "# The port GUID on which the OpenSM is running.\n" + "# The port GUID on which the OpenSM is running\n" "guid 0x%016" PRIx64 "\n\n" - "# M_Key value sent to all ports qualifing all Set(PortInfo).\n" + "# M_Key value sent to all ports qualifying all Set(PortInfo)\n" "m_key 0x%016" PRIx64 "\n\n" "# The lease period used for the M_Key on this subnet in [msec]\n" "m_key_lease_period %u\n\n" @@ -818,22 +1043,38 @@ osm_subn_write_conf_file( "subnet_prefix 0x%016" PRIx64 "\n\n" "# The LMC value used on this subnet\n" "lmc %u\n\n" + "# lmc_esp0 determines whether LMC value used on subnet is used for\n" + "#enhanced switch port 0. If TRUE, LMC value for subnet is used for\n" + "#ESP0. Otherwise, LMC value for ESP0s is 0.\n" + "lmc_esp0 %s\n\n" "# The code of maximal time a packet can live in a switch\n" - "# The actual time is 4.096usec * 2^\n" + "# The actual time is 4.096usec * 2^\n" "# The value 0x14 disables this mechanism\n" "packet_life_time 0x%02x\n\n" + "# The number of sequential packets dropped that cause the port\n" + "# to enter the VLStalled state. The result of setting this value to\n" + "# zero is undefined.\n" + "vl_stall_count 0x%02x\n\n" + "# The number of sequential packets dropped that cause the port\n" + "# to enter the VLStalled state. This value is for switch ports\n" + "# driving a CA or router port. The result of setting this value\n" + "# to zero is undefined.\n" + "leaf_vl_stall_count 0x%02x\n\n" "# The code of maximal time a packet can wait at the head of\n" "# transmission queue. \n" "# The actual time is 4.096usec * 2^\n" "# The value 0x14 disables this mechanism\n" "head_of_queue_lifetime 0x%02x\n\n" "# The maximal time a packet can wait at the head of queue on \n" - "# switch port connected to a HCA\n" + "# switch port connected to a CA or router port\n" "leaf_head_of_queue_lifetime 0x%02x\n\n" "# Limit the maximal operational VLs\n" "max_op_vls %u\n\n" + "# Force switch links which are more than SDR capable to \n" + "# operate at SDR speed\n\n" + "force_link_speed %u\n\n" "# The subnet_timeout code that will be set for all the ports\n" - "# The actual timeout is 4.096usec * 2^\n" + "# The actual timeout is 4.096usec * 2^\n" "subnet_timeout %u\n\n" "# Threshold of local phy errors for sending Trap 129\n" "local_phy_errors_threshold 0x%02x\n\n" @@ -845,31 +1086,45 @@ osm_subn_write_conf_file( cl_ntoh64(p_opts->sm_key), cl_ntoh64(p_opts->subnet_prefix), p_opts->lmc, + p_opts->lmc_esp0 ? "TRUE" : "FALSE", p_opts->packet_life_time, + p_opts->vl_stall_count, + p_opts->leaf_vl_stall_count, p_opts->head_of_queue_lifetime, p_opts->leaf_head_of_queue_lifetime, p_opts->max_op_vls, + p_opts->force_link_speed, p_opts->subnet_timeout, p_opts->local_phy_errors_threshold, p_opts->overrun_errors_threshold ); + fprintf( + opts_file, + "#\n# PARTITIONING OPTIONS\n#\n" + "# Partition configuration file to be used\n" + "partition_config_file %s\n\n" + "# Disable partition enforcement by switches\n" + "no_partition_enforcement %s\n\n", + p_opts->partition_config_file, + p_opts->no_partition_enforcement ? "TRUE" : "FALSE"); + fprintf( opts_file, "#\n# SWEEP OPTIONS\n#\n" "# The number of seconds between subnet sweeps (0 disables it)\n" "sweep_interval %u\n\n" - "# If TRUE cause all lids to be re-assigned\n" + "# If TRUE cause all lids to be reassigned\n" "reassign_lids %s\n\n" "# If TRUE ignore existing LFT entries on first sweep (default).\n" "# Otherwise only non minimal hop cases are modified.\n" "# NOTE: A standby SM clears its first sweep flag - since the\n" "# master SM already sweeps...\n" "reassign_lfts %s\n\n" - "# If true forces every sweep to be a heavy sweep\n" + "# If TRUE forces every sweep to be a heavy sweep\n" "force_heavy_sweep %s\n\n" - "# If true every trap will cause a heavy sweep.\n" - "# NOTE: successive same traps (>10) are supressed\n" + "# If TRUE every trap will cause a heavy sweep.\n" + "# NOTE: successive identical traps (>10) are suppressed\n" "sweep_on_trap %s\n\n", p_opts->sweep_interval, p_opts->reassign_lids ? "TRUE" : "FALSE", @@ -881,32 +1136,49 @@ osm_subn_write_conf_file( fprintf( opts_file, "#\n# ROUTING OPTIONS\n#\n" - "# If true do not count switches as link subscriptions\n" - "port_profile_switch_nodes %s\n\n" - "# Activate the Up/Down routing algorithm\n" - "updn_activate %s\n\n", - p_opts->port_profile_switch_nodes ? "TRUE" : "FALSE", - p_opts->updn_activate ? "TRUE" : "FALSE" - ); + "# If TRUE count switches as link subscriptions\n" + "port_profile_switch_nodes %s\n\n", + p_opts->port_profile_switch_nodes ? "TRUE" : "FALSE"); + + if (p_opts->routing_engine_name) + fprintf( opts_file, + "# Routing engine\n" + "routing_engine %s\n\n", + p_opts->routing_engine_name); + if (p_opts->lid_matrix_dump_file) + fprintf( opts_file, + "# Lid matrix dump file name\n" + "lid_matrix_dump_file %s\n\n", + p_opts->lid_matrix_dump_file); + if (p_opts->ucast_dump_file) + fprintf( opts_file, + "# Ucast dump file name\n" + "ucast_dump_file %s\n\n", + p_opts->ucast_dump_file); if (p_opts->updn_guid_file) fprintf( opts_file, "# The file holding the Up/Down root node guids\n" "# One guid in each line\n" "updn_guid_file %s\n\n", p_opts->updn_guid_file); + if (p_opts->sa_db_file) + fprintf( opts_file, + "# SA database file name\n" + "sa_db_file %s\n\n", + p_opts->sa_db_file); fprintf( opts_file, - "#\n# HANDOVER - MULTIPLE SM's OPTIONS\n#\n" + "#\n# HANDOVER - MULTIPLE SMs OPTIONS\n#\n" "# SM priority used for deciding who is the master\n" "sm_priority %u\n\n" - "# If TRUE other SM's on the subnet should be ignored\n" + "# If TRUE other SMs on the subnet should be ignored\n" "ignore_other_sm %s\n\n" - "# Timeout in [sec] between two polls of active master SM\n" + "# Timeout in [msec] between two polls of active master SM\n" "sminfo_polling_timeout %u\n\n" "# Number of failing polls of remote SM that declares it dead\n" - "polling_retry_number %u\n" - "# If true honor the guid2lid file when coming out of standby\n" + "polling_retry_number %u\n\n" + "# If TRUE honor the guid2lid file when coming out of standby\n" "# state, if such file exists and is valid\n" "honor_guid2lid_file %s\n\n", p_opts->sm_priority, @@ -924,8 +1196,8 @@ osm_subn_write_conf_file( "# The time taken to a transaction to finish in [msec]\n" "transaction_timeout %u\n\n" "# Maximal time in [msec] a message can stay in the incoming message queue.\n" - "# If there is more then one message in the queue and the last message\n" - "# stayed in the queue more then this value any SA request will be \n" + "# If there is more than one message in the queue and the last message\n" + "# stayed in the queue more than this value any SA request will be \n" "# immediately returned with a BUSY status.\n" "max_msg_fifo_timeout %u\n\n" "# Use a single thread for handling SA queries\n" @@ -944,11 +1216,16 @@ osm_subn_write_conf_file( "# Force flush of the log file after each log message\n" "force_log_flush %s\n\n" "# Log file to be used\n" - "log_file %s\n\n" + "log_file %s\n\n" + "# Limit the size of the log file. If overrun, log is restarted\n" + "log_max_size %lu\n\n" + "# If TRUE will accumulate the log over multiple OpenSM sessions\n" "accum_log_file %s\n\n" "# The directory to hold the file OpenSM dumps\n" "dump_files_dir %s\n\n" - "# If TRUE if OpenSM should disable multicast support\n" + "# If TRUE enables new high risk options and hardware specific quirks\n" + "enable_quirks %s\n\n" + "# If TRUE OpenSM should disable multicast support\n" "no_multicast_option %s\n\n" "# No multicast routing is performed if TRUE\n" "disable_multicast %s\n\n" @@ -957,13 +1234,37 @@ osm_subn_write_conf_file( p_opts->log_flags, p_opts->force_log_flush ? "TRUE" : "FALSE", p_opts->log_file, + p_opts->log_max_size, p_opts->accum_log_file ? "TRUE" : "FALSE", p_opts->dump_files_dir, + p_opts->enable_quirks ? "TRUE" : "FALSE", p_opts->no_multicast_option ? "TRUE" : "FALSE", p_opts->disable_multicast ? "TRUE" : "FALSE", p_opts->exit_on_fatal ? "TRUE" : "FALSE" ); + fprintf( + opts_file, + "#\n# QoS OPTIONS\n#\n" + "# Disable QoS setup\n" + "no_qos %s\n\n", + p_opts->no_qos ? "TRUE" : "FALSE"); + + subn_dump_qos_options(opts_file, + "QoS default options", "qos", &p_opts->qos_options); + fprintf(opts_file, "\n"); + subn_dump_qos_options(opts_file, + "QoS CA options", "qos_ca", &p_opts->qos_ca_options); + fprintf(opts_file, "\n"); + subn_dump_qos_options(opts_file, + "QoS Switch Port 0 options", "qos_sw0", &p_opts->qos_sw0_options); + fprintf(opts_file, "\n"); + subn_dump_qos_options(opts_file, + "QoS Switch external ports options", "qos_swe", &p_opts->qos_swe_options); + fprintf(opts_file, "\n"); + subn_dump_qos_options(opts_file, + "QoS Router ports options", "qos_rtr", &p_opts->qos_rtr_options); + /* optional string attributes ... */ fclose(opts_file); diff --git a/trunk/ulp/opensm/user/opensm/osm_sw_info_rcv.c b/trunk/ulp/opensm/user/opensm/osm_sw_info_rcv.c index 5c8d2d20..9fbdb145 100644 --- a/trunk/ulp/opensm/user/opensm/osm_sw_info_rcv.c +++ b/trunk/ulp/opensm/user/opensm/osm_sw_info_rcv.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -48,8 +48,8 @@ # include #endif /* HAVE_CONFIG_H */ +#include #include -#include #include #include #include @@ -59,50 +59,10 @@ #include #include -/********************************************************************** - **********************************************************************/ -void -__osm_si_rcv_clear_sc_bit( - IN const osm_si_rcv_t* const p_rcv, - IN osm_node_t* const p_node, - IN ib_switch_info_t* const p_si ) -{ - uint8_t payload[IB_SMP_DATA_SIZE]; - ib_api_status_t status; - osm_madw_context_t context; - OSM_LOG_ENTER( p_rcv->p_log, __osm_si_rcv_clear_sc_bit ); - - context.si_context.node_guid = osm_node_get_node_guid( p_node ); - context.si_context.set_method = TRUE; - context.si_context.light_sweep = FALSE; - - cl_memcpy( payload, p_si, IB_SMP_DATA_SIZE ); - - status = osm_req_set( p_rcv->p_req, - osm_node_get_any_dr_path_ptr( p_node ), - payload, - sizeof(payload), - IB_MAD_ATTR_SWITCH_INFO, - 0, - CL_DISP_MSGID_NONE, - &context ); - - if( status != IB_SUCCESS ) - { - osm_log( p_rcv->p_log, OSM_LOG_ERROR, - "__osm_si_rcv_clear_sc_bit: ERR 3601: " - "Unable to clear state change bit for switch " - "with GUID = 0x%" PRIx64 "\n", - cl_ntoh64( osm_node_get_node_guid( p_node ) ) ); - } - - OSM_LOG_EXIT( p_rcv->p_log ); -} - /********************************************************************** The plock must be held before calling this function. **********************************************************************/ -void +static void __osm_si_rcv_get_port_info( IN const osm_si_rcv_t* const p_rcv, IN osm_switch_t* const p_sw, @@ -144,6 +104,7 @@ __osm_si_rcv_get_port_info( context.pi_context.update_master_sm_base_lid = FALSE; context.pi_context.ignore_errors = FALSE; context.pi_context.light_sweep = FALSE; + context.pi_context.active_transition = FALSE; num_ports = osm_node_get_num_physp( p_node ); osm_dr_path_init( &dr_path, @@ -175,7 +136,7 @@ __osm_si_rcv_get_port_info( /********************************************************************** The plock must be held before calling this function. **********************************************************************/ -void +static void __osm_si_rcv_get_fwd_tbl( IN const osm_si_rcv_t* const p_rcv, IN osm_switch_t* const p_sw ) @@ -236,10 +197,11 @@ __osm_si_rcv_get_fwd_tbl( OSM_LOG_EXIT( p_rcv->p_log ); } +#if 0 /********************************************************************** The plock must be held before calling this function. **********************************************************************/ -void +static void __osm_si_rcv_get_mcast_fwd_tbl( IN const osm_si_rcv_t* const p_rcv, IN osm_switch_t* const p_sw ) @@ -344,11 +306,12 @@ __osm_si_rcv_get_mcast_fwd_tbl( Exit: OSM_LOG_EXIT( p_rcv->p_log ); } +#endif /********************************************************************** Lock must be held on entry to this function. **********************************************************************/ -void +static void __osm_si_rcv_process_new( IN const osm_si_rcv_t* const p_rcv, IN osm_node_t* const p_node, @@ -407,7 +370,8 @@ __osm_si_rcv_process_new( } p_check = (osm_switch_t*)cl_qmap_insert( p_sw_guid_tbl, - osm_node_get_node_guid( p_node ), &p_sw->map_item ); + osm_node_get_node_guid( p_node ), + &p_sw->map_item ); if( p_check != p_sw ) { @@ -421,6 +385,8 @@ __osm_si_rcv_process_new( goto Exit; } + p_node->sw = p_sw; + /* Update the switch info according to the info we just received. @@ -459,13 +425,13 @@ __osm_si_rcv_process_new( Return 1 if the caller is expected to send a change_detected event. this can not be done internally as the event needs the lock... **********************************************************************/ -boolean_t +static boolean_t __osm_si_rcv_process_existing( IN const osm_si_rcv_t* const p_rcv, IN osm_node_t* const p_node, - IN osm_switch_t* const p_sw, IN const osm_madw_t* const p_madw ) { + osm_switch_t *p_sw = p_node->sw; ib_switch_info_t *p_si; osm_si_context_t *p_si_context; ib_smp_t *p_smp; @@ -473,8 +439,6 @@ __osm_si_rcv_process_existing( OSM_LOG_ENTER( p_rcv->p_log, __osm_si_rcv_process_existing ); - CL_ASSERT( p_node ); - CL_ASSERT( p_sw ); CL_ASSERT( p_madw ); p_smp = osm_madw_get_smp_ptr( p_madw ); @@ -570,7 +534,7 @@ void osm_si_rcv_construct( IN osm_si_rcv_t* const p_rcv ) { - cl_memclr( p_rcv, sizeof(*p_rcv) ); + memset( p_rcv, 0, sizeof(*p_rcv) ); } /********************************************************************** @@ -620,11 +584,9 @@ osm_si_rcv_process( IN osm_madw_t* const p_madw ) { cl_qmap_t *p_node_guid_tbl; - cl_qmap_t *p_sw_guid_tbl; ib_switch_info_t *p_si; ib_smp_t *p_smp; osm_node_t *p_node; - osm_switch_t *p_sw; ib_net64_t node_guid; osm_si_context_t *p_context; @@ -635,7 +597,6 @@ osm_si_rcv_process( CL_ASSERT( p_madw ); p_node_guid_tbl = &p_rcv->p_subn->node_guid_tbl; - p_sw_guid_tbl = &p_rcv->p_subn->sw_guid_tbl; p_smp = osm_madw_get_smp_ptr( p_madw ); p_si = (ib_switch_info_t*)ib_smp_get_payload_ptr( p_smp ); @@ -651,8 +612,8 @@ osm_si_rcv_process( { osm_log( p_rcv->p_log, OSM_LOG_DEBUG, "osm_si_rcv_process: " - "Switch GUID = 0x%016" PRIx64 - ", TID = 0x%" PRIx64 "\n", + "Switch GUID 0x%016" PRIx64 + ", TID 0x%" PRIx64 "\n", cl_ntoh64( node_guid ), cl_ntoh64( p_smp->trans_id ) ); } @@ -665,7 +626,7 @@ osm_si_rcv_process( osm_log( p_rcv->p_log, OSM_LOG_ERROR, "osm_si_rcv_process: ERR 3606: " "SwitchInfo received for nonexistent node " - "with GUID = 0x%" PRIx64 "\n", + "with GUID 0x%" PRIx64 "\n", cl_ntoh64( node_guid ) ); } else @@ -679,7 +640,7 @@ osm_si_rcv_process( osm_log( p_rcv->p_log, OSM_LOG_ERROR, "osm_si_rcv_process: ERR 3610: " "\n\t\t\t\tBad LinearFDBTop value = 0x%X " - "on switch 0x%" PRIx64 "." + "on switch 0x%" PRIx64 "\n\t\t\t\tForcing correction to 0x%X\n", cl_ntoh16( p_si->lin_top ), cl_ntoh64( osm_node_get_node_guid( p_node ) ), @@ -691,9 +652,7 @@ osm_si_rcv_process( /* Acquire the switch object for this switch. */ - p_sw = (osm_switch_t*)cl_qmap_get( p_sw_guid_tbl, - node_guid ); - if( p_sw == (osm_switch_t*)cl_qmap_end( p_sw_guid_tbl ) ) + if( !p_node->sw ) { __osm_si_rcv_process_new( p_rcv, p_node, p_madw ); /* @@ -705,7 +664,7 @@ osm_si_rcv_process( else { /* we might get back a request for signaling change was detected */ - if (__osm_si_rcv_process_existing( p_rcv, p_node, p_sw, p_madw )) + if (__osm_si_rcv_process_existing( p_rcv, p_node, p_madw )) { CL_PLOCK_RELEASE( p_rcv->p_lock ); osm_state_mgr_process( p_rcv->p_state_mgr, @@ -719,3 +678,4 @@ osm_si_rcv_process( Exit: OSM_LOG_EXIT( p_rcv->p_log ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_sw_info_rcv_ctrl.c b/trunk/ulp/opensm/user/opensm/osm_sw_info_rcv_ctrl.c index 37870283..4b2170de 100644 --- a/trunk/ulp/opensm/user/opensm/osm_sw_info_rcv_ctrl.c +++ b/trunk/ulp/opensm/user/opensm/osm_sw_info_rcv_ctrl.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -44,15 +44,11 @@ * $Revision: 1.5 $ */ -/* - Next available error code: 0x203 -*/ - #if HAVE_CONFIG_H # include #endif /* HAVE_CONFIG_H */ -#include +#include #include #include @@ -74,7 +70,7 @@ void osm_si_rcv_ctrl_construct( IN osm_si_rcv_ctrl_t* const p_ctrl ) { - cl_memclr( p_ctrl, sizeof(*p_ctrl) ); + memset( p_ctrl, 0, sizeof(*p_ctrl) ); p_ctrl->h_disp = CL_DISP_INVALID_HANDLE; } @@ -127,3 +123,4 @@ osm_si_rcv_ctrl_init( return( status ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_sweep_fail_ctrl.c b/trunk/ulp/opensm/user/opensm/osm_sweep_fail_ctrl.c index f9c3aea7..547825cc 100644 --- a/trunk/ulp/opensm/user/opensm/osm_sweep_fail_ctrl.c +++ b/trunk/ulp/opensm/user/opensm/osm_sweep_fail_ctrl.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Implementation of osm_sweep_fail_ctrl_t. @@ -46,7 +47,7 @@ # include #endif /* HAVE_CONFIG_H */ -#include +#include #include #include @@ -77,7 +78,7 @@ void osm_sweep_fail_ctrl_construct( IN osm_sweep_fail_ctrl_t* const p_ctrl ) { - cl_memclr( p_ctrl, sizeof(*p_ctrl) ); + memset( p_ctrl, 0, sizeof(*p_ctrl) ); p_ctrl->h_disp = CL_DISP_INVALID_HANDLE; } @@ -129,3 +130,4 @@ osm_sweep_fail_ctrl_init( return( status ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_switch.c b/trunk/ulp/opensm/user/opensm/osm_switch.c index 3d4a538c..23bb8b68 100644 --- a/trunk/ulp/opensm/user/opensm/osm_switch.c +++ b/trunk/ulp/opensm/user/opensm/osm_switch.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -48,12 +48,12 @@ # include #endif /* HAVE_CONFIG_H */ -#include +#include +#include #include #include #include - /********************************************************************** **********************************************************************/ void @@ -61,7 +61,7 @@ osm_switch_construct( IN osm_switch_t* const p_sw ) { CL_ASSERT( p_sw ); - cl_memclr( p_sw, sizeof(*p_sw) ); + memset( p_sw, 0, sizeof(*p_sw) ); osm_lid_matrix_construct( &p_sw->lmx ); } @@ -75,9 +75,9 @@ osm_switch_init( { ib_api_status_t status = IB_SUCCESS; ib_switch_info_t *p_si; - ib_smp_t *p_smp; + ib_smp_t *p_smp; uint8_t num_ports; - uint32_t port_num; + uint32_t port_num; CL_ASSERT( p_sw ); CL_ASSERT( p_madw ); @@ -99,14 +99,18 @@ osm_switch_init( goto Exit; status = osm_fwd_tbl_init( &p_sw->fwd_tbl, p_si ); + if( status != IB_SUCCESS ) + goto Exit; - p_sw->p_prof = cl_zalloc( sizeof(*p_sw->p_prof) * num_ports ); + p_sw->p_prof = malloc( sizeof(*p_sw->p_prof) * num_ports ); if( p_sw->p_prof == NULL ) { status = IB_INSUFFICIENT_MEMORY; goto Exit; } + memset( p_sw->p_prof, 0, sizeof(*p_sw->p_prof) * num_ports ); + status = osm_mcast_tbl_init( &p_sw->mcast_tbl, osm_node_get_num_physp( p_node ), cl_ntoh16( p_si->mcast_cap ) ); if( status != IB_SUCCESS ) @@ -127,7 +131,7 @@ osm_switch_destroy( { /* free memory to avoid leaks */ osm_mcast_tbl_destroy( &p_sw->mcast_tbl ); - cl_free( p_sw->p_prof ); + free( p_sw->p_prof ); osm_fwd_tbl_destroy( &p_sw->fwd_tbl ); osm_lid_matrix_destroy( &p_sw->lmx ); } @@ -139,7 +143,7 @@ osm_switch_delete( IN OUT osm_switch_t** const pp_sw ) { osm_switch_destroy( *pp_sw ); - cl_free( *pp_sw ); + free( *pp_sw ); *pp_sw = NULL; } @@ -153,9 +157,10 @@ osm_switch_new( ib_api_status_t status; osm_switch_t *p_sw; - p_sw = (osm_switch_t*)cl_zalloc( sizeof(*p_sw) ); + p_sw = (osm_switch_t*)malloc( sizeof(*p_sw) ); if( p_sw ) { + memset( p_sw, 0, sizeof(*p_sw) ); status = osm_switch_init( p_sw, p_node, p_madw ); if( status != IB_SUCCESS ) osm_switch_delete( &p_sw ); @@ -190,7 +195,8 @@ osm_switch_get_fwd_tbl_block( if( base_lid_ho <= max_lid_ho ) { - cl_memclr( p_block, IB_SMP_DATA_SIZE ); + /* Initialize LIDs in block to invalid port number. */ + memset( p_block, 0xff, IB_SMP_DATA_SIZE ); /* Determine the range of LIDs we can return with this block. */ @@ -223,14 +229,12 @@ osm_switch_recommend_path( IN OUT uint64_t *remote_sys_guids, IN OUT uint16_t *p_num_used_sys, IN OUT uint64_t *remote_node_guids, - IN OUT uint16_t *p_num_used_nodes, - IN const uint32_t max_routes_subscribed, - IN boolean_t ui_ucast_fdb_assign_func_defined + IN OUT uint16_t *p_num_used_nodes ) { /* We support an enhanced LMC aware routing mode: - In case of LMC > 0 we can track the remote side + In the case of LMC > 0, we can track the remote side system and node for all of the lids of the target and try and avoid routing again through the same system / node. @@ -271,7 +275,6 @@ osm_switch_recommend_path( num_ports = osm_switch_get_num_ports( p_sw ); least_hops = osm_switch_get_least_hops( p_sw, lid_ho ); - if ( least_hops == OSM_NO_PATH ) return (OSM_NO_PATH); @@ -310,7 +313,7 @@ osm_switch_recommend_path( in the forwarding tables that he wants to be overridden by the minimum hop function. */ - if ( hops == least_hops || ui_ucast_fdb_assign_func_defined ) + if ( hops == least_hops ) { return( port_num ); } @@ -337,7 +340,7 @@ osm_switch_recommend_path( { if ( osm_switch_get_hop_count( p_sw, lid_ho, port_num ) == least_hops) { - /* let us make sure it is not down or un-healthy */ + /* let us make sure it is not down or unhealthy */ p_physp = osm_node_get_physp_ptr(p_sw->p_node, port_num); if (osm_physp_is_valid(p_physp) && osm_physp_is_healthy(p_physp) && @@ -345,7 +348,7 @@ osm_switch_recommend_path( we require all - non sma ports to be linked to be routed through */ - (! port_num || osm_physp_get_remote(p_physp))) + (!port_num || osm_physp_get_remote(p_physp))) { /* @@ -360,11 +363,13 @@ osm_switch_recommend_path( /* Advanced LMC routing requires tracking of the best port by the node connected to the other side of - it . + it. */ if (routing_for_lmc && port_num) { - /* printf("LID:%u SYS:%d NODE:%d\n", lid_ho,*p_num_used_sys, *p_num_used_nodes); */ +#if 0 + printf("LID:0x%X SYS:%d NODE:%d\n", lid_ho, *p_num_used_sys, *p_num_used_nodes); +#endif /* Get the Remote Node */ p_rem_physp = osm_physp_get_remote(p_physp); @@ -373,13 +378,13 @@ osm_switch_recommend_path( /* Is the sys guid already used ? */ sys_used = FALSE; for (i = 0; !sys_used && (i < *p_num_used_sys); i++) - if (!cl_memcmp(&p_rem_node->node_info.sys_guid, - &remote_sys_guids[i], - sizeof(uint64_t))) + if (!memcmp(&p_rem_node->node_info.sys_guid, + &remote_sys_guids[i], + sizeof(uint64_t))) sys_used = TRUE; /* If not update the least hops for this case */ - if (! sys_used) + if (!sys_used) { if (check_count < least_paths_other_sys) { @@ -390,17 +395,17 @@ osm_switch_recommend_path( else { /* same sys found - try node */ - /* Else Is the node guid already used ? */ + /* Else is the node guid already used ? */ node_used = FALSE; for (i = 0; !node_used && (i < *p_num_used_nodes); i++) - if (!cl_memcmp(&p_rem_node->node_info.node_guid, - &remote_node_guids[i], - sizeof(uint64_t))) + if (!memcmp(&p_rem_node->node_info.node_guid, + &remote_node_guids[i], + sizeof(uint64_t))) node_used = TRUE; /* If not update the least hops for this case */ - if (! node_used) + if (!node_used) { if (check_count < least_paths_other_nodes) { @@ -415,8 +420,7 @@ osm_switch_recommend_path( /* the count is min but also lower then the max subscribed */ - if( (check_count < least_paths) && - (check_count <= max_routes_subscribed)) + if( check_count < least_paths ) { port_found = TRUE; best_port = port_num; @@ -445,13 +449,13 @@ osm_switch_recommend_path( p_physp = osm_node_get_physp_ptr(p_sw->p_node, best_port); p_rem_physp = osm_physp_get_remote(p_physp); p_rem_node = osm_physp_get_node_ptr(p_rem_physp); - cl_memcpy(&remote_node_guids[*p_num_used_nodes], - &(p_rem_node->node_info.node_guid), - sizeof(uint64_t)); + memcpy(&remote_node_guids[*p_num_used_nodes], + &(p_rem_node->node_info.node_guid), + sizeof(uint64_t)); (*p_num_used_nodes)++; - cl_memcpy(&remote_sys_guids[*p_num_used_sys], - &(p_rem_node->node_info.sys_guid), - sizeof(uint64_t)); + memcpy(&remote_sys_guids[*p_num_used_sys], + &(p_rem_node->node_info.sys_guid), + sizeof(uint64_t)); (*p_num_used_sys)++; } @@ -480,7 +484,7 @@ osm_switch_recommend_mcast_path( IN osm_switch_t* const p_sw, IN uint16_t const lid_ho, IN uint16_t const mlid_ho, - IN boolean_t const ignore_existing ) + IN boolean_t const ignore_existing ) { uint8_t hops; uint8_t port_num; @@ -489,6 +493,7 @@ osm_switch_recommend_mcast_path( CL_ASSERT( lid_ho > 0 ); CL_ASSERT( mlid_ho >= IB_LID_MCAST_START_HO ); + num_ports = osm_switch_get_num_ports( p_sw ); /* @@ -524,7 +529,7 @@ osm_switch_recommend_mcast_path( Determine the best multicast path to the target. Note that this algorithm is slightly different from the one used for unicast route - recommendation. In this case (multicast) we must NOT + recommendation. In this case (multicast), we must NOT perform any sort of load balancing. We MUST take the FIRST port found that has <= the lowest hop count path. This prevents more than one multicast path to the same remote switch which @@ -542,3 +547,4 @@ osm_switch_recommend_mcast_path( CL_ASSERT( port_num < num_ports ); return( port_num ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_trap_rcv.c b/trunk/ulp/opensm/user/opensm/osm_trap_rcv.c index dcdef2ea..3fe79324 100644 --- a/trunk/ulp/opensm/user/opensm/osm_trap_rcv.c +++ b/trunk/ulp/opensm/user/opensm/osm_trap_rcv.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -48,8 +48,8 @@ # include #endif /* HAVE_CONFIG_H */ +#include #include -#include #include #include #include @@ -140,7 +140,7 @@ osm_trap_rcv_aging_tracker_callback( { osm_log( p_rcv->p_log, OSM_LOG_VERBOSE, "osm_trap_rcv_aging_tracker_callback: " - "Cannot find port num:%u with lid:%u\n", + "Cannot find port num:0x%X with lid:%u\n", port_num, lid ); } else @@ -175,7 +175,7 @@ void osm_trap_rcv_construct( IN osm_trap_rcv_t* const p_rcv ) { - cl_memclr( p_rcv, sizeof(*p_rcv) ); + memset( p_rcv, 0, sizeof(*p_rcv) ); cl_event_wheel_construct( &p_rcv->trap_aging_tracker ); } @@ -232,7 +232,7 @@ osm_trap_rcv_init( #define CRC32_POLYNOMIAL 0xEDB88320L /* calculate the crc for a given buffer */ -uint32_t +static uint32_t __osm_trap_calc_crc32(void *buffer, uint32_t count) { uint32_t temp1, temp2; @@ -279,7 +279,7 @@ __osm_trap_calc_crc32(void *buffer, uint32_t count) \______/ \___/ \___/ 16b 16b 32b */ -void +static void __osm_trap_get_key( IN uint16_t lid, IN uint8_t port_num, @@ -296,7 +296,28 @@ __osm_trap_get_key( /********************************************************************** **********************************************************************/ -void +static int +__print_num_received( + IN uint32_t num_received ) +{ + uint32_t i; + + /* Series is 10, 20, 50, 100, 200, 500, ... */ + i = num_received; + while (i >= 10) { + if (i % 10) + break; + i = i / 10; + } + if (i == 1 || i == 2 || i == 5) + return 1; + else + return 0; +} + +/********************************************************************** + **********************************************************************/ +static void __osm_trap_rcv_process_request( IN osm_trap_rcv_t* const p_rcv, IN const osm_madw_t* const p_madw ) @@ -305,8 +326,7 @@ __osm_trap_rcv_process_request( ib_smp_t* p_smp; ib_mad_notice_attr_t* p_ntci = (ib_mad_notice_attr_t*)payload; ib_api_status_t status; - osm_madw_t tmp_madw; /* we need a copy to last after */ - /* repress. */ + osm_madw_t tmp_madw; /* we need a copy to last after repress */ uint64_t trap_key; uint32_t num_received; osm_physp_t* p_physp; @@ -341,8 +361,8 @@ __osm_trap_rcv_process_request( /* No real need to grab the lock for this function. */ - cl_memclr( payload, sizeof( payload ) ); - cl_memclr( &tmp_madw, sizeof( tmp_madw )); + memset( payload, 0, sizeof( payload ) ); + memset( &tmp_madw, 0, sizeof( tmp_madw )); p_smp = osm_madw_get_smp_ptr( p_madw ); @@ -361,8 +381,8 @@ __osm_trap_rcv_process_request( * payload. */ - cl_memcpy(payload, &(p_smp->data), IB_SMP_DATA_SIZE); - cl_memcpy(&tmp_madw, p_madw, sizeof( tmp_madw )); + memcpy(payload, &(p_smp->data), IB_SMP_DATA_SIZE); + memcpy(&tmp_madw, p_madw, sizeof( tmp_madw )); if (is_gsi == FALSE) { @@ -397,16 +417,35 @@ __osm_trap_rcv_process_request( /* Print some info about the incoming Trap */ if (ib_notice_is_generic(p_ntci)) { - osm_log( p_rcv->p_log, OSM_LOG_ERROR, - "__osm_trap_rcv_process_request: " - "Received Generic Notice type:0x%02X num:%u Producer:%u " - "from LID:0x%04X TID:0x%016" PRIx64 "\n", - ib_notice_get_type(p_ntci), - cl_ntoh16(p_ntci->g_or_v.generic.trap_num), - cl_ntoh32(ib_notice_get_prod_type(p_ntci)), - cl_hton16(source_lid), - cl_ntoh64(p_smp->trans_id) - ); + if ((p_ntci->g_or_v.generic.trap_num == CL_HTON16(129)) || + (p_ntci->g_or_v.generic.trap_num == CL_HTON16(130)) || + (p_ntci->g_or_v.generic.trap_num == CL_HTON16(131))) + { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "__osm_trap_rcv_process_request: " + "Received Generic Notice type:0x%02X num:%u Producer:%u " + "from LID:0x%04X Port %d TID:0x%016" PRIx64 "\n", + ib_notice_get_type(p_ntci), + cl_ntoh16(p_ntci->g_or_v.generic.trap_num), + cl_ntoh32(ib_notice_get_prod_type(p_ntci)), + cl_hton16(source_lid), + p_ntci->data_details.ntc_129_131.port_num, + cl_ntoh64(p_smp->trans_id) + ); + } + else + { + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "__osm_trap_rcv_process_request: " + "Received Generic Notice type:0x%02X num:%u Producer:%u " + "from LID:0x%04X TID:0x%016" PRIx64 "\n", + ib_notice_get_type(p_ntci), + cl_ntoh16(p_ntci->g_or_v.generic.trap_num), + cl_ntoh32(ib_notice_get_prod_type(p_ntci)), + cl_hton16(source_lid), + cl_ntoh64(p_smp->trans_id) + ); + } } else { @@ -423,7 +462,7 @@ __osm_trap_rcv_process_request( } } - osm_dump_notice( p_rcv->p_log ,p_ntci, OSM_LOG_VERBOSE); + osm_dump_notice( p_rcv->p_log, p_ntci, OSM_LOG_VERBOSE ); status = osm_resp_send( p_rcv->p_resp, &tmp_madw, 0, payload ); if( status != IB_SUCCESS ) @@ -449,7 +488,7 @@ __osm_trap_rcv_process_request( (p_ntci->g_or_v.generic.trap_num == CL_HTON16(130)) || (p_ntci->g_or_v.generic.trap_num == CL_HTON16(131))) ) { - /* If this is a trap 129, 130 or 131 - then this is a trap + /* If this is a trap 129, 130, or 131 - then this is a trap signaling a change on a physical port. Mark the flag physp_change_trap as TRUE. */ physp_change_trap = TRUE; /* The source_lid should be based on the source_lid from the trap */ @@ -461,16 +500,10 @@ __osm_trap_rcv_process_request( if ( physp_change_trap == TRUE ) { port_num = p_ntci->data_details.ntc_129_131.port_num; - __osm_trap_get_key(source_lid, - port_num, - p_ntci, - &trap_key); + __osm_trap_get_key(source_lid, port_num, p_ntci, &trap_key); } else - __osm_trap_get_key(source_lid, - 0, - p_ntci, - &trap_key); + __osm_trap_get_key(source_lid, 0, p_ntci, &trap_key); /* try to find it in the aging tracker */ num_received = cl_event_wheel_num_regs(&p_rcv->trap_aging_tracker, @@ -479,14 +512,14 @@ __osm_trap_rcv_process_request( /* Now we know how many times it provided this trap */ if (num_received > 10) { - osm_log( p_rcv->p_log, OSM_LOG_ERROR, - "__osm_trap_rcv_process_request: ERR 3804: " - "Received trap %u times consecutively\n", - num_received); + if (__print_num_received(num_received)) + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "__osm_trap_rcv_process_request: ERR 3804: " + "Received trap %u times consecutively\n", + num_received); /* * If the trap provides info about a bad port - * we will mark it as unhealthy. - * + * we mark it as unhealthy. */ if (physp_change_trap == TRUE) { @@ -522,11 +555,11 @@ __osm_trap_rcv_process_request( osm_physp_set_health(p_physp, FALSE); /* Make sure we sweep again - force a heavy sweep. */ /* The sweep should be done only after the re-registration, or - else we'll be loosing track of the timer. */ + else we'll be losing track of the timer. */ run_heavy_sweep = TRUE; } /* If we are marking the port as unhealthy - we want to - keep this for a longer period of time then the + keep this for a longer period of time than the OSM_DEFAULT_TRAP_SUPRESSION_TIMEOUT. Use the OSM_DEFAULT_UNHEALTHY_TIMEOUT */ event_wheel_timeout = OSM_DEFAULT_UNHEALTHY_TIMEOUT; @@ -541,24 +574,25 @@ __osm_trap_rcv_process_request( cl_event_wheel_reg(&p_rcv->trap_aging_tracker, trap_key, cl_get_time_stamp() + event_wheel_timeout, - osm_trap_rcv_aging_tracker_callback, /* no callback */ - p_rcv /* no context */ + osm_trap_rcv_aging_tracker_callback, /* no callback */ + p_rcv /* no context */ ); else cl_event_wheel_reg(&p_rcv->trap_aging_tracker, trap_key, cl_get_time_stamp() + event_wheel_timeout, - NULL, /* no callback */ - NULL /* no context */ + NULL, /* no callback */ + NULL /* no context */ ); /* If was already registered do nothing more */ if ( num_received > 10 && run_heavy_sweep == FALSE ) { - osm_log( p_rcv->p_log, OSM_LOG_VERBOSE, - "__osm_trap_rcv_process_request: " - "Continuously received this trap %u times. Ignoring it\n", - num_received); + if (__print_num_received(num_received)) + osm_log( p_rcv->p_log, OSM_LOG_VERBOSE, + "__osm_trap_rcv_process_request: " + "Continuously received this trap %u times. Ignoring it\n", + num_received); goto Exit; } } @@ -586,8 +620,7 @@ __osm_trap_rcv_process_request( p_rcv->p_subn->force_immediate_heavy_sweep = TRUE; } - osm_state_mgr_process( p_rcv->p_state_mgr, - OSM_SIGNAL_SWEEP ); + osm_state_mgr_process( p_rcv->p_state_mgr, OSM_SIGNAL_SWEEP ); } /* If we reached here due to trap 129/130/131 - do not need to do @@ -603,9 +636,9 @@ __osm_trap_rcv_process_request( { if (tmp_madw.mad_addr.addr_type.gsi.global_route) { - cl_memcpy(&(p_ntci->issuer_gid), - &(tmp_madw.mad_addr.addr_type.gsi.grh_info.src_gid), - sizeof(ib_gid_t)); + memcpy(&(p_ntci->issuer_gid), + &(tmp_madw.mad_addr.addr_type.gsi.grh_info.src_gid), + sizeof(ib_gid_t)); } else { @@ -649,7 +682,10 @@ __osm_trap_rcv_process_request( p_ntci->issuer_gid.unicast.interface_id = p_port->guid; } + /* we need a lock here as the InformInfo DB must be stable */ + CL_PLOCK_ACQUIRE( p_rcv->p_lock ); status = osm_report_notice(p_rcv->p_log, p_rcv->p_subn, p_ntci); + CL_PLOCK_RELEASE( p_rcv->p_lock ); if( status != IB_SUCCESS ) { osm_log( p_rcv->p_log, OSM_LOG_ERROR, @@ -663,10 +699,11 @@ __osm_trap_rcv_process_request( OSM_LOG_EXIT( p_rcv->p_log ); } +#if 0 /********************************************************************** CURRENTLY WE ARE NOT CREATING TRAPS - SO THIS CALL IS AN ERROR **********************************************************************/ -void +static void __osm_trap_rcv_process_sm( IN const osm_trap_rcv_t* const p_rcv, IN const osm_remote_sm_t* const p_sm ) @@ -675,16 +712,17 @@ __osm_trap_rcv_process_sm( OSM_LOG_ENTER( p_rcv->p_log, __osm_trap_rcv_process_sm ); osm_log( p_rcv->p_log, OSM_LOG_ERROR, - "__osm_trap_rcv_process_sm: " + "__osm_trap_rcv_process_sm: ERR 3807: " "This function is not supported yet\n"); OSM_LOG_EXIT( p_rcv->p_log ); } +#endif /********************************************************************** CURRENTLY WE ARE NOT CREATING TRAPS - SO THIS CALL IN AN ERROR **********************************************************************/ -void +static void __osm_trap_rcv_process_response( IN const osm_trap_rcv_t* const p_rcv, IN const osm_madw_t* const p_madw ) @@ -693,7 +731,7 @@ __osm_trap_rcv_process_response( OSM_LOG_ENTER( p_rcv->p_log, __osm_trap_rcv_process_response ); osm_log( p_rcv->p_log, OSM_LOG_ERROR, - "__osm_trap_rcv_process_response: " + "__osm_trap_rcv_process_response: ERR 3808: " "This function is not supported yet\n"); OSM_LOG_EXIT( p_rcv->p_log ); @@ -730,3 +768,4 @@ osm_trap_rcv_process( OSM_LOG_EXIT( p_rcv->p_log ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_trap_rcv_ctrl.c b/trunk/ulp/opensm/user/opensm/osm_trap_rcv_ctrl.c index 138fe027..d7803506 100644 --- a/trunk/ulp/opensm/user/opensm/osm_trap_rcv_ctrl.c +++ b/trunk/ulp/opensm/user/opensm/osm_trap_rcv_ctrl.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Implementation of osm_trap_rcv_ctrl_t. @@ -48,7 +49,7 @@ # include #endif /* HAVE_CONFIG_H */ -#include +#include #include #include @@ -70,7 +71,7 @@ void osm_trap_rcv_ctrl_construct( IN osm_trap_rcv_ctrl_t* const p_ctrl ) { - cl_memclr( p_ctrl, sizeof(*p_ctrl) ); + memset( p_ctrl, 0, sizeof(*p_ctrl) ); p_ctrl->h_disp = CL_DISP_INVALID_HANDLE; } @@ -122,3 +123,4 @@ osm_trap_rcv_ctrl_init( OSM_LOG_EXIT( p_log ); return( status ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_ucast_file.c b/trunk/ulp/opensm/user/opensm/osm_ucast_file.c new file mode 100644 index 00000000..424fed24 --- /dev/null +++ b/trunk/ulp/opensm/user/opensm/osm_ucast_file.c @@ -0,0 +1,413 @@ +/* + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. + * + * This software is available to you under the OpenIB.org BSD license + * below: + * + * Redistribution and use in source and binary forms, with or + * without modification, are permitted provided that the following + * conditions are met: + * + * - Redistributions of source code must retain the above + * copyright notice, this list of conditions and the following + * disclaimer. + * + * - Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials + * provided with the distribution. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS + * BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN + * ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN + * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + * + * $Id$ + */ + + +/* + * Abstract: + * Implementation of OpenSM unicast routing module which loads + * routes from the dump file + * + * Environment: + * Linux User Mode + * + */ + +#if HAVE_CONFIG_H +# include +#endif /* HAVE_CONFIG_H */ + +#include +#include +#include + +#include +#include +#include +#include +#include +#include + + +static uint16_t remap_lid(osm_opensm_t *p_osm, uint16_t lid, ib_net64_t guid) +{ + osm_port_t *p_port; + uint16_t min_lid, max_lid; + uint8_t lmc; + + p_port = (osm_port_t *)cl_qmap_get(&p_osm->subn.port_guid_tbl, guid); + if (!p_port || + p_port == (osm_port_t *)cl_qmap_end(&p_osm->subn.port_guid_tbl)) { + osm_log(&p_osm->log, OSM_LOG_VERBOSE, + "remap_lid: cannot find port guid 0x%016" PRIx64 + " , will use the same lid\n", cl_ntoh64(guid)); + return lid; + } + + osm_port_get_lid_range_ho(p_port, &min_lid, &max_lid); + if (min_lid <= lid && lid <= max_lid) + return lid; + + lmc = osm_port_get_lmc(p_port); + return min_lid + (lid & ((1 << lmc) - 1)); +} + +static void add_path(osm_opensm_t * p_osm, + osm_switch_t * p_sw, uint16_t lid, uint8_t port_num, + ib_net64_t port_guid) +{ + uint16_t new_lid; + uint8_t old_port; + + new_lid = port_guid ? remap_lid(p_osm, lid, port_guid) : lid; + old_port = osm_fwd_tbl_get(osm_switch_get_fwd_tbl_ptr(p_sw), new_lid); + if (old_port != OSM_NO_PATH && old_port != port_num) { + osm_log(&p_osm->log, OSM_LOG_VERBOSE, + "add_path: LID collision is detected on switch " + "0x016%" PRIx64 ", will overwrite LID 0x%x entry\n", + cl_ntoh64(osm_node_get_node_guid + (osm_switch_get_node_ptr(p_sw))), new_lid); + } + + p_osm->sm.ucast_mgr.lft_buf[new_lid] = port_num; + if (!(p_osm->subn.opt.port_profile_switch_nodes && port_guid && + osm_get_switch_by_guid(&p_osm->subn, port_guid))) + osm_switch_count_path(p_sw, port_num); + + osm_log(&p_osm->log, OSM_LOG_DEBUG, + "add_path: route 0x%04x(was 0x%04x) %u 0x%016" PRIx64 + " is added to switch 0x%016" PRIx64 "\n", + new_lid, lid, port_num, cl_ntoh64(port_guid), + cl_ntoh64(osm_node_get_node_guid + (osm_switch_get_node_ptr(p_sw)))); +} + +static void add_lid_hops(osm_opensm_t *p_osm, osm_switch_t *p_sw, + uint16_t lid, ib_net64_t guid, + uint8_t hops[], unsigned len) +{ + uint16_t new_lid; + uint8_t i; + + new_lid = guid ? remap_lid(p_osm, lid, guid) : lid; + if (len > osm_switch_get_num_ports(p_sw)) + len = osm_switch_get_num_ports(p_sw); + + for (i = 0 ; i < len ; i++) + osm_switch_set_hops(p_sw, lid, i, hops[i]); +} + +static int do_ucast_file_load(void *context) +{ + char line[1024]; + char *file_name; + FILE *file; + ib_net64_t sw_guid, port_guid; + osm_opensm_t *p_osm = context; + osm_switch_t *p_sw; + uint16_t lid; + uint8_t port_num; + unsigned lineno; + + file_name = p_osm->subn.opt.ucast_dump_file; + if (!file_name) { + osm_log(&p_osm->log, OSM_LOG_ERROR|OSM_LOG_SYS, + "do_ucast_file_load: ERR 6301: " + "ucast dump file name is not defined; " + "using default routing algorithm\n"); + return -1; + } + + file = fopen(file_name, "r"); + if (!file) { + osm_log(&p_osm->log, OSM_LOG_ERROR|OSM_LOG_SYS, + "do_ucast_file_load: ERR 6302: " + "cannot open ucast dump file \'%s\'; " + "using default routing algorithm\n", file_name); + return -1; + } + + lineno = 0; + p_sw = NULL; + + while (fgets(line, sizeof(line) - 1, file) != NULL) { + char *p, *q; + lineno++; + + p = line; + while (isspace(*p)) + p++; + + if (*p == '#') + continue; + + if (!strncmp(p, "Multicast mlids", 15)) { + osm_log(&p_osm->log, OSM_LOG_ERROR|OSM_LOG_SYS, + "do_ucast_file_load: ERR 6303: " + "Multicast dump file detected; " + "skipping parsing. Using default " + "routing algorithm\n"); + } else if (!strncmp(p, "Unicast lids", 12)) { + if (p_sw) + osm_ucast_mgr_set_fwd_table(&p_osm->sm.ucast_mgr, p_sw); + q = strstr(p, " guid 0x"); + if (!q) { + osm_log(&p_osm->log, OSM_LOG_ERROR, + "PARSE ERROR: %s:%u: " + "cannot parse switch definition\n", + file_name, lineno); + return -1; + } + p = q + 8; + sw_guid = strtoull(p, &q, 16); + if (q == p || !isspace(*q)) { + osm_log(&p_osm->log, OSM_LOG_ERROR, + "PARSE ERROR: %s:%u: " + "cannot parse switch guid: \'%s\'\n", + file_name, lineno, p); + return -1; + } + sw_guid = cl_hton64(sw_guid); + + p_sw = osm_get_switch_by_guid(&p_osm->subn, sw_guid); + if (!p_sw) { + osm_log(&p_osm->log, OSM_LOG_VERBOSE, + "do_ucast_file_load: " + "cannot find switch %016" PRIx64 "\n", + cl_ntoh64(sw_guid)); + continue; + } + memset(p_osm->sm.ucast_mgr.lft_buf, 0xff, IB_LID_UCAST_END_HO + 1); + } else if (p_sw && !strncmp(p, "0x", 2)) { + p += 2; + lid = (uint16_t)strtoul(p, &q, 16); + if (q == p || !isspace(*q)) { + osm_log(&p_osm->log, OSM_LOG_ERROR, + "PARSE ERROR: %s:%u: " + "cannot parse lid: \'%s\'\n", + file_name, lineno, p); + return -1; + } + p = q; + while (isspace(*p)) + p++; + port_num = (uint8_t)strtoul(p, &q, 10); + if (q == p || !isspace(*q)) { + osm_log(&p_osm->log, OSM_LOG_ERROR, + "PARSE ERROR: %s:%u: " + "cannot parse port: \'%s\'\n", + file_name, lineno, p); + return -1; + } + p = q; + /* additionally try to exract guid */ + q = strstr(p, " portguid 0x"); + if (!q) { + osm_log(&p_osm->log, OSM_LOG_VERBOSE, + "PARSE WARNING: %s:%u: " + "cannot find port guid " + "(maybe broken dump): \'%s\'\n", + file_name, lineno, p); + port_guid = 0; + } + else { + p = q + 12; + port_guid = strtoull(p, &q, 16); + if (q == p || (!isspace(*q) && *q != ':')) { + osm_log(&p_osm->log, OSM_LOG_VERBOSE, + "PARSE WARNING: %s:%u: " + "cannot parse port guid " + "(maybe broken dump): \'%s\'\n", + file_name, lineno, p); + port_guid = 0; + } + } + port_guid = cl_hton64(port_guid); + add_path(p_osm, p_sw, lid, port_num, port_guid); + } + } + + if (p_sw) + osm_ucast_mgr_set_fwd_table(&p_osm->sm.ucast_mgr, p_sw); + + fclose(file); + return 0; +} + +static int do_lid_matrix_file_load(void *context) +{ + char line[1024]; + uint8_t hops[256]; + char *file_name; + FILE *file; + ib_net64_t guid; + osm_opensm_t *p_osm = context; + osm_switch_t *p_sw; + unsigned lineno; + uint16_t lid; + + file_name = p_osm->subn.opt.lid_matrix_dump_file; + if (!file_name) { + osm_log(&p_osm->log, OSM_LOG_ERROR|OSM_LOG_SYS, + "do_lid_matrix_file_load: ERR 6304: " + "lid matrix file name is not defined; " + "using default lid matrix generation algorithm\n"); + return -1; + } + + file = fopen(file_name, "r"); + if (!file) { + osm_log(&p_osm->log, OSM_LOG_ERROR|OSM_LOG_SYS, + "do_lid_matrix_file_load: ERR 6305: " + "cannot open lid matrix file \'%s\'; " + "using default lid matrix generation algorithm\n", + file_name); + return -1; + } + + lineno = 0; + p_sw = NULL; + + while (fgets(line, sizeof(line) - 1, file) != NULL) { + char *p, *q; + lineno++; + + p = line; + while (isspace(*p)) + p++; + + if (*p == '#') + continue; + + if (!strncmp(p, "Switch", 6)) { + q = strstr(p, " guid 0x"); + if (!q) { + osm_log(&p_osm->log, OSM_LOG_ERROR, + "PARSE ERROR: %s:%u: " + "cannot parse switch definition\n", + file_name, lineno); + return -1; + } + p = q + 8; + guid = strtoull(p, &q, 16); + if (q == p || !isspace(*q)) { + osm_log(&p_osm->log, OSM_LOG_ERROR, + "PARSE ERROR: %s:%u: " + "cannot parse switch guid: \'%s\'\n", + file_name, lineno, p); + return -1; + } + guid = cl_hton64(guid); + + p_sw = osm_get_switch_by_guid(&p_osm->subn, guid); + if (!p_sw) { + osm_log(&p_osm->log, OSM_LOG_VERBOSE, + "do_lid_matrix_file_load: " + "cannot find switch %016" PRIx64 "\n", + cl_ntoh64(guid)); + continue; + } + } else if (p_sw && !strncmp(p, "0x", 2)) { + unsigned long num; + unsigned len = 0; + + memset(hops, 0xff, sizeof(hops)); + + p += 2; + num = strtoul(p, &q, 16); + if (num > 0xffff || q == p || + (*q != ':' && !isspace(*q))) { + osm_log(&p_osm->log, OSM_LOG_ERROR, + "PARSE ERROR: %s:%u: " + "cannot parse lid: \'%s\'\n", + file_name, lineno, p); + return -1; + } + /* Just checked the range, so casting is safe */ + lid = (uint16_t)num; + p = q; + while (isspace(*p) || *p == ':') + p++; + while (len < 256 && *p && *p != '#') { + num = strtoul(p, &q, 16); + if (num > 0xff || q == p) { + osm_log(&p_osm->log, OSM_LOG_ERROR, + "PARSE ERROR: %s:%u: " + "cannot parse hops number: \'%s\'\n", + file_name, lineno, p); + return -1; + } + /* Just checked the range, so casting is safe */ + hops[len++] = (uint8_t)num; + p = q; + while (isspace(*p)) + p++; + } + /* additionally try to extract guid */ + q = strstr(p, " portguid 0x"); + if (!q) { + osm_log(&p_osm->log, OSM_LOG_VERBOSE, + "PARSE WARNING: %s:%u: " + "cannot find port guid " + "(maybe broken dump): \'%s\'\n", + file_name, lineno, p); + guid = 0; + } + else { + p = q + 12; + guid = strtoull(p, &q, 16); + if (q == p || !isspace(*q)) { + osm_log(&p_osm->log, OSM_LOG_VERBOSE, + "PARSE WARNING: %s:%u: " + "cannot parse port guid " + "(maybe broken dump): \'%s\'\n", + file_name, lineno, p); + guid = 0; + } + } + guid = cl_hton64(guid); + add_lid_hops(p_osm, p_sw, lid, guid, hops, len); + } + } + + fclose(file); + return 0; +} + +int osm_ucast_file_setup(osm_opensm_t * p_osm) +{ + p_osm->routing_engine.context = (void *)p_osm; + p_osm->routing_engine.build_lid_matrices = do_lid_matrix_file_load; + p_osm->routing_engine.ucast_build_fwd_tables = do_ucast_file_load; + return 0; +} + diff --git a/trunk/ulp/opensm/user/opensm/osm_ucast_ftree.c b/trunk/ulp/opensm/user/opensm/osm_ucast_ftree.c new file mode 100644 index 00000000..6a8eae2d --- /dev/null +++ b/trunk/ulp/opensm/user/opensm/osm_ucast_ftree.c @@ -0,0 +1,3141 @@ +/* + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. + * + * This software is available to you under the OpenIB.org BSD license + * below: + * + * Redistribution and use in source and binary forms, with or + * without modification, are permitted provided that the following + * conditions are met: + * + * - Redistributions of source code must retain the above + * copyright notice, this list of conditions and the following + * disclaimer. + * + * - Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials + * provided with the distribution. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS + * BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN + * ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN + * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + * + * $Id$ + */ + + +/* + * Abstract: + * Implementation of OpenSM FatTree routing + * + * Environment: + * Linux User Mode + * + */ + +#if HAVE_CONFIG_H +# include +#endif + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +/* + * FatTree rank is bounded between 2 and 8: + * - Tree of rank 1 has only trivial routing pathes, + * so no need to use FatTree routing. + * - Why maximum rank is 8: + * Each node (switch) is assigned a unique tuple. + * Switches are stored in two cl_qmaps - one is + * ordered by guid, and the other by a key that is + * generated from tuple. Since cl_qmap supports only + * a 64-bit key, the maximal tuple lenght is 8 bytes. + * which means that maximal tree rank is 8. + * Note that the above also implies that each switch + * can have at max 255 up/down ports. + */ + +#define FAT_TREE_MIN_RANK 2 +#define FAT_TREE_MAX_RANK 8 + +typedef enum { + FTREE_DIRECTION_DOWN = -1, + FTREE_DIRECTION_SAME, + FTREE_DIRECTION_UP +} ftree_direction_t; + + +/*************************************************** + ** + ** Forward references + ** + ***************************************************/ + +struct ftree_sw_t_; +struct ftree_hca_t_; +struct ftree_port_t_; +struct ftree_port_group_t_; +struct ftree_fabric_t_; + +/*************************************************** + ** + ** ftree_tuple_t definition + ** + ***************************************************/ + +#define FTREE_TUPLE_BUFF_LEN 1024 +#define FTREE_TUPLE_LEN 8 + +typedef uint8_t ftree_tuple_t[FTREE_TUPLE_LEN]; +typedef uint64_t ftree_tuple_key_t; + +/*************************************************** + ** + ** ftree_sw_table_element_t definition + ** + ***************************************************/ + +typedef struct { + cl_map_item_t map_item; + struct ftree_sw_t_ * p_sw; +} ftree_sw_tbl_element_t; + +/*************************************************** + ** + ** ftree_fwd_tbl_t definition + ** + ***************************************************/ + +typedef uint8_t * ftree_fwd_tbl_t; +#define FTREE_FWD_TBL_LEN (IB_LID_UCAST_END_HO + 1) + +/*************************************************** + ** + ** ftree_port_t definition + ** + ***************************************************/ + +typedef struct ftree_port_t_ +{ + cl_map_item_t map_item; + uint8_t port_num; /* port number on the current node */ + uint8_t remote_port_num; /* port number on the remote node */ + uint32_t counter_up; /* number of allocated routs upwards */ + uint32_t counter_down; /* number of allocated routs downwards */ +} ftree_port_t; + +/*************************************************** + ** + ** ftree_port_group_t definition + ** + ***************************************************/ + +typedef struct ftree_port_group_t_ +{ + cl_map_item_t map_item; + ib_net16_t base_lid; /* base lid of the current node */ + ib_net16_t remote_base_lid; /* base lid of the remote node */ + ib_net64_t port_guid; /* port guid of this port */ + ib_net64_t remote_port_guid; /* port guid of the remote port */ + ib_net64_t remote_node_guid; /* node guid of the remote node */ + uint8_t remote_node_type; /* IB_NODE_TYPE_{CA,SWITCH,ROUTER,...} */ + union remote_hca_or_sw_ + { + struct ftree_hca_t_ * remote_hca; + struct ftree_sw_t_ * remote_sw; + } remote_hca_or_sw; /* pointer to remote hca/switch */ + cl_ptr_vector_t ports; /* vector of ports to the same lid */ +} ftree_port_group_t; + +/*************************************************** + ** + ** ftree_sw_t definition + ** + ***************************************************/ + +typedef struct ftree_sw_t_ +{ + cl_map_item_t map_item; + osm_switch_t * p_osm_sw; + uint8_t rank; + ftree_tuple_t tuple; + ib_net16_t base_lid; + ftree_port_group_t ** down_port_groups; + uint8_t down_port_groups_num; + ftree_port_group_t ** up_port_groups; + uint8_t up_port_groups_num; + ftree_fwd_tbl_t lft_buf; +} ftree_sw_t; + +/*************************************************** + ** + ** ftree_hca_t definition + ** + ***************************************************/ + +typedef struct ftree_hca_t_ { + cl_map_item_t map_item; + osm_node_t * p_osm_node; + ftree_port_group_t ** up_port_groups; + uint16_t up_port_groups_num; +} ftree_hca_t; + +/*************************************************** + ** + ** ftree_fabric_t definition + ** + ***************************************************/ + +typedef struct ftree_fabric_t_ +{ + osm_opensm_t * p_osm; + cl_qmap_t hca_tbl; + cl_qmap_t sw_tbl; + cl_qmap_t sw_by_tuple_tbl; + uint8_t tree_rank; + ftree_sw_t ** leaf_switches; + uint32_t leaf_switches_num; + uint16_t max_hcas_per_leaf; + cl_pool_t sw_fwd_tbl_pool; + uint16_t lft_max_lid_ho; + boolean_t fabric_built; +} ftree_fabric_t; + +/*************************************************** + ** + ** comparators + ** + ***************************************************/ + +static int OSM_CDECL +__osm_ftree_compare_switches_by_index( + IN const void * p1, + IN const void * p2) +{ + ftree_sw_t ** pp_sw1 = (ftree_sw_t **)p1; + ftree_sw_t ** pp_sw2 = (ftree_sw_t **)p2; + + uint16_t i; + for (i = 0; i < FTREE_TUPLE_LEN; i++) + { + if ((*pp_sw1)->tuple[i] > (*pp_sw2)->tuple[i]) + return 1; + if ((*pp_sw1)->tuple[i] < (*pp_sw2)->tuple[i]) + return -1; + } + return 0; +} + +/***************************************************/ + +static int OSM_CDECL +__osm_ftree_compare_port_groups_by_remote_switch_index( + IN const void * p1, + IN const void * p2) +{ + ftree_port_group_t ** pp_g1 = (ftree_port_group_t **)p1; + ftree_port_group_t ** pp_g2 = (ftree_port_group_t **)p2; + + return __osm_ftree_compare_switches_by_index( + &((*pp_g1)->remote_hca_or_sw.remote_sw), + &((*pp_g2)->remote_hca_or_sw.remote_sw) ); +} + +/***************************************************/ + +boolean_t +__osm_ftree_sw_less_by_index( + IN ftree_sw_t * p_sw1, + IN ftree_sw_t * p_sw2) +{ + if (__osm_ftree_compare_switches_by_index((void *)&p_sw1, + (void *)&p_sw2) < 0) + return TRUE; + return FALSE; +} + +/***************************************************/ + +boolean_t +__osm_ftree_sw_greater_by_index( + IN ftree_sw_t * p_sw1, + IN ftree_sw_t * p_sw2) +{ + if (__osm_ftree_compare_switches_by_index((void *)&p_sw1, + (void *)&p_sw2) > 0) + return TRUE; + return FALSE; +} + +/*************************************************** + ** + ** ftree_tuple_t functions + ** + ***************************************************/ + +static void +__osm_ftree_tuple_init( + IN ftree_tuple_t tuple) +{ + memset(tuple, 0xFF, FTREE_TUPLE_LEN); +} + +/***************************************************/ + +static inline boolean_t +__osm_ftree_tuple_assigned( + IN ftree_tuple_t tuple) +{ + return (tuple[0] != 0xFF); +} + +/***************************************************/ + +#define FTREE_TUPLE_BUFFERS_NUM 6 + +static char * +__osm_ftree_tuple_to_str( + IN ftree_tuple_t tuple) +{ + static char buffer[FTREE_TUPLE_BUFFERS_NUM][FTREE_TUPLE_BUFF_LEN]; + static uint8_t ind = 0; + char * ret_buffer; + uint32_t i; + + if (!__osm_ftree_tuple_assigned(tuple)) + return "INDEX.NOT.ASSIGNED"; + + buffer[ind][0] = '\0'; + + for(i = 0; (i < FTREE_TUPLE_LEN) && (tuple[i] != 0xFF); i++) + { + if ((strlen(buffer[ind]) + 10) > FTREE_TUPLE_BUFF_LEN) + return "INDEX.TOO.LONG"; + if (i != 0) + strcat(buffer[ind],"."); + sprintf(&buffer[ind][strlen(buffer[ind])], "%u", tuple[i]); + } + + ret_buffer = buffer[ind]; + ind = (ind + 1) % FTREE_TUPLE_BUFFERS_NUM; + return ret_buffer; +} /* __osm_ftree_tuple_to_str() */ + +/***************************************************/ + +static inline ftree_tuple_key_t +__osm_ftree_tuple_to_key( + IN ftree_tuple_t tuple) +{ + ftree_tuple_key_t key; + memcpy(&key, tuple, FTREE_TUPLE_LEN); + return key; +} + +/***************************************************/ + +static inline void +__osm_ftree_tuple_from_key( + IN ftree_tuple_t tuple, + IN ftree_tuple_key_t key) +{ + memcpy(tuple, &key, FTREE_TUPLE_LEN); +} + +/*************************************************** + ** + ** ftree_sw_tbl_element_t functions + ** + ***************************************************/ + +static ftree_sw_tbl_element_t * +__osm_ftree_sw_tbl_element_create( + IN ftree_sw_t * p_sw) +{ + ftree_sw_tbl_element_t * p_element = + (ftree_sw_tbl_element_t *) malloc(sizeof(ftree_sw_tbl_element_t)); + if (!p_element) + return NULL; + memset(p_element, 0,sizeof(ftree_sw_tbl_element_t)); + + if (p_element) + p_element->p_sw = p_sw; + return p_element; +} + +/***************************************************/ + +static void +__osm_ftree_sw_tbl_element_destroy( + IN ftree_sw_tbl_element_t * p_element) +{ + if (!p_element) + return; + free(p_element); +} + +/*************************************************** + ** + ** ftree_port_t functions + ** + ***************************************************/ + +static ftree_port_t * +__osm_ftree_port_create( + IN uint8_t port_num, + IN uint8_t remote_port_num) +{ + ftree_port_t * p_port = (ftree_port_t *)malloc(sizeof(ftree_port_t)); + if (!p_port) + return NULL; + memset(p_port,0,sizeof(ftree_port_t)); + + p_port->port_num = port_num; + p_port->remote_port_num = remote_port_num; + + return p_port; +} + +/***************************************************/ + +static void +__osm_ftree_port_destroy( + IN ftree_port_t * p_port) +{ + if(p_port) + free(p_port); +} + +/*************************************************** + ** + ** ftree_port_group_t functions + ** + ***************************************************/ + +static ftree_port_group_t * +__osm_ftree_port_group_create( + IN ib_net16_t base_lid, + IN ib_net16_t remote_base_lid, + IN ib_net64_t * p_port_guid, + IN ib_net64_t * p_remote_port_guid, + IN ib_net64_t * p_remote_node_guid, + IN uint8_t remote_node_type, + IN void * p_remote_hca_or_sw) +{ + ftree_port_group_t * p_group = + (ftree_port_group_t *)malloc(sizeof(ftree_port_group_t)); + if (p_group == NULL) + return NULL; + memset(p_group, 0, sizeof(ftree_port_group_t)); + + p_group->base_lid = base_lid; + p_group->remote_base_lid = remote_base_lid; + memcpy(&p_group->port_guid, p_port_guid, sizeof(ib_net64_t)); + memcpy(&p_group->remote_port_guid, p_remote_port_guid, sizeof(ib_net64_t)); + memcpy(&p_group->remote_node_guid, p_remote_node_guid, sizeof(ib_net64_t)); + + p_group->remote_node_type = remote_node_type; + switch (remote_node_type) + { + case IB_NODE_TYPE_CA: + p_group->remote_hca_or_sw.remote_hca = (ftree_hca_t *)p_remote_hca_or_sw; + break; + case IB_NODE_TYPE_SWITCH: + p_group->remote_hca_or_sw.remote_sw = (ftree_sw_t *)p_remote_hca_or_sw; + break; + default: + /* we shouldn't get here - port is created only in hca or switch */ + CL_ASSERT(0); + } + + cl_ptr_vector_init(&p_group->ports, + 0, /* min size */ + 8); /* grow size */ + return p_group; +} /* __osm_ftree_port_group_create() */ + +/***************************************************/ + +static void +__osm_ftree_port_group_destroy( + IN ftree_port_group_t * p_group) +{ + uint32_t i; + uint32_t size; + ftree_port_t * p_port; + + if (!p_group) + return; + + /* remove all the elements of p_group->ports vector */ + size = cl_ptr_vector_get_size(&p_group->ports); + for (i = 0; i < size; i++) + { + cl_ptr_vector_at(&p_group->ports, i, (void **)&p_port); + __osm_ftree_port_destroy(p_port); + } + cl_ptr_vector_destroy(&p_group->ports); + free(p_group); +} /* __osm_ftree_port_group_destroy() */ + +/***************************************************/ + +static void +__osm_ftree_port_group_dump( + IN ftree_fabric_t *p_ftree, + IN ftree_port_group_t * p_group, + IN ftree_direction_t direction) +{ + ftree_port_t * p_port; + uint32_t size; + uint32_t i; + char buff[10*1024]; + + if (!p_group) + return; + + if (!osm_log_is_active(&p_ftree->p_osm->log, OSM_LOG_DEBUG)) + return; + + size = cl_ptr_vector_get_size(&p_group->ports); + buff[0] = '\0'; + + for (i = 0; i < size; i++) + { + cl_ptr_vector_at(&p_group->ports, i, (void **)&p_port); + CL_ASSERT(p_port); + + if (i != 0) + strcat(buff,", "); + sprintf(buff + strlen(buff), "%u", p_port->port_num); + } + + osm_log(&p_ftree->p_osm->log, OSM_LOG_DEBUG, + "__osm_ftree_port_group_dump:" + " Port Group of size %u, port(s): %s, direction: %s\n" + " Local <--> Remote GUID (LID):" + "0x%016" PRIx64 " (0x%x) <--> 0x%016" PRIx64 " (0x%x)\n", + size, + buff, + (direction == FTREE_DIRECTION_DOWN)? "DOWN" : "UP", + cl_ntoh64(p_group->port_guid), + cl_ntoh16(p_group->base_lid), + cl_ntoh64(p_group->remote_port_guid), + cl_ntoh16(p_group->remote_base_lid)); + +} /* __osm_ftree_port_group_dump() */ + +/***************************************************/ + +static void +__osm_ftree_port_group_add_port( + IN ftree_port_group_t * p_group, + IN uint8_t port_num, + IN uint8_t remote_port_num) +{ + uint16_t i; + ftree_port_t * p_port; + + for (i = 0; i < cl_ptr_vector_get_size(&p_group->ports); i++) + { + cl_ptr_vector_at(&p_group->ports, i, (void **)&p_port); + if (p_port->port_num == port_num) + return; + } + + p_port = __osm_ftree_port_create(port_num,remote_port_num); + cl_ptr_vector_insert(&p_group->ports, p_port, NULL); +} + +/*************************************************** + ** + ** ftree_sw_t functions + ** + ***************************************************/ + +static ftree_sw_t * +__osm_ftree_sw_create( + IN ftree_fabric_t * p_ftree, + IN osm_switch_t * p_osm_sw) +{ + ftree_sw_t * p_sw; + uint8_t ports_num; + + /* make sure that the switch has ports */ + if (osm_switch_get_num_ports(p_osm_sw) == 1) + return NULL; + + p_sw = (ftree_sw_t *)malloc(sizeof(ftree_sw_t)); + if (p_sw == NULL) + return NULL; + memset(p_sw, 0, sizeof(ftree_sw_t)); + + p_sw->p_osm_sw = p_osm_sw; + p_sw->rank = 0xFF; + __osm_ftree_tuple_init(p_sw->tuple); + + p_sw->base_lid = osm_node_get_base_lid(osm_switch_get_node_ptr(p_sw->p_osm_sw),0); + + ports_num = osm_node_get_num_physp(osm_switch_get_node_ptr(p_sw->p_osm_sw)); + p_sw->down_port_groups = + (ftree_port_group_t **) malloc(ports_num * sizeof(ftree_port_group_t *)); + p_sw->up_port_groups = + (ftree_port_group_t **) malloc(ports_num * sizeof(ftree_port_group_t *)); + if (!p_sw->down_port_groups || !p_sw->up_port_groups) + return NULL; + p_sw->down_port_groups_num = 0; + p_sw->up_port_groups_num = 0; + + /* initialize lft buffer */ + p_sw->lft_buf = (ftree_fwd_tbl_t)cl_pool_get(&p_ftree->sw_fwd_tbl_pool); + memset(p_sw->lft_buf, OSM_NO_PATH, FTREE_FWD_TBL_LEN); + + return p_sw; +} /* __osm_ftree_sw_create() */ + +/***************************************************/ + +static void +__osm_ftree_sw_destroy( + IN ftree_fabric_t * p_ftree, + IN ftree_sw_t * p_sw) +{ + uint8_t i; + + if (!p_sw) + return; + + for (i = 0; i < p_sw->down_port_groups_num; i++) + __osm_ftree_port_group_destroy(p_sw->down_port_groups[i]); + for (i = 0; i < p_sw->up_port_groups_num; i++) + __osm_ftree_port_group_destroy(p_sw->up_port_groups[i]); + if (p_sw->down_port_groups) + free(p_sw->down_port_groups); + if (p_sw->up_port_groups) + free(p_sw->up_port_groups); + + /* return switch fwd_tbl to pool */ + if (p_sw->lft_buf) + cl_pool_put(&p_ftree->sw_fwd_tbl_pool, (void *)p_sw->lft_buf); + + free(p_sw); +} /* __osm_ftree_sw_destroy() */ + +/***************************************************/ + +static void +__osm_ftree_sw_dump( + IN ftree_fabric_t * p_ftree, + IN ftree_sw_t * p_sw) +{ + uint32_t i; + + if (!p_sw) + return; + + if (!osm_log_is_active(&p_ftree->p_osm->log, OSM_LOG_DEBUG)) + return; + + osm_log(&p_ftree->p_osm->log, OSM_LOG_DEBUG, + "__osm_ftree_sw_dump: " + "Switch index: %s, GUID: 0x%016" PRIx64 ", Ports: %u DOWN, %u UP\n", + __osm_ftree_tuple_to_str(p_sw->tuple), + cl_ntoh64(osm_node_get_node_guid(osm_switch_get_node_ptr(p_sw->p_osm_sw))), + p_sw->down_port_groups_num, + p_sw->up_port_groups_num); + + for( i = 0; i < p_sw->down_port_groups_num; i++ ) + __osm_ftree_port_group_dump(p_ftree, + p_sw->down_port_groups[i], + FTREE_DIRECTION_DOWN); + for( i = 0; i < p_sw->up_port_groups_num; i++ ) + __osm_ftree_port_group_dump(p_ftree, + p_sw->up_port_groups[i], + FTREE_DIRECTION_UP); + +} /* __osm_ftree_sw_dump() */ + +/***************************************************/ + +static boolean_t +__osm_ftree_sw_ranked( + IN ftree_sw_t * p_sw) +{ + return (p_sw->rank != 0xFF); +} + +/***************************************************/ + +static ftree_port_group_t * +__osm_ftree_sw_get_port_group_by_remote_lid( + IN ftree_sw_t * p_sw, + IN ib_net16_t remote_base_lid, + IN ftree_direction_t direction) +{ + uint32_t i; + uint32_t size; + ftree_port_group_t ** port_groups; + + if (direction == FTREE_DIRECTION_UP) + { + port_groups = p_sw->up_port_groups; + size = p_sw->up_port_groups_num; + } + else + { + port_groups = p_sw->down_port_groups; + size = p_sw->down_port_groups_num; + } + + for (i = 0; i < size; i++) + if (remote_base_lid == port_groups[i]->remote_base_lid) + return port_groups[i]; + + return NULL; +} /* __osm_ftree_sw_get_port_group_by_remote_lid() */ + +/***************************************************/ + +static void +__osm_ftree_sw_add_port( + IN ftree_sw_t * p_sw, + IN uint8_t port_num, + IN uint8_t remote_port_num, + IN ib_net16_t base_lid, + IN ib_net16_t remote_base_lid, + IN ib_net64_t port_guid, + IN ib_net64_t remote_port_guid, + IN ib_net64_t remote_node_guid, + IN uint8_t remote_node_type, + IN void * p_remote_hca_or_sw, + IN ftree_direction_t direction) +{ + ftree_port_group_t * p_group = + __osm_ftree_sw_get_port_group_by_remote_lid(p_sw,remote_base_lid,direction); + + if (!p_group) + { + p_group = __osm_ftree_port_group_create( + base_lid, + remote_base_lid, + &port_guid, + &remote_port_guid, + &remote_node_guid, + remote_node_type, + p_remote_hca_or_sw); + CL_ASSERT(p_group); + + if (direction == FTREE_DIRECTION_UP) + p_sw->up_port_groups[p_sw->up_port_groups_num++] = p_group; + else + p_sw->down_port_groups[p_sw->down_port_groups_num++] = p_group; + } + __osm_ftree_port_group_add_port(p_group,port_num,remote_port_num); + +} /* __osm_ftree_sw_add_port() */ + +/***************************************************/ + +static inline void +__osm_ftree_sw_set_fwd_table_block( + IN ftree_sw_t * p_sw, + IN uint16_t lid_ho, + IN uint8_t port_num) +{ + p_sw->lft_buf[lid_ho] = port_num; +} + +/***************************************************/ + +static inline uint8_t +__osm_ftree_sw_get_fwd_table_block( + IN ftree_sw_t * p_sw, + IN uint16_t lid_ho) +{ + return p_sw->lft_buf[lid_ho]; +} + +/***************************************************/ + +static inline cl_status_t +__osm_ftree_sw_set_hops( + IN ftree_sw_t * p_sw, + IN uint16_t max_lid_ho, + IN uint16_t lid_ho, + IN uint8_t port_num, + IN uint8_t hops) +{ + /* make sure the lid matrix has enough room */ + osm_switch_set_min_lid_size(p_sw->p_osm_sw, max_lid_ho); + + /* set local min hop table(LID) */ + return osm_switch_set_hops(p_sw->p_osm_sw, + lid_ho, + port_num, + hops); +} + +/*************************************************** + ** + ** ftree_hca_t functions + ** + ***************************************************/ + +static ftree_hca_t * +__osm_ftree_hca_create( + IN osm_node_t * p_osm_node) +{ + ftree_hca_t * p_hca = (ftree_hca_t *)malloc(sizeof(ftree_hca_t)); + if (p_hca == NULL) + return NULL; + memset(p_hca,0,sizeof(ftree_hca_t)); + + p_hca->p_osm_node = p_osm_node; + p_hca->up_port_groups = (ftree_port_group_t **) + malloc(osm_node_get_num_physp(p_hca->p_osm_node) * sizeof (ftree_port_group_t *)); + if (!p_hca->up_port_groups) + return NULL; + p_hca->up_port_groups_num = 0; + return p_hca; +} + +/***************************************************/ + +static void +__osm_ftree_hca_destroy( + IN ftree_hca_t * p_hca) +{ + uint32_t i; + + if (!p_hca) + return; + + for (i = 0; i < p_hca->up_port_groups_num; i++) + __osm_ftree_port_group_destroy(p_hca->up_port_groups[i]); + + if (p_hca->up_port_groups) + free(p_hca->up_port_groups); + + free(p_hca); +} + +/***************************************************/ + +static void +__osm_ftree_hca_dump( + IN ftree_fabric_t * p_ftree, + IN ftree_hca_t * p_hca) +{ + uint32_t i; + + if (!p_hca) + return; + + if (!osm_log_is_active(&p_ftree->p_osm->log,OSM_LOG_DEBUG)) + return; + + osm_log(&p_ftree->p_osm->log, OSM_LOG_DEBUG, + "__osm_ftree_hca_dump: " + "HCA GUID: 0x%016" PRIx64 ", Ports: %u UP\n", + cl_ntoh64(osm_node_get_node_guid(p_hca->p_osm_node)), + p_hca->up_port_groups_num); + + for( i = 0; i < p_hca->up_port_groups_num; i++ ) + __osm_ftree_port_group_dump(p_ftree, + p_hca->up_port_groups[i], + FTREE_DIRECTION_UP); +} + +/***************************************************/ + +static ftree_port_group_t * +__osm_ftree_hca_get_port_group_by_remote_lid( + IN ftree_hca_t * p_hca, + IN ib_net16_t remote_base_lid) +{ + uint32_t i; + for (i = 0; i < p_hca->up_port_groups_num; i++) + if (remote_base_lid == p_hca->up_port_groups[i]->remote_base_lid) + return p_hca->up_port_groups[i]; + + return NULL; +} + +/***************************************************/ + +static void +__osm_ftree_hca_add_port( + IN ftree_hca_t * p_hca, + IN uint8_t port_num, + IN uint8_t remote_port_num, + IN ib_net16_t base_lid, + IN ib_net16_t remote_base_lid, + IN ib_net64_t port_guid, + IN ib_net64_t remote_port_guid, + IN ib_net64_t remote_node_guid, + IN uint8_t remote_node_type, + IN void * p_remote_hca_or_sw) +{ + ftree_port_group_t * p_group; + + /* this function is supposed to be called only for adding ports + in hca's that lead to switches */ + CL_ASSERT(remote_node_type == IB_NODE_TYPE_SWITCH); + + p_group = __osm_ftree_hca_get_port_group_by_remote_lid(p_hca,remote_base_lid); + + if (!p_group) + { + p_group = __osm_ftree_port_group_create( + base_lid, + remote_base_lid, + &port_guid, + &remote_port_guid, + &remote_node_guid, + remote_node_type, + p_remote_hca_or_sw); + p_hca->up_port_groups[p_hca->up_port_groups_num++] = p_group; + } + __osm_ftree_port_group_add_port(p_group, port_num, remote_port_num); + +} /* __osm_ftree_hca_add_port() */ + +/*************************************************** + ** + ** ftree_fabric_t functions + ** + ***************************************************/ + +static ftree_fabric_t * +__osm_ftree_fabric_create() +{ + cl_status_t status; + ftree_fabric_t * p_ftree = (ftree_fabric_t *)malloc(sizeof(ftree_fabric_t)); + if (p_ftree == NULL) + return NULL; + + memset(p_ftree,0,sizeof(ftree_fabric_t)); + + cl_qmap_init(&p_ftree->hca_tbl); + cl_qmap_init(&p_ftree->sw_tbl); + cl_qmap_init(&p_ftree->sw_by_tuple_tbl); + + status = cl_pool_init( &p_ftree->sw_fwd_tbl_pool, + 8, /* min pool size */ + 0, /* max pool size - unlimited */ + 8, /* grow size */ + FTREE_FWD_TBL_LEN, /* object_size */ + NULL, /* object initializer */ + NULL, /* object destructor */ + NULL ); /* context */ + if (status != CL_SUCCESS) + return NULL; + + p_ftree->tree_rank = 1; + return p_ftree; +} + +/***************************************************/ + +static void +__osm_ftree_fabric_clear(ftree_fabric_t * p_ftree) +{ + ftree_hca_t * p_hca; + ftree_hca_t * p_next_hca; + ftree_sw_t * p_sw; + ftree_sw_t * p_next_sw; + ftree_sw_tbl_element_t * p_element; + ftree_sw_tbl_element_t * p_next_element; + + if (!p_ftree) + return; + + /* remove all the elements of hca_tbl */ + + p_next_hca = (ftree_hca_t *)cl_qmap_head(&p_ftree->hca_tbl); + while( p_next_hca != (ftree_hca_t *)cl_qmap_end( &p_ftree->hca_tbl ) ) + { + p_hca = p_next_hca; + p_next_hca = (ftree_hca_t *)cl_qmap_next(&p_hca->map_item ); + __osm_ftree_hca_destroy(p_hca); + } + cl_qmap_remove_all(&p_ftree->hca_tbl); + + /* remove all the elements of sw_tbl */ + + p_next_sw = (ftree_sw_t *)cl_qmap_head(&p_ftree->sw_tbl); + while( p_next_sw != (ftree_sw_t *)cl_qmap_end( &p_ftree->sw_tbl ) ) + { + p_sw = p_next_sw; + p_next_sw = (ftree_sw_t *)cl_qmap_next(&p_sw->map_item ); + __osm_ftree_sw_destroy(p_ftree,p_sw); + } + cl_qmap_remove_all(&p_ftree->sw_tbl); + + /* remove all the elements of sw_by_tuple_tbl */ + + p_next_element = + (ftree_sw_tbl_element_t *)cl_qmap_head(&p_ftree->sw_by_tuple_tbl); + while( p_next_element != + (ftree_sw_tbl_element_t *)cl_qmap_end( &p_ftree->sw_by_tuple_tbl ) ) + { + p_element = p_next_element; + p_next_element = + (ftree_sw_tbl_element_t *)cl_qmap_next(&p_element->map_item); + __osm_ftree_sw_tbl_element_destroy(p_element); + } + cl_qmap_remove_all(&p_ftree->sw_by_tuple_tbl); + + /* free the leaf switches array */ + if ((p_ftree->leaf_switches_num > 0) && (p_ftree->leaf_switches)) + free(p_ftree->leaf_switches); + + p_ftree->leaf_switches_num = 0; + p_ftree->leaf_switches = NULL; + p_ftree->fabric_built = FALSE; + +} /* __osm_ftree_fabric_destroy() */ + +/***************************************************/ + +static void +__osm_ftree_fabric_destroy(ftree_fabric_t * p_ftree) +{ + if (!p_ftree) + return; + __osm_ftree_fabric_clear(p_ftree); + cl_pool_destroy(&p_ftree->sw_fwd_tbl_pool); + free(p_ftree); +} + +/***************************************************/ + +static void +__osm_ftree_fabric_set_rank(ftree_fabric_t * p_ftree, uint8_t rank) +{ + if (rank > p_ftree->tree_rank) + p_ftree->tree_rank = rank; +} + +/***************************************************/ + +static uint8_t +__osm_ftree_fabric_get_rank(ftree_fabric_t * p_ftree) +{ + return p_ftree->tree_rank; +} + +/***************************************************/ + +static void +__osm_ftree_fabric_add_hca(ftree_fabric_t * p_ftree, osm_node_t * p_osm_node) +{ + ftree_hca_t * p_hca = __osm_ftree_hca_create(p_osm_node); + + CL_ASSERT(osm_node_get_type(p_osm_node) == IB_NODE_TYPE_CA); + + cl_qmap_insert(&p_ftree->hca_tbl, + p_osm_node->node_info.node_guid, + &p_hca->map_item); +} + +/***************************************************/ + +static void +__osm_ftree_fabric_add_sw(ftree_fabric_t * p_ftree, osm_switch_t * p_osm_sw) +{ + ftree_sw_t * p_sw = __osm_ftree_sw_create(p_ftree,p_osm_sw); + + CL_ASSERT(osm_node_get_type(p_osm_sw->p_node) == IB_NODE_TYPE_SWITCH); + + cl_qmap_insert(&p_ftree->sw_tbl, + p_osm_sw->p_node->node_info.node_guid, + &p_sw->map_item); + + /* track the max lid (in host order) that exists in the fabric */ + if (cl_ntoh16(p_sw->base_lid) > p_ftree->lft_max_lid_ho) + p_ftree->lft_max_lid_ho = cl_ntoh16(p_sw->base_lid); +} + +/***************************************************/ + +static void +__osm_ftree_fabric_add_sw_by_tuple( + IN ftree_fabric_t * p_ftree, + IN ftree_sw_t * p_sw) +{ + CL_ASSERT(__osm_ftree_tuple_assigned(p_sw->tuple)); + + cl_qmap_insert(&p_ftree->sw_by_tuple_tbl, + __osm_ftree_tuple_to_key(p_sw->tuple), + &__osm_ftree_sw_tbl_element_create(p_sw)->map_item); +} + +/***************************************************/ + +static ftree_sw_t * +__osm_ftree_fabric_get_sw_by_tuple( + IN ftree_fabric_t * p_ftree, + IN ftree_tuple_t tuple) +{ + ftree_sw_tbl_element_t * p_element; + + CL_ASSERT(__osm_ftree_tuple_assigned(tuple)); + + __osm_ftree_tuple_to_key(tuple); + + p_element = (ftree_sw_tbl_element_t * )cl_qmap_get(&p_ftree->sw_by_tuple_tbl, + __osm_ftree_tuple_to_key(tuple)); + if (p_element == (ftree_sw_tbl_element_t * )cl_qmap_end(&p_ftree->sw_by_tuple_tbl)) + return NULL; + + return p_element->p_sw; +} + +/***************************************************/ + +static void +__osm_ftree_fabric_dump(ftree_fabric_t * p_ftree) +{ + uint32_t i; + ftree_hca_t * p_hca; + ftree_sw_t * p_sw; + + if (!osm_log_is_active(&p_ftree->p_osm->log,OSM_LOG_DEBUG)) + return; + + osm_log(&p_ftree->p_osm->log, OSM_LOG_DEBUG,"__osm_ftree_fabric_dump: \n" + " |-------------------------------|\n" + " |- Full fabric topology dump -|\n" + " |-------------------------------|\n\n"); + + osm_log(&p_ftree->p_osm->log, OSM_LOG_DEBUG, + "__osm_ftree_fabric_dump: -- HCAs:\n"); + + for ( p_hca = (ftree_hca_t *)cl_qmap_head(&p_ftree->hca_tbl); + p_hca != (ftree_hca_t *)cl_qmap_end(&p_ftree->hca_tbl); + p_hca = (ftree_hca_t *)cl_qmap_next(&p_hca->map_item) ) + { + __osm_ftree_hca_dump(p_ftree, p_hca); + } + + for (i = 0; i < __osm_ftree_fabric_get_rank(p_ftree); i++) + { + osm_log(&p_ftree->p_osm->log, OSM_LOG_DEBUG, + "__osm_ftree_fabric_dump: -- Rank %u switches\n", i); + for ( p_sw = (ftree_sw_t *)cl_qmap_head(&p_ftree->sw_tbl); + p_sw != (ftree_sw_t *)cl_qmap_end(&p_ftree->sw_tbl); + p_sw = (ftree_sw_t *)cl_qmap_next(&p_sw->map_item) ) + { + if (p_sw->rank == i) + __osm_ftree_sw_dump(p_ftree, p_sw); + } + } + + osm_log(&p_ftree->p_osm->log, OSM_LOG_DEBUG,"__osm_ftree_fabric_dump: \n" + " |---------------------------------------|\n" + " |- Full fabric topology dump completed -|\n" + " |---------------------------------------|\n\n"); +} /* __osm_ftree_fabric_dump() */ + +/***************************************************/ + +static void +__osm_ftree_fabric_dump_general_info( + IN ftree_fabric_t * p_ftree) +{ + uint32_t i,j; + ftree_sw_t * p_sw; + char * addition_str; + + osm_log(&p_ftree->p_osm->log, OSM_LOG_INFO, + "__osm_ftree_fabric_dump_general_info: " + "General fabric topology info\n"); + osm_log(&p_ftree->p_osm->log, OSM_LOG_INFO,"__osm_ftree_fabric_dump_general_info: " + "============================\n"); + + osm_log(&p_ftree->p_osm->log, OSM_LOG_INFO, + "__osm_ftree_fabric_dump_general_info: " + " - FatTree rank (switches only): %u\n", + p_ftree->tree_rank); + osm_log(&p_ftree->p_osm->log, OSM_LOG_INFO, + "__osm_ftree_fabric_dump_general_info: " + " - Fabric has %u HCAs, %u switches\n", + cl_qmap_count(&p_ftree->hca_tbl), + cl_qmap_count(&p_ftree->sw_tbl)); + + for (i = 0; i < __osm_ftree_fabric_get_rank(p_ftree); i++) + { + j = 0; + for ( p_sw = (ftree_sw_t *)cl_qmap_head(&p_ftree->sw_tbl); + p_sw != (ftree_sw_t *)cl_qmap_end(&p_ftree->sw_tbl); + p_sw = (ftree_sw_t *)cl_qmap_next(&p_sw->map_item) ) + { + if (p_sw->rank == i) + j++; + } + if (i == 0) + addition_str = " (root) "; + else + if (i == (__osm_ftree_fabric_get_rank(p_ftree) - 1)) + addition_str = " (leaf) "; + else + addition_str = " "; + osm_log(&p_ftree->p_osm->log, OSM_LOG_INFO, + "__osm_ftree_fabric_dump_general_info: " + " - Fabric has %u rank %u%s switches\n", + j, i, addition_str); + } + + if (osm_log_is_active(&p_ftree->p_osm->log, OSM_LOG_VERBOSE)) + { + osm_log(&p_ftree->p_osm->log, OSM_LOG_VERBOSE, + "__osm_ftree_fabric_dump_general_info: " + " - Root switches:\n"); + for ( p_sw = (ftree_sw_t *)cl_qmap_head(&p_ftree->sw_tbl); + p_sw != (ftree_sw_t *)cl_qmap_end(&p_ftree->sw_tbl); + p_sw = (ftree_sw_t *)cl_qmap_next(&p_sw->map_item) ) + { + if (p_sw->rank == 0) + osm_log(&p_ftree->p_osm->log, OSM_LOG_VERBOSE, + "__osm_ftree_fabric_dump_general_info: " + " GUID: 0x%016" PRIx64 ", LID: 0x%x, Index %s\n", + cl_ntoh64(osm_node_get_node_guid(osm_switch_get_node_ptr(p_sw->p_osm_sw))), + cl_ntoh16(p_sw->base_lid), + __osm_ftree_tuple_to_str(p_sw->tuple)); + } + + osm_log(&p_ftree->p_osm->log, OSM_LOG_VERBOSE, + "__osm_ftree_fabric_dump_general_info: " + " - Leaf switches (sorted by index):\n"); + for (i = 0; i < p_ftree->leaf_switches_num; i++) + { + osm_log(&p_ftree->p_osm->log, OSM_LOG_VERBOSE, + "__osm_ftree_fabric_dump_general_info: " + " GUID: 0x%016" PRIx64 ", LID: 0x%x, Index %s\n", + cl_ntoh64(osm_node_get_node_guid( + osm_switch_get_node_ptr( + p_ftree->leaf_switches[i]->p_osm_sw))), + cl_ntoh16(p_ftree->leaf_switches[i]->base_lid), + __osm_ftree_tuple_to_str(p_ftree->leaf_switches[i]->tuple)); + } + } +} /* __osm_ftree_fabric_dump_general_info() */ + +/***************************************************/ + +static void +__osm_ftree_fabric_dump_hca_ordering( + IN ftree_fabric_t * p_ftree) +{ + ftree_hca_t * p_hca; + ftree_sw_t * p_sw; + ftree_port_group_t * p_group; + uint32_t i; + uint32_t j; + + char desc[IB_NODE_DESCRIPTION_SIZE + 1]; + char path[1024]; + FILE * p_hca_ordering_file; + char * filename = "osm-ftree-ca-order.dump"; + + snprintf(path, sizeof(path), "%s/%s", + p_ftree->p_osm->subn.opt.dump_files_dir, filename); + p_hca_ordering_file = fopen(path, "w"); + if (!p_hca_ordering_file) + { + osm_log(&p_ftree->p_osm->log, OSM_LOG_ERROR, + "__osm_ftree_fabric_dump_hca_ordering: ERR AB01: " + "cannot open file \'%s\': %s\n", + filename, strerror(errno)); + OSM_LOG_EXIT(&p_ftree->p_osm->log); + return; + } + + /* for each leaf switch (in indexing order) */ + for(i = 0; i < p_ftree->leaf_switches_num; i++) + { + p_sw = p_ftree->leaf_switches[i]; + /* for each real HCA connected to this switch */ + for (j = 0; j < p_sw->down_port_groups_num; j++) + { + p_group = p_sw->down_port_groups[j]; + p_hca = p_group->remote_hca_or_sw.remote_hca; + memcpy(desc,p_hca->p_osm_node->node_desc.description,IB_NODE_DESCRIPTION_SIZE); + desc[IB_NODE_DESCRIPTION_SIZE] = '\0'; + + fprintf(p_hca_ordering_file,"0x%x\t%s\n", + cl_ntoh16(p_group->remote_base_lid), desc); + } + + /* now print dummy HCAs */ + for (j = p_sw->down_port_groups_num; j < p_ftree->max_hcas_per_leaf; j++) + { + fprintf(p_hca_ordering_file,"0xFFFF\tDUMMY\n"); + } + + } + /* done going through all the leaf switches */ + + fclose(p_hca_ordering_file); +} /* __osm_ftree_fabric_dump_hca_ordering() */ + +/***************************************************/ + +static void +__osm_ftree_fabric_assign_tuple( + IN ftree_fabric_t * p_ftree, + IN ftree_sw_t * p_sw, + IN ftree_tuple_t new_tuple) +{ + memcpy(p_sw->tuple, new_tuple, FTREE_TUPLE_LEN); + __osm_ftree_fabric_add_sw_by_tuple(p_ftree,p_sw); +} + +/***************************************************/ + +static void +__osm_ftree_fabric_assign_first_tuple( + IN ftree_fabric_t * p_ftree, + IN ftree_sw_t * p_sw) +{ + uint8_t i; + ftree_tuple_t new_tuple; + + __osm_ftree_tuple_init(new_tuple); + new_tuple[0] = p_sw->rank; + for (i = 1; i <= p_sw->rank; i++) + new_tuple[i] = 0; + + __osm_ftree_fabric_assign_tuple(p_ftree,p_sw,new_tuple); +} + +/***************************************************/ + +static void +__osm_ftree_fabric_get_new_tuple( + IN ftree_fabric_t * p_ftree, + OUT ftree_tuple_t new_tuple, + IN ftree_tuple_t from_tuple, + IN ftree_direction_t direction) +{ + ftree_sw_t * p_sw; + ftree_tuple_t temp_tuple; + uint8_t var_index; + uint8_t i; + + __osm_ftree_tuple_init(new_tuple); + memcpy(temp_tuple, from_tuple, FTREE_TUPLE_LEN); + + if (direction == FTREE_DIRECTION_DOWN) + { + temp_tuple[0] ++; + var_index = from_tuple[0] + 1; + } + else + { + temp_tuple[0] --; + var_index = from_tuple[0]; + } + + for (i = 0; i < 0xFF; i++) + { + temp_tuple[var_index] = i; + p_sw = __osm_ftree_fabric_get_sw_by_tuple(p_ftree,temp_tuple); + if (p_sw == NULL) /* found free tuple */ + break; + } + + if (i == 0xFF) + { + /* new tuple not found - there are more than 255 ports in one direction */ + return; + } + memcpy(new_tuple, temp_tuple, FTREE_TUPLE_LEN); + +} /* __osm_ftree_fabric_get_new_tuple() */ + +/***************************************************/ + +static void +__osm_ftree_fabric_calculate_rank( + IN ftree_fabric_t * p_ftree) +{ + ftree_sw_t * p_sw; + ftree_sw_t * p_next_sw; + uint16_t max_rank = 0; + + /* go over all the switches and find maximal switch rank */ + + p_next_sw = (ftree_sw_t *)cl_qmap_head(&p_ftree->sw_tbl); + while( p_next_sw != (ftree_sw_t *)cl_qmap_end(&p_ftree->sw_tbl) ) + { + p_sw = p_next_sw; + if(p_sw->rank > max_rank) + max_rank = p_sw->rank; + p_next_sw = (ftree_sw_t *)cl_qmap_next(&p_sw->map_item ); + } + + /* set FatTree rank */ + __osm_ftree_fabric_set_rank(p_ftree, max_rank + 1); +} + +/***************************************************/ + +static void +__osm_ftree_fabric_make_indexing( + IN ftree_fabric_t * p_ftree) +{ + ftree_sw_t * p_remote_sw; + ftree_sw_t * p_sw; + ftree_sw_t * p_next_sw; + ftree_tuple_t new_tuple; + uint32_t i; + cl_list_t bfs_list; + ftree_sw_tbl_element_t * p_sw_tbl_element; + + OSM_LOG_ENTER(&p_ftree->p_osm->log, __osm_ftree_fabric_make_indexing); + + osm_log(&p_ftree->p_osm->log, OSM_LOG_VERBOSE,"__osm_ftree_fabric_make_indexing: " + "Starting FatTree indexing\n"); + + /* create array of leaf switches */ + p_ftree->leaf_switches = (ftree_sw_t **) + malloc(cl_qmap_count(&p_ftree->sw_tbl) * sizeof(ftree_sw_t *)); + + /* Looking for a leaf switch - the one that has rank equal to (tree_rank - 1). + This switch will be used as a starting point for indexing algorithm. */ + + p_next_sw = (ftree_sw_t *)cl_qmap_head(&p_ftree->sw_tbl); + while( p_next_sw != (ftree_sw_t *)cl_qmap_end( &p_ftree->sw_tbl ) ) + { + p_sw = p_next_sw; + if(p_sw->rank == (__osm_ftree_fabric_get_rank(p_ftree) - 1)) + break; + p_next_sw = (ftree_sw_t *)cl_qmap_next(&p_sw->map_item ); + } + + CL_ASSERT(p_next_sw != (ftree_sw_t *)cl_qmap_end(&p_ftree->sw_tbl)); + + /* Assign the first tuple to the switch that is used as BFS starting point. + The tuple will be as follows: [rank].0.0.0... + This fuction also adds the switch it into the switch_by_tuple table. */ + __osm_ftree_fabric_assign_first_tuple(p_ftree,p_sw); + + osm_log(&p_ftree->p_osm->log, OSM_LOG_VERBOSE, + "__osm_ftree_fabric_make_indexing: Indexing starting point:\n" + " - Switch rank : %u\n" + " - Switch index : %s\n" + " - Node LID : 0x%x\n" + " - Node GUID : 0x%016" PRIx64 "\n", + p_sw->rank, + __osm_ftree_tuple_to_str(p_sw->tuple), + cl_ntoh16(p_sw->base_lid), + cl_ntoh64(osm_node_get_node_guid(osm_switch_get_node_ptr(p_sw->p_osm_sw)))); + + /* + * Now run BFS and assign indexes to all switches + * Pseudo code of the algorithm is as follows: + * + * * Add first switch to BFS queue + * * While (BFS queue not empty) + * - Pop the switch from the head of the queue + * - Scan all the downward and upward ports + * - For each port + * + Get the remote switch + * + Assign index to the remote switch + * + Add remote switch to the BFS queue + */ + + cl_list_init(&bfs_list, cl_qmap_count(&p_ftree->sw_tbl)); + cl_list_insert_tail(&bfs_list, &__osm_ftree_sw_tbl_element_create(p_sw)->map_item); + + while (!cl_is_list_empty(&bfs_list)) + { + p_sw_tbl_element = (ftree_sw_tbl_element_t *)cl_list_remove_head(&bfs_list); + p_sw = p_sw_tbl_element->p_sw; + __osm_ftree_sw_tbl_element_destroy(p_sw_tbl_element); + + /* Discover all the nodes from ports that are pointing down */ + + if (p_sw->rank == (__osm_ftree_fabric_get_rank(p_ftree) - 1)) + { + /* add switch to leaf switches array */ + p_ftree->leaf_switches[p_ftree->leaf_switches_num++] = p_sw; + /* update the max_hcas_per_leaf value */ + if (p_sw->down_port_groups_num > p_ftree->max_hcas_per_leaf) + p_ftree->max_hcas_per_leaf = p_sw->down_port_groups_num; + } + else + { + /* This is not the leaf switch, which means that all the + ports that point down are taking us to another switches. + No need to assign indexing to HCAs */ + for( i = 0; i < p_sw->down_port_groups_num; i++ ) + { + p_remote_sw = p_sw->down_port_groups[i]->remote_hca_or_sw.remote_sw; + if (__osm_ftree_tuple_assigned(p_remote_sw->tuple)) + { + /* this switch has been already indexed */ + continue; + } + /* allocate new tuple */ + __osm_ftree_fabric_get_new_tuple(p_ftree, + new_tuple, + p_sw->tuple, + FTREE_DIRECTION_DOWN); + /* Assign the new tuple to the remote switch. + This fuction also adds the switch into the switch_by_tuple table. */ + __osm_ftree_fabric_assign_tuple(p_ftree, + p_remote_sw, + new_tuple); + + /* add the newly discovered switch to the BFS queue */ + cl_list_insert_tail(&bfs_list, + &__osm_ftree_sw_tbl_element_create(p_remote_sw)->map_item); + } + /* Done assigning indexes to all the remote switches + that are pointed by the downgoing ports. + Now sort port groups according to remote index. */ + qsort(p_sw->down_port_groups, /* array */ + p_sw->down_port_groups_num, /* number of elements */ + sizeof(ftree_port_group_t *), /* size of each element */ + __osm_ftree_compare_port_groups_by_remote_switch_index); /* comparator */ + } + + /* Done indexing switches from ports that go down. + Now do the same with ports that are pointing up. */ + + if (p_sw->rank != 0) + { + /* This is not the root switch, which means that all the ports + that are pointing up are taking us to another switches. */ + for( i = 0; i < p_sw->up_port_groups_num; i++ ) + { + p_remote_sw = p_sw->up_port_groups[i]->remote_hca_or_sw.remote_sw; + if (__osm_ftree_tuple_assigned(p_remote_sw->tuple)) + continue; + /* allocate new tuple */ + __osm_ftree_fabric_get_new_tuple(p_ftree, + new_tuple, + p_sw->tuple, + FTREE_DIRECTION_UP); + /* Assign the new tuple to the remote switch. + This fuction also adds the switch to the + switch_by_tuple table. */ + __osm_ftree_fabric_assign_tuple(p_ftree, + p_remote_sw, + new_tuple); + /* add the newly discovered switch to the BFS queue */ + cl_list_insert_tail(&bfs_list, + &__osm_ftree_sw_tbl_element_create(p_remote_sw)->map_item); + } + /* Done assigning indexes to all the remote switches + that are pointed by the upgoing ports. + Now sort port groups according to remote index. */ + qsort(p_sw->up_port_groups, /* array */ + p_sw->up_port_groups_num, /* number of elements */ + sizeof(ftree_port_group_t *), /* size of each element */ + __osm_ftree_compare_port_groups_by_remote_switch_index); /* comparator */ + } + /* Done assigning indexes to all the switches that are directly connected + to the current switch - go to the next switch in the BFS queue */ + } + + /* sort array of leaf switches by index */ + qsort(p_ftree->leaf_switches, /* array */ + p_ftree->leaf_switches_num, /* number of elements */ + sizeof(ftree_sw_t *), /* size of each element */ + __osm_ftree_compare_switches_by_index); /* comparator */ + + OSM_LOG_EXIT(&p_ftree->p_osm->log); +} /* __osm_ftree_fabric_make_indexing() */ + +/***************************************************/ + +static boolean_t +__osm_ftree_fabric_validate_topology( + IN ftree_fabric_t * p_ftree) +{ + ftree_port_group_t * p_group; + ftree_port_group_t * p_ref_group; + ftree_sw_t * p_sw; + ftree_sw_t * p_next_sw; + ftree_sw_t ** reference_sw_arr; + uint16_t tree_rank = __osm_ftree_fabric_get_rank(p_ftree); + boolean_t res = TRUE; + uint8_t i; + + OSM_LOG_ENTER(&p_ftree->p_osm->log, __osm_ftree_fabric_validate_topology); + + osm_log(&p_ftree->p_osm->log, OSM_LOG_VERBOSE, + "__osm_ftree_fabric_validate_topology: " + "Validating fabric topology\n"); + + reference_sw_arr = (ftree_sw_t **)malloc(tree_rank * sizeof(ftree_sw_t *)); + if ( reference_sw_arr == NULL ) + { + osm_log(&p_ftree->p_osm->log, OSM_LOG_SYS, + "Fat-tree routing: Memory allocation failed\n"); + return FALSE; + } + memset(reference_sw_arr, 0, tree_rank * sizeof(ftree_sw_t *)); + + p_next_sw = (ftree_sw_t *)cl_qmap_head(&p_ftree->sw_tbl); + while( res && + p_next_sw != (ftree_sw_t *)cl_qmap_end( &p_ftree->sw_tbl ) ) + { + p_sw = p_next_sw; + p_next_sw = (ftree_sw_t *)cl_qmap_next(&p_sw->map_item ); + + if (!reference_sw_arr[p_sw->rank]) + { + /* This is the first switch in the current level that + we're checking - use it as a reference */ + reference_sw_arr[p_sw->rank] = p_sw; + } + else + { + /* compare this switch properties to the reference switch */ + + if ( reference_sw_arr[p_sw->rank]->up_port_groups_num != p_sw->up_port_groups_num ) + { + osm_log(&p_ftree->p_osm->log, OSM_LOG_ERROR, + "__osm_ftree_fabric_validate_topology: " + "ERR AB09: Different number of upward port groups on switches:\n" + " GUID 0x%016" PRIx64 ", LID 0x%x, Index %s - %u groups\n" + " GUID 0x%016" PRIx64 ", LID 0x%x, Index %s - %u groups\n", + cl_ntoh64(osm_node_get_node_guid(osm_switch_get_node_ptr(reference_sw_arr[p_sw->rank]->p_osm_sw))), + cl_ntoh16(reference_sw_arr[p_sw->rank]->base_lid), + __osm_ftree_tuple_to_str(reference_sw_arr[p_sw->rank]->tuple), + reference_sw_arr[p_sw->rank]->up_port_groups_num, + cl_ntoh64(osm_node_get_node_guid(osm_switch_get_node_ptr(p_sw->p_osm_sw))), + cl_ntoh16(p_sw->base_lid), + __osm_ftree_tuple_to_str(p_sw->tuple), + p_sw->up_port_groups_num); + res = FALSE; + break; + } + + if ( p_sw->rank != (__osm_ftree_fabric_get_rank(p_ftree) - 1) && + reference_sw_arr[p_sw->rank]->down_port_groups_num != p_sw->down_port_groups_num ) + { + /* we're allowing some hca's to be missing */ + osm_log(&p_ftree->p_osm->log, OSM_LOG_ERROR, + "__osm_ftree_fabric_validate_topology: " + "ERR AB0A: Different number of downward port groups on switches:\n" + " GUID 0x%016" PRIx64 ", LID 0x%x, Index %s - %u port groups\n" + " GUID 0x%016" PRIx64 ", LID 0x%x, Index %s - %u port groups\n", + cl_ntoh64(osm_node_get_node_guid(osm_switch_get_node_ptr(reference_sw_arr[p_sw->rank]->p_osm_sw))), + cl_ntoh16(reference_sw_arr[p_sw->rank]->base_lid), + __osm_ftree_tuple_to_str(reference_sw_arr[p_sw->rank]->tuple), + reference_sw_arr[p_sw->rank]->down_port_groups_num, + cl_ntoh64(osm_node_get_node_guid(osm_switch_get_node_ptr(p_sw->p_osm_sw))), + cl_ntoh16(p_sw->base_lid), + __osm_ftree_tuple_to_str(p_sw->tuple), + p_sw->down_port_groups_num); + res = FALSE; + break; + } + + if ( reference_sw_arr[p_sw->rank]->up_port_groups_num != 0 ) + { + p_ref_group = reference_sw_arr[p_sw->rank]->up_port_groups[0]; + for (i = 0; i < p_sw->up_port_groups_num; i++) + { + p_group = p_sw->up_port_groups[i]; + if (cl_ptr_vector_get_size(&p_ref_group->ports) != cl_ptr_vector_get_size(&p_group->ports)) + { + osm_log(&p_ftree->p_osm->log, OSM_LOG_ERROR, + "__osm_ftree_fabric_validate_topology: " + "ERR AB0B: Different number of ports in an upward port group on switches:\n" + " GUID 0x%016" PRIx64 ", LID 0x%x, Index %s - %u ports\n" + " GUID 0x%016" PRIx64 ", LID 0x%x, Index %s - %u ports\n", + cl_ntoh64(osm_node_get_node_guid(osm_switch_get_node_ptr(reference_sw_arr[p_sw->rank]->p_osm_sw))), + cl_ntoh16(reference_sw_arr[p_sw->rank]->base_lid), + __osm_ftree_tuple_to_str(reference_sw_arr[p_sw->rank]->tuple), + cl_ptr_vector_get_size(&p_ref_group->ports), + cl_ntoh64(osm_node_get_node_guid(osm_switch_get_node_ptr(p_sw->p_osm_sw))), + cl_ntoh16(p_sw->base_lid), + __osm_ftree_tuple_to_str(p_sw->tuple), + cl_ptr_vector_get_size(&p_group->ports)); + res = FALSE; + break; + } + } + } + if ( reference_sw_arr[p_sw->rank]->down_port_groups_num != 0 && + p_sw->rank != (tree_rank - 1) ) + { + /* we're allowing some hca's to be missing */ + p_ref_group = reference_sw_arr[p_sw->rank]->down_port_groups[0]; + for (i = 0; i < p_sw->down_port_groups_num; i++) + { + p_group = p_sw->down_port_groups[0]; + if (cl_ptr_vector_get_size(&p_ref_group->ports) != cl_ptr_vector_get_size(&p_group->ports)) + { + osm_log(&p_ftree->p_osm->log, OSM_LOG_ERROR, + "__osm_ftree_fabric_validate_topology: " + "ERR AB0C: Different number of ports in an downward port group on switches:\n" + " GUID 0x%016" PRIx64 ", LID 0x%x, Index %s - %u ports\n" + " GUID 0x%016" PRIx64 ", LID 0x%x, Index %s - %u ports\n", + cl_ntoh64(osm_node_get_node_guid(osm_switch_get_node_ptr(reference_sw_arr[p_sw->rank]->p_osm_sw))), + cl_ntoh16(reference_sw_arr[p_sw->rank]->base_lid), + __osm_ftree_tuple_to_str(reference_sw_arr[p_sw->rank]->tuple), + cl_ptr_vector_get_size(&p_ref_group->ports), + cl_ntoh64(osm_node_get_node_guid(osm_switch_get_node_ptr(p_sw->p_osm_sw))), + cl_ntoh16(p_sw->base_lid), + __osm_ftree_tuple_to_str(p_sw->tuple), + cl_ptr_vector_get_size(&p_group->ports)); + res = FALSE; + break; + } + } + } + } /* end of else */ + } /* end of while */ + + if (res == TRUE) + osm_log(&p_ftree->p_osm->log, OSM_LOG_VERBOSE, + "__osm_ftree_fabric_validate_topology: " + "Fabric topology has been identified as FatTree\n"); + else + osm_log(&p_ftree->p_osm->log, OSM_LOG_ERROR, + "__osm_ftree_fabric_validate_topology: " + "ERR AB0D: Fabric topology hasn't been identified as FatTree\n"); + + free(reference_sw_arr); + OSM_LOG_EXIT(&p_ftree->p_osm->log); + return res; +} /* __osm_ftree_fabric_validate_topology() */ + +/*************************************************** + ***************************************************/ + +static void +__osm_ftree_set_sw_fwd_table( + IN cl_map_item_t* const p_map_item, + IN void *context) +{ + ftree_sw_t * p_sw = (ftree_sw_t * const) p_map_item; + ftree_fabric_t * p_ftree = (ftree_fabric_t *)context; + + /* calculate lft length rounded up to a multiple of 64 (block length) */ + uint16_t lft_len = 64 * ((p_ftree->lft_max_lid_ho + 1 + 63) / 64); + + p_sw->p_osm_sw->max_lid_ho = p_ftree->lft_max_lid_ho; + + memcpy(p_ftree->p_osm->sm.ucast_mgr.lft_buf, + p_sw->lft_buf, + lft_len); + osm_ucast_mgr_set_fwd_table(&p_ftree->p_osm->sm.ucast_mgr, p_sw->p_osm_sw); +} + +/*************************************************** + ***************************************************/ + +/* + * Function: assign-up-going-port-by-descending-down + * Given : a switch and a LID + * Pseudo code: + * foreach down-going-port-group (in indexing order) + * skip this group if the LFT(LID) port is part of this group + * find the least loaded port of the group (scan in indexing order) + * r-port is the remote port connected to it + * assign the remote switch node LFT(LID) to r-port + * increase r-port usage counter + * assign-up-going-port-by-descending-down to r-port node (recursion) + */ + +static void +__osm_ftree_fabric_route_upgoing_by_going_down( + IN ftree_fabric_t * p_ftree, + IN ftree_sw_t * p_sw, + IN ftree_sw_t * p_prev_sw, + IN ib_net16_t target_lid, + IN uint8_t target_rank, + IN boolean_t is_real_lid, + IN boolean_t is_main_path, + IN uint8_t highest_rank_in_route) +{ + ftree_sw_t * p_remote_sw; + uint16_t ports_num; + ftree_port_group_t * p_group; + ftree_port_t * p_port; + ftree_port_t * p_min_port; + uint16_t i; + uint16_t j; + + /* we shouldn't enter here if both real_lid and main_path are false */ + CL_ASSERT(is_real_lid || is_main_path); + + /* can't be here for leaf switch, */ + CL_ASSERT(p_sw->rank != (__osm_ftree_fabric_get_rank(p_ftree) - 1)); + + /* if there is no down-going ports */ + if (p_sw->down_port_groups_num == 0) + return; + + /* foreach down-going port group (in indexing order) */ + for (i = 0; i < p_sw->down_port_groups_num; i++) + { + p_group = p_sw->down_port_groups[i]; + + if ( p_prev_sw && (p_group->remote_base_lid == p_prev_sw->base_lid) ) + { + /* This port group has a port that was used when we entered this switch, + which means that the current group points to the switch where we were + at the previous step of the algorithm (before going up). + Skipping this group. */ + continue; + } + + /* find the least loaded port of the group (in indexing order) */ + p_min_port = NULL; + ports_num = (uint16_t)cl_ptr_vector_get_size(&p_group->ports); + /* ToDo: no need to select a least loaded port for non-main path. + Think about optimization. */ + for (j = 0; j < ports_num; j++) + { + cl_ptr_vector_at(&p_group->ports, j, (void **)&p_port); + if (!p_min_port) + { + /* first port that we're checking - set as port with the lowest load */ + p_min_port = p_port; + } + else if (p_port->counter_up < p_min_port->counter_up) + { + /* this port is less loaded - use it as min */ + p_min_port = p_port; + } + } + /* At this point we have selected a port in this group with the + lowest load of upgoing routes. + Set on the remote switch how to get to the target_lid - + set LFT(target_lid) on the remote switch to the remote port */ + p_remote_sw = p_group->remote_hca_or_sw.remote_sw; + + /* Four possible cases: + * + * 1. is_real_lid == TRUE && is_main_path == TRUE: + * - going DOWN(TRUE,TRUE) through ALL the groups + * + promoting port counter + * + setting path in remote switch fwd tbl + * + setting hops in remote switch on all the ports of each group + * + * 2. is_real_lid == TRUE && is_main_path == FALSE: + * - going DOWN(TRUE,FALSE) through ALL the groups but only if + * the remote (upper) switch hasn't been already configured + * for this target LID + * + NOT promoting port counter + * + setting path in remote switch fwd tbl if it hasn't been set yet + * + setting hops in remote switch on all the ports of each group + * if it hasn't been set yet + * + * 3. is_real_lid == FALSE && is_main_path == TRUE: + * - going DOWN(FALSE,TRUE) through ALL the groups + * + promoting port counter + * + NOT setting path in remote switch fwd tbl + * + NOT setting hops in remote switch + * + * 4. is_real_lid == FALSE && is_main_path == FALSE: + * - illegal state - we shouldn't get here + */ + + /* second case: skip the port group if the remote (upper) + switch has been already configured for this target LID */ + if ( is_real_lid && !is_main_path && + __osm_ftree_sw_get_fwd_table_block(p_remote_sw, + cl_ntoh16(target_lid)) != OSM_NO_PATH ) + continue; + + /* setting fwd tbl port only if this is real LID */ + if (is_real_lid) + { + __osm_ftree_sw_set_fwd_table_block(p_remote_sw, + cl_ntoh16(target_lid), + p_min_port->remote_port_num); + osm_log(&p_ftree->p_osm->log, OSM_LOG_DEBUG, + "__osm_ftree_fabric_route_upgoing_by_going_down: " + "Switch %s: set path to HCA LID 0x%x through port %u\n", + __osm_ftree_tuple_to_str(p_remote_sw->tuple), + cl_ntoh16(target_lid), + p_min_port->remote_port_num); + + /* On the remote switch that is pointed by the p_group, + set hops for ALL the ports in the remote group. */ + + for (j = 0; j < ports_num; j++) + { + cl_ptr_vector_at(&p_group->ports, j, (void **)&p_port); + + __osm_ftree_sw_set_hops(p_remote_sw, + p_ftree->lft_max_lid_ho, + cl_ntoh16(target_lid), + p_port->remote_port_num, + ( (target_rank - highest_rank_in_route) + + (p_remote_sw->rank - highest_rank_in_route) )); + } + + + } + + /* The number of upgoing routes is tracked in the + p_port->counter_up counter of the port that belongs to + the upper side of the link (on switch with lower rank). + Counter is promoted only if we're routing LID on the main + path (whether it's a real LID or a dummy one). */ + if (is_main_path) + p_min_port->counter_up++; + + /* Recursion step: + Assign upgoing ports by stepping down, starting on REMOTE switch. + Recursion stop condition - if the REMOTE switch is a leaf switch. */ + if (p_remote_sw->rank != (__osm_ftree_fabric_get_rank(p_ftree) - 1)) + { + __osm_ftree_fabric_route_upgoing_by_going_down( + p_ftree, + p_remote_sw, /* remote switch - used as a route-upgoing alg. start point */ + NULL, /* prev. position - NULL to mark that we went down and not up */ + target_lid, /* LID that we're routing to */ + target_rank, /* rank of the LID that we're routing to */ + is_real_lid, /* whether the target LID is real or dummy */ + is_main_path, /* whether this is path to HCA that should by tracked by counters */ + highest_rank_in_route); /* highest visited point in the tree before going down */ + } + } + /* done scanning all the down-going port groups */ + +} /* __osm_ftree_fabric_route_upgoing_by_going_down() */ + +/***************************************************/ + +/* + * Function: assign-down-going-port-by-descending-up + * Given : a switch and a LID + * Pseudo code: + * find the least loaded port of all the upgoing groups (scan in indexing order) + * assign the LFT(LID) of remote switch to that port + * track that port usage + * assign-up-going-port-by-descending-down on CURRENT switch + * assign-down-going-port-by-descending-up on REMOTE switch (recursion) + */ + +static void +__osm_ftree_fabric_route_downgoing_by_going_up( + IN ftree_fabric_t * p_ftree, + IN ftree_sw_t * p_sw, + IN ftree_sw_t * p_prev_sw, + IN ib_net16_t target_lid, + IN uint8_t target_rank, + IN boolean_t is_real_lid, + IN boolean_t is_main_path) +{ + ftree_sw_t * p_remote_sw; + uint16_t ports_num; + ftree_port_group_t * p_group; + ftree_port_t * p_port; + ftree_port_group_t * p_min_group; + ftree_port_t * p_min_port; + uint16_t i; + uint16_t j; + + /* we shouldn't enter here if both real_lid and main_path are false */ + CL_ASSERT(is_real_lid || is_main_path); + + /* If this switch isn't a leaf switch: + Assign upgoing ports by stepping down, starting on THIS switch. */ + if (p_sw->rank != (__osm_ftree_fabric_get_rank(p_ftree) - 1)) + { + __osm_ftree_fabric_route_upgoing_by_going_down( + p_ftree, + p_sw, /* local switch - used as a route-upgoing alg. start point */ + p_prev_sw, /* switch that we went up from (NULL means that we went down) */ + target_lid, /* LID that we're routing to */ + target_rank, /* rank of the LID that we're routing to */ + is_real_lid, /* whether this target LID is real or dummy */ + is_main_path, /* whether this path to HCA should by tracked by counters */ + p_sw->rank); /* the highest visited point in the tree before going down */ + } + + /* recursion stop condition - if it's a root switch, */ + if (p_sw->rank == 0) + return; + + /* Find the least loaded port of all the upgoing port groups + (in indexing order of the remote switches). */ + p_min_group = NULL; + p_min_port = NULL; + for (i = 0; i < p_sw->up_port_groups_num; i++) + { + p_group = p_sw->up_port_groups[i]; + + ports_num = (uint16_t)cl_ptr_vector_get_size(&p_group->ports); + for (j = 0; j < ports_num; j++) + { + cl_ptr_vector_at(&p_group->ports, j, (void **)&p_port); + if (!p_min_group) + { + /* first port that we're checking - use + it as a port with the lowest load */ + p_min_group = p_group; + p_min_port = p_port; + } + else + { + if ( p_port->counter_down < p_min_port->counter_down ) + { + /* this port is less loaded - use it as min */ + p_min_group = p_group; + p_min_port = p_port; + } + } + } + } + + /* At this point we have selected a group and port with the + lowest load of downgoing routes. + Set on the remote switch how to get to the target_lid - + set LFT(target_lid) on the remote switch to the remote port */ + p_remote_sw = p_min_group->remote_hca_or_sw.remote_sw; + + /* Four possible cases: + * + * 1. is_real_lid == TRUE && is_main_path == TRUE: + * - going UP(TRUE,TRUE) on selected min_group and min_port + * + promoting port counter + * + setting path in remote switch fwd tbl + * + setting hops in remote switch on all the ports of selected group + * - going UP(TRUE,FALSE) on rest of the groups, each time on port 0 + * + NOT promoting port counter + * + setting path in remote switch fwd tbl if it hasn't been set yet + * + setting hops in remote switch on all the ports of each group + * if it hasn't been set yet + * + * 2. is_real_lid == TRUE && is_main_path == FALSE: + * - going UP(TRUE,FALSE) on ALL the groups, each time on port 0, + * but only if the remote (upper) switch hasn't been already + * configured for this target LID + * + NOT promoting port counter + * + setting path in remote switch fwd tbl if it hasn't been set yet + * + setting hops in remote switch on all the ports of each group + * if it hasn't been set yet + * + * 3. is_real_lid == FALSE && is_main_path == TRUE: + * - going UP(FALSE,TRUE) ONLY on selected min_group and min_port + * + promoting port counter + * + NOT setting path in remote switch fwd tbl + * + NOT setting hops in remote switch + * + * 4. is_real_lid == FALSE && is_main_path == FALSE: + * - illegal state - we shouldn't get here + */ + + /* covering first half of case 1, and case 3 */ + if (is_main_path) + { + if (p_sw->rank == (__osm_ftree_fabric_get_rank(p_ftree) - 1)) + { + osm_log(&p_ftree->p_osm->log, OSM_LOG_DEBUG, + "__osm_ftree_fabric_route_downgoing_by_going_up: " + " - Routing MAIN path for %s HCA LID 0x%x: %s --> %s\n", + (is_real_lid)? "real" : "DUMMY", + cl_ntoh16(target_lid), + __osm_ftree_tuple_to_str(p_sw->tuple), + __osm_ftree_tuple_to_str(p_remote_sw->tuple)); + } + /* The number of downgoing routes is tracked in the + p_port->counter_down counter of the port that belongs to + the lower side of the link (on switch with higher rank) */ + p_min_port->counter_down++; + if (is_real_lid) + { + __osm_ftree_sw_set_fwd_table_block(p_remote_sw, + cl_ntoh16(target_lid), + p_min_port->remote_port_num); + osm_log(&p_ftree->p_osm->log, OSM_LOG_DEBUG, + "__osm_ftree_fabric_route_downgoing_by_going_up: " + "Switch %s: set path to HCA LID 0x%x through port %u\n", + __osm_ftree_tuple_to_str(p_remote_sw->tuple), + cl_ntoh16(target_lid),p_min_port->remote_port_num); + + /* On the remote switch that is pointed by the min_group, + set hops for ALL the ports in the remote group. */ + + ports_num = (uint16_t)cl_ptr_vector_get_size(&p_min_group->ports); + for (j = 0; j < ports_num; j++) + { + cl_ptr_vector_at(&p_min_group->ports, j, (void **)&p_port); + __osm_ftree_sw_set_hops(p_remote_sw, + p_ftree->lft_max_lid_ho, + cl_ntoh16(target_lid), + p_port->remote_port_num, + target_rank - p_remote_sw->rank); + } + } + + /* Recursion step: + Assign downgoing ports by stepping up, starting on REMOTE switch. */ + __osm_ftree_fabric_route_downgoing_by_going_up( + p_ftree, + p_remote_sw, /* remote switch - used as a route-downgoing alg. next step point */ + p_sw, /* this switch - prev. position switch for the function */ + target_lid, /* LID that we're routing to */ + target_rank, /* rank of the LID that we're routing to */ + is_real_lid, /* whether this target LID is real or dummy */ + is_main_path); /* whether this is path to HCA that should by tracked by counters */ + } + + /* we're done for the third case */ + if (!is_real_lid) + return; + + /* What's left to do at this point: + * + * 1. is_real_lid == TRUE && is_main_path == TRUE: + * - going UP(TRUE,FALSE) on rest of the groups, each time on port 0, + * but only if the remote (upper) switch hasn't been already + * configured for this target LID + * + NOT promoting port counter + * + setting path in remote switch fwd tbl if it hasn't been set yet + * + setting hops in remote switch on all the ports of each group + * if it hasn't been set yet + * + * 2. is_real_lid == TRUE && is_main_path == FALSE: + * - going UP(TRUE,FALSE) on ALL the groups, each time on port 0, + * but only if the remote (upper) switch hasn't been already + * configured for this target LID + * + NOT promoting port counter + * + setting path in remote switch fwd tbl if it hasn't been set yet + * + setting hops in remote switch on all the ports of each group + * if it hasn't been set yet + * + * These two rules can be rephrased this way: + * - foreach UP port group + * + if remote switch has been set with the target LID + * - skip this port group + * + else + * - select port 0 + * - do NOT promote port counter + * - set path in remote switch fwd tbl + * - set hops in remote switch on all the ports of this group + * - go UP(TRUE,FALSE) to the remote switch + */ + + for (i = 0; i < p_sw->up_port_groups_num; i++) + { + p_group = p_sw->up_port_groups[i]; + p_remote_sw = p_group->remote_hca_or_sw.remote_sw; + + /* skip if target lid has been already set on remote switch fwd tbl */ + if (__osm_ftree_sw_get_fwd_table_block( + p_remote_sw,cl_ntoh16(target_lid)) != OSM_NO_PATH) + continue; + + if (p_sw->rank == (__osm_ftree_fabric_get_rank(p_ftree) - 1)) + { + osm_log(&p_ftree->p_osm->log, OSM_LOG_DEBUG, + "__osm_ftree_fabric_route_downgoing_by_going_up: " + " - Routing SECONDARY path for LID 0x%x: %s --> %s\n", + cl_ntoh16(target_lid), + __osm_ftree_tuple_to_str(p_sw->tuple), + __osm_ftree_tuple_to_str(p_remote_sw->tuple)); + } + + cl_ptr_vector_at(&p_group->ports, 0, (void **)&p_port); + __osm_ftree_sw_set_fwd_table_block(p_remote_sw, + cl_ntoh16(target_lid), + p_port->remote_port_num); + + /* On the remote switch that is pointed by the p_group, + set hops for ALL the ports in the remote group. */ + + ports_num = (uint16_t)cl_ptr_vector_get_size(&p_group->ports); + for (j = 0; j < ports_num; j++) + { + cl_ptr_vector_at(&p_group->ports, j, (void **)&p_port); + + __osm_ftree_sw_set_hops(p_remote_sw, + p_ftree->lft_max_lid_ho, + cl_ntoh16(target_lid), + p_port->remote_port_num, + target_rank - p_remote_sw->rank); + } + + /* Recursion step: + Assign downgoing ports by stepping up, starting on REMOTE switch. */ + __osm_ftree_fabric_route_downgoing_by_going_up( + p_ftree, + p_remote_sw, /* remote switch - used as a route-downgoing alg. next step point */ + p_sw, /* this switch - prev. position switch for the function */ + target_lid, /* LID that we're routing to */ + target_rank, /* rank of the LID that we're routing to */ + TRUE, /* whether the target LID is real or dummy */ + FALSE); /* whether this is path to HCA that should by tracked by counters */ + } + +} /* ftree_fabric_route_downgoing_by_going_up() */ + +/***************************************************/ + +/* + * Pseudo code: + * foreach leaf switch (in indexing order) + * for each compute node (in indexing order) + * obtain the LID of the compute node + * set local LFT(LID) of the port connecting to compute node + * call assign-down-going-port-by-descending-up(TRUE,TRUE) on CURRENT switch + * for each MISSING compute node + * call assign-down-going-port-by-descending-up(FALSE,TRUE) on CURRENT switch + */ + +static void +__osm_ftree_fabric_route_to_hcas( + IN ftree_fabric_t * p_ftree) +{ + ftree_sw_t * p_sw; + ftree_port_group_t * p_group; + ftree_port_t * p_port; + uint32_t i; + uint32_t j; + ib_net16_t remote_lid; + + OSM_LOG_ENTER(&p_ftree->p_osm->log, __osm_ftree_fabric_route_to_hcas); + + /* for each leaf switch (in indexing order) */ + for(i = 0; i < p_ftree->leaf_switches_num; i++) + { + p_sw = p_ftree->leaf_switches[i]; + + /* for each HCA connected to this switch */ + for (j = 0; j < p_sw->down_port_groups_num; j++) + { + /* obtain the LID of HCA port */ + p_group = p_sw->down_port_groups[j]; + remote_lid = p_group->remote_base_lid; + + /* set local LFT(LID) to the port that is connected to HCA */ + cl_ptr_vector_at(&p_group->ports, 0, (void **)&p_port); + __osm_ftree_sw_set_fwd_table_block(p_sw, + cl_ntoh16(remote_lid), + p_port->port_num); + osm_log(&p_ftree->p_osm->log, OSM_LOG_DEBUG, + "__osm_ftree_fabric_route_to_hcas: " + "Switch %s: set path to HCA LID 0x%x through port %u\n", + __osm_ftree_tuple_to_str(p_sw->tuple), + cl_ntoh16(remote_lid), + p_port->port_num); + + /* set local min hop table(LID) to route to the CA */ + __osm_ftree_sw_set_hops(p_sw, + p_ftree->lft_max_lid_ho, + cl_ntoh16(remote_lid), + p_port->port_num, + 1); + + /* assign downgoing ports by stepping up */ + __osm_ftree_fabric_route_downgoing_by_going_up( + p_ftree, + p_sw, /* local switch - used as a route-downgoing alg. start point */ + NULL, /* prev. position switch */ + remote_lid, /* LID that we're routing to */ + __osm_ftree_fabric_get_rank(p_ftree), /* rank of the LID that we're routing to */ + TRUE, /* whether this HCA LID is real or dummy */ + TRUE); /* whether this path to HCA should by tracked by counters */ + } + + /* We're done with the real HCAs. Now route the dummy HCAs that are missing. + When routing to dummy HCAs we don't fill lid matrices. */ + + if (p_ftree->max_hcas_per_leaf > p_sw->down_port_groups_num) + { + osm_log(&p_ftree->p_osm->log, OSM_LOG_DEBUG,"__osm_ftree_fabric_route_to_hcas: " + "Routing %u dummy HCAs\n", + p_ftree->max_hcas_per_leaf - p_sw->down_port_groups_num); + for ( j = 0; + ((int)j) < (p_ftree->max_hcas_per_leaf - p_sw->down_port_groups_num); + j++) + { + /* assign downgoing ports by stepping up */ + __osm_ftree_fabric_route_downgoing_by_going_up( + p_ftree, + p_sw, /* local switch - used as a route-downgoing alg. start point */ + NULL, /* prev. position switch */ + 0, /* LID that we're routing to - ignored for dummy HCA */ + 0, /* rank of the LID that we're routing to - ignored for dummy HCA */ + FALSE, /* whether this HCA LID is real or dummy */ + TRUE); /* whether this path to HCA should by tracked by counters */ + } + } + } + /* done going through all the leaf switches */ + OSM_LOG_EXIT(&p_ftree->p_osm->log); +} /* __osm_ftree_fabric_route_to_hcas() */ + +/***************************************************/ + +/* + * Pseudo code: + * foreach switch in fabric + * obtain its LID + * set local LFT(LID) to port 0 + * call assign-down-going-port-by-descending-up(TRUE,FALSE) on CURRENT switch + * + * Routing to switch is similar to routing a REAL hca lid on SECONDARY path: + * - we should set fwd tables + * - we should NOT update port counters + */ + +static void +__osm_ftree_fabric_route_to_switches( + IN ftree_fabric_t * p_ftree) +{ + ftree_sw_t * p_sw; + ftree_sw_t * p_next_sw; + + OSM_LOG_ENTER(&p_ftree->p_osm->log, __osm_ftree_fabric_route_to_switches); + + p_next_sw = (ftree_sw_t *)cl_qmap_head(&p_ftree->sw_tbl); + while( p_next_sw != (ftree_sw_t *)cl_qmap_end(&p_ftree->sw_tbl) ) + { + p_sw = p_next_sw; + p_next_sw = (ftree_sw_t *)cl_qmap_next(&p_sw->map_item ); + + /* set local LFT(LID) to 0 (route to itself) */ + __osm_ftree_sw_set_fwd_table_block(p_sw, + cl_ntoh16(p_sw->base_lid), + 0); + + osm_log(&p_ftree->p_osm->log, OSM_LOG_DEBUG, + "__osm_ftree_fabric_route_to_switches: " + "Switch %s (LID 0x%x): routing switch-to-switch pathes\n", + __osm_ftree_tuple_to_str(p_sw->tuple), + cl_ntoh16(p_sw->base_lid)); + + /* set min hop table of the switch to itself */ + __osm_ftree_sw_set_hops(p_sw, + p_ftree->lft_max_lid_ho, + cl_ntoh16(p_sw->base_lid), + 0, /* port_num */ + 0);/* hops */ + + __osm_ftree_fabric_route_downgoing_by_going_up( + p_ftree, + p_sw, /* local switch - used as a route-downgoing alg. start point */ + NULL, /* prev. position switch */ + p_sw->base_lid, /* LID that we're routing to */ + p_sw->rank, /* rank of the LID that we're routing to */ + TRUE, /* whether the target LID is a real or dummy */ + FALSE); /* whether this path should by tracked by counters */ + } + + OSM_LOG_EXIT(&p_ftree->p_osm->log); +} /* __osm_ftree_fabric_route_to_switches() */ + +/*************************************************** + ***************************************************/ + +static int +__osm_ftree_fabric_populate_switches( + IN ftree_fabric_t * p_ftree) +{ + osm_switch_t * p_osm_sw; + osm_switch_t * p_next_osm_sw; + + OSM_LOG_ENTER(&p_ftree->p_osm->log, __osm_ftree_fabric_populate_switches); + + p_next_osm_sw = (osm_switch_t *)cl_qmap_head(&p_ftree->p_osm->subn.sw_guid_tbl); + while( p_next_osm_sw != (osm_switch_t *)cl_qmap_end(&p_ftree->p_osm->subn.sw_guid_tbl) ) + { + p_osm_sw = p_next_osm_sw; + p_next_osm_sw = (osm_switch_t *)cl_qmap_next(&p_osm_sw->map_item ); + __osm_ftree_fabric_add_sw(p_ftree,p_osm_sw); + } + OSM_LOG_EXIT(&p_ftree->p_osm->log); + return 0; +} /* __osm_ftree_fabric_populate_switches() */ + +/*************************************************** + ***************************************************/ + +static int +__osm_ftree_fabric_populate_hcas( + IN ftree_fabric_t * p_ftree) +{ + osm_node_t * p_osm_node; + osm_node_t * p_next_osm_node; + + OSM_LOG_ENTER(&p_ftree->p_osm->log, __osm_ftree_fabric_populate_hcas); + + p_next_osm_node = (osm_node_t *)cl_qmap_head(&p_ftree->p_osm->subn.node_guid_tbl); + while( p_next_osm_node != (osm_node_t *)cl_qmap_end(&p_ftree->p_osm->subn.node_guid_tbl) ) + { + p_osm_node = p_next_osm_node; + p_next_osm_node = (osm_node_t *)cl_qmap_next(&p_osm_node->map_item); + switch (osm_node_get_type(p_osm_node)) + { + case IB_NODE_TYPE_CA: + __osm_ftree_fabric_add_hca(p_ftree,p_osm_node); + break; + case IB_NODE_TYPE_ROUTER: + break; + case IB_NODE_TYPE_SWITCH: + /* all the switches added separately */ + break; + default: + osm_log(&p_ftree->p_osm->log, OSM_LOG_ERROR, + "__osm_ftree_fabric_populate_hcas: ERR AB0E: " + "Node GUID 0x%016" PRIx64 " - Unknown node type: %s\n", + cl_ntoh64(osm_node_get_node_guid(p_osm_node)), + ib_get_node_type_str(osm_node_get_type(p_osm_node))); + OSM_LOG_EXIT(&p_ftree->p_osm->log); + return -1; + } + } + + OSM_LOG_EXIT(&p_ftree->p_osm->log); + return 0; +} /* __osm_ftree_fabric_populate_hcas() */ + +/*************************************************** + ***************************************************/ + +static void +__osm_ftree_rank_from_switch( + IN ftree_fabric_t * p_ftree, + IN ftree_sw_t * p_starting_sw) +{ + ftree_sw_t * p_sw; + ftree_sw_t * p_remote_sw; + osm_node_t * p_node; + osm_node_t * p_remote_node; + osm_physp_t * p_osm_port; + uint8_t i; + cl_list_t bfs_list; + ftree_sw_tbl_element_t * p_sw_tbl_element = NULL; + + p_starting_sw->rank = 0; + + /* Run BFS scan of the tree, starting from this switch */ + + cl_list_init(&bfs_list, cl_qmap_count(&p_ftree->sw_tbl)); + cl_list_insert_tail(&bfs_list, &__osm_ftree_sw_tbl_element_create(p_starting_sw)->map_item); + + while (!cl_is_list_empty(&bfs_list)) + { + p_sw_tbl_element = (ftree_sw_tbl_element_t *)cl_list_remove_head(&bfs_list); + p_sw = p_sw_tbl_element->p_sw; + __osm_ftree_sw_tbl_element_destroy(p_sw_tbl_element); + + p_node = osm_switch_get_node_ptr(p_sw->p_osm_sw); + + /* note: skipping port 0 on switches */ + for (i = 1; i < osm_node_get_num_physp(p_node); i++) + { + p_osm_port = osm_node_get_physp_ptr(p_node,i); + if (!osm_physp_is_valid(p_osm_port)) + continue; + if (!osm_link_is_healthy(p_osm_port)) + continue; + + p_remote_node = osm_node_get_remote_node(p_node,i,NULL); + if (!p_remote_node) + continue; + if (osm_node_get_type(p_remote_node) != IB_NODE_TYPE_SWITCH) + continue; + + p_remote_sw = (ftree_sw_t *)cl_qmap_get(&p_ftree->sw_tbl, + osm_node_get_node_guid(p_remote_node)); + if (p_remote_sw == (ftree_sw_t *)cl_qmap_end(&p_ftree->sw_tbl)) + { + /* remote node is not a switch */ + continue; + } + if (__osm_ftree_sw_ranked(p_remote_sw) && p_remote_sw->rank <= (p_sw->rank + 1)) + continue; + + /* rank the remote switch and add it to the BFS list */ + p_remote_sw->rank = p_sw->rank + 1; + cl_list_insert_tail(&bfs_list, + &__osm_ftree_sw_tbl_element_create(p_remote_sw)->map_item); + } + } +} /* __osm_ftree_rank_from_switch() */ + + +/*************************************************** + ***************************************************/ + +static int +__osm_ftree_rank_switches_from_hca( + IN ftree_fabric_t * p_ftree, + IN ftree_hca_t * p_hca) +{ + ftree_sw_t * p_sw; + osm_node_t * p_osm_node = p_hca->p_osm_node; + osm_node_t * p_remote_osm_node; + osm_physp_t * p_osm_port; + static uint8_t i = 0; + int res = 0; + + OSM_LOG_ENTER(&p_ftree->p_osm->log, __osm_ftree_rank_switches_from_hca); + + for (i = 0; i < osm_node_get_num_physp(p_osm_node); i++) + { + p_osm_port = osm_node_get_physp_ptr(p_osm_node,i); + if (!osm_physp_is_valid(p_osm_port)) + continue; + if (!osm_link_is_healthy(p_osm_port)) + continue; + + p_remote_osm_node = osm_node_get_remote_node(p_osm_node,i,NULL); + + switch (osm_node_get_type(p_remote_osm_node)) + { + case IB_NODE_TYPE_CA: + /* HCA connected directly to another HCA - not FatTree */ + osm_log(&p_ftree->p_osm->log, OSM_LOG_ERROR, + "__osm_ftree_rank_switches_from_hca: ERR AB0F: " + "HCA conected directly to another HCA: " + "0x%016" PRIx64 " <---> 0x%016" PRIx64 "\n", + cl_ntoh64(osm_node_get_node_guid(p_hca->p_osm_node)), + cl_ntoh64(osm_node_get_node_guid(p_remote_osm_node))); + res = -1; + goto Exit; + + case IB_NODE_TYPE_ROUTER: + /* leaving this port - proceeding to the next one */ + continue; + + case IB_NODE_TYPE_SWITCH: + /* continue with this port */ + break; + + default: + osm_log(&p_ftree->p_osm->log, OSM_LOG_ERROR, + "__osm_ftree_rank_switches_from_hca: ERR AB10: " + "Node GUID 0x%016" PRIx64 " - Unknown node type: %s\n", + cl_ntoh64(osm_node_get_node_guid(p_remote_osm_node)), + ib_get_node_type_str(osm_node_get_type(p_remote_osm_node))); + res = -1; + goto Exit; + } + + /* remote node is switch */ + + p_sw = (ftree_sw_t *)cl_qmap_get(&p_ftree->sw_tbl, + p_osm_port->p_remote_physp->p_node->node_info.node_guid); + + CL_ASSERT(p_sw != (ftree_sw_t *)cl_qmap_end(&p_ftree->sw_tbl)); + + if (__osm_ftree_sw_ranked(p_sw) && p_sw->rank == 0) + continue; + + osm_log(&p_ftree->p_osm->log, OSM_LOG_DEBUG, + "__osm_ftree_rank_switches_from_hca: " + "Marking rank of switch that is directly connected to HCA:\n" + " - HCA guid : 0x%016" PRIx64 "\n" + " - Switch guid: 0x%016" PRIx64 "\n" + " - Switch LID : 0x%x\n", + cl_ntoh64(osm_node_get_node_guid(p_hca->p_osm_node)), + cl_ntoh64(osm_node_get_node_guid(osm_switch_get_node_ptr(p_sw->p_osm_sw))), + cl_ntoh16(p_sw->base_lid)); + __osm_ftree_rank_from_switch(p_ftree, p_sw); + } + + Exit: + OSM_LOG_EXIT(&p_ftree->p_osm->log); + return res; +} /* __osm_ftree_rank_switches_from_hca() */ + +/***************************************************/ + +static void +__osm_ftree_sw_reverse_rank( + IN cl_map_item_t* const p_map_item, + IN void *context) +{ + ftree_fabric_t * p_ftree = (ftree_fabric_t *)context; + ftree_sw_t * p_sw = (ftree_sw_t * const) p_map_item; + p_sw->rank = __osm_ftree_fabric_get_rank(p_ftree) - p_sw->rank - 1; +} + +/*************************************************** + ***************************************************/ + +static int +__osm_ftree_fabric_construct_hca_ports( + IN ftree_fabric_t * p_ftree, + IN ftree_hca_t * p_hca) +{ + ftree_sw_t * p_remote_sw; + osm_node_t * p_node = p_hca->p_osm_node; + osm_node_t * p_remote_node; + uint8_t remote_node_type; + ib_net64_t remote_node_guid; + osm_physp_t * p_remote_osm_port; + uint8_t i; + uint8_t remote_port_num; + int res = 0; + + for (i = 0; i < osm_node_get_num_physp(p_node); i++) + { + osm_physp_t * p_osm_port = osm_node_get_physp_ptr(p_node,i); + + if (!osm_physp_is_valid(p_osm_port)) + continue; + if (!osm_link_is_healthy(p_osm_port)) + continue; + + p_remote_osm_port = osm_physp_get_remote(p_osm_port); + p_remote_node = osm_node_get_remote_node(p_node,i,&remote_port_num); + + if (!p_remote_osm_port) + continue; + + remote_node_type = osm_node_get_type(p_remote_node); + remote_node_guid = osm_node_get_node_guid(p_remote_node); + + switch (remote_node_type) + { + case IB_NODE_TYPE_ROUTER: + /* leaving this port - proceeding to the next one */ + continue; + + case IB_NODE_TYPE_CA: + /* HCA connected directly to another HCA - not FatTree */ + osm_log(&p_ftree->p_osm->log, OSM_LOG_ERROR, + "__osm_ftree_fabric_construct_hca_ports: ERR AB11: " + "HCA conected directly to another HCA: " + "0x%016" PRIx64 " <---> 0x%016" PRIx64 "\n", + cl_ntoh64(osm_node_get_node_guid(p_node)), + cl_ntoh64(remote_node_guid)); + res = -1; + goto Exit; + + case IB_NODE_TYPE_SWITCH: + /* continue with this port */ + break; + + default: + osm_log(&p_ftree->p_osm->log, OSM_LOG_ERROR, + "__osm_ftree_fabric_construct_hca_ports: ERR AB12: " + "Node GUID 0x%016" PRIx64 " - Unknown node type: %s\n", + cl_ntoh64(remote_node_guid), + ib_get_node_type_str(remote_node_type)); + res = -1; + goto Exit; + } + + /* remote node is switch */ + + p_remote_sw = (ftree_sw_t *)cl_qmap_get(&p_ftree->sw_tbl,remote_node_guid); + CL_ASSERT( p_remote_sw != (ftree_sw_t *)cl_qmap_end(&p_ftree->sw_tbl) ); + CL_ASSERT( (p_remote_sw->rank + 1) == __osm_ftree_fabric_get_rank(p_ftree) ); + + __osm_ftree_hca_add_port( + p_hca, /* local ftree_hca object */ + i, /* local port number */ + remote_port_num, /* remote port number */ + osm_node_get_base_lid(p_node, i), /* local lid */ + osm_node_get_base_lid(p_remote_node, 0), /* remote lid */ + osm_physp_get_port_guid(p_osm_port), /* local port guid */ + osm_physp_get_port_guid(p_remote_osm_port),/* remote port guid */ + remote_node_guid, /* remote node guid */ + remote_node_type, /* remote node type */ + (void *) p_remote_sw); /* remote ftree_hca/sw object */ + } + + Exit: + return res; +} /* __osm_ftree_fabric_construct_hca_ports() */ + +/*************************************************** + ***************************************************/ + +static int +__osm_ftree_fabric_construct_sw_ports( + IN ftree_fabric_t * p_ftree, + IN ftree_sw_t * p_sw) +{ + ftree_hca_t * p_remote_hca; + ftree_sw_t * p_remote_sw; + osm_node_t * p_node = osm_switch_get_node_ptr(p_sw->p_osm_sw); + osm_node_t * p_remote_node; + ib_net16_t remote_base_lid; + uint8_t remote_node_type; + ib_net64_t remote_node_guid; + osm_physp_t * p_remote_osm_port; + ftree_direction_t direction; + void * p_remote_hca_or_sw; + uint8_t i; + uint8_t remote_port_num; + int res = 0; + + CL_ASSERT(osm_node_get_type(p_node) == IB_NODE_TYPE_SWITCH); + + for (i = 0; i < osm_node_get_num_physp(p_node); i++) + { + osm_physp_t * p_osm_port = osm_node_get_physp_ptr(p_node,i); + + if (!osm_physp_is_valid(p_osm_port)) + continue; + if (!osm_link_is_healthy(p_osm_port)) + continue; + + p_remote_osm_port = osm_physp_get_remote(p_osm_port); + p_remote_node = osm_node_get_remote_node(p_node,i,&remote_port_num); + + if (!p_remote_osm_port) + continue; + + remote_node_type = osm_node_get_type(p_remote_node); + remote_node_guid = osm_node_get_node_guid(p_remote_node); + + switch (remote_node_type) + { + case IB_NODE_TYPE_ROUTER: + /* leaving this port - proceeding to the next one */ + continue; + + case IB_NODE_TYPE_CA: + /* switch connected to hca */ + + CL_ASSERT((p_sw->rank + 1) == __osm_ftree_fabric_get_rank(p_ftree)); + + p_remote_hca = (ftree_hca_t *)cl_qmap_get(&p_ftree->hca_tbl,remote_node_guid); + CL_ASSERT(p_remote_hca != (ftree_hca_t *)cl_qmap_end(&p_ftree->hca_tbl)); + + p_remote_hca_or_sw = (void *)p_remote_hca; + direction = FTREE_DIRECTION_DOWN; + + remote_base_lid = osm_physp_get_base_lid(p_remote_osm_port); + break; + + case IB_NODE_TYPE_SWITCH: + /* switch connected to another switch */ + + p_remote_sw = (ftree_sw_t *)cl_qmap_get(&p_ftree->sw_tbl,remote_node_guid); + CL_ASSERT(p_remote_sw != (ftree_sw_t *)cl_qmap_end(&p_ftree->sw_tbl)); + p_remote_hca_or_sw = (void *)p_remote_sw; + + if (abs(p_sw->rank - p_remote_sw->rank) != 1) + { + osm_log(&p_ftree->p_osm->log, OSM_LOG_ERROR, + "__osm_ftree_fabric_construct_sw_ports: ERR AB16: " + "Illegal link between switches with ranks %u and %u:\n" + " GUID 0x%016" PRIx64 ", LID 0x%x, rank %u\n" + " GUID 0x%016" PRIx64 ", LID 0x%x, rank %u\n", + p_sw->rank, + p_remote_sw->rank, + cl_ntoh64(osm_node_get_node_guid(osm_switch_get_node_ptr(p_sw->p_osm_sw))), + cl_ntoh16(p_sw->base_lid), + p_sw->rank, + cl_ntoh64(osm_node_get_node_guid(osm_switch_get_node_ptr(p_remote_sw->p_osm_sw))), + cl_ntoh16(p_remote_sw->base_lid), + p_remote_sw->rank); + res = -1; + goto Exit; + } + + if (p_sw->rank > p_remote_sw->rank) + direction = FTREE_DIRECTION_UP; + else + direction = FTREE_DIRECTION_DOWN; + + /* switch LID is only in port 0 port_info structure */ + remote_base_lid = osm_node_get_base_lid(p_remote_node, 0); + + break; + + default: + osm_log(&p_ftree->p_osm->log, OSM_LOG_ERROR, + "__osm_ftree_fabric_construct_sw_ports: ERR AB13: " + "Node GUID 0x%016" PRIx64 " - Unknown node type: %s\n", + cl_ntoh64(remote_node_guid), + ib_get_node_type_str(remote_node_type)); + res = -1; + goto Exit; + } + __osm_ftree_sw_add_port( + p_sw, /* local ftree_sw object */ + i, /* local port number */ + remote_port_num, /* remote port number */ + p_sw->base_lid, /* local lid */ + remote_base_lid, /* remote lid */ + osm_physp_get_port_guid(p_osm_port), /* local port guid */ + osm_physp_get_port_guid(p_remote_osm_port), /* remote port guid */ + remote_node_guid, /* remote node guid */ + remote_node_type, /* remote node type */ + p_remote_hca_or_sw, /* remote ftree_hca/sw object */ + direction); /* port direction (up or down) */ + + /* Track the max lid (in host order) that exists in the fabric */ + if (cl_ntoh16(remote_base_lid) > p_ftree->lft_max_lid_ho) + p_ftree->lft_max_lid_ho = cl_ntoh16(remote_base_lid); + } + + Exit: + return res; +} /* __osm_ftree_fabric_construct_sw_ports() */ + +/*************************************************** + ***************************************************/ + +/* ToDo: improve ranking algorithm complexity + by propogating BFS from more nodes */ +static int +__osm_ftree_fabric_perform_ranking( + IN ftree_fabric_t * p_ftree) +{ + ftree_hca_t * p_hca; + ftree_hca_t * p_next_hca; + int res = 0; + + OSM_LOG_ENTER(&p_ftree->p_osm->log, __osm_ftree_fabric_perform_ranking); + + /* Mark REVERSED rank of all the switches in the subnet. + Start from switches that are connected to hca's, and + scan all the switches in the subnet. */ + p_next_hca = (ftree_hca_t *)cl_qmap_head(&p_ftree->hca_tbl); + while( p_next_hca != (ftree_hca_t *)cl_qmap_end( &p_ftree->hca_tbl ) ) + { + p_hca = p_next_hca; + p_next_hca = (ftree_hca_t *)cl_qmap_next(&p_hca->map_item ); + if (__osm_ftree_rank_switches_from_hca(p_ftree,p_hca) != 0) + { + res = -1; + osm_log(&p_ftree->p_osm->log, OSM_LOG_ERROR, + "__osm_ftree_fabric_perform_ranking: ERR AB14: " + "Subnet ranking failed - subnet is not FatTree"); + goto Exit; + } + } + + /* calculate and set FatTree rank */ + __osm_ftree_fabric_calculate_rank(p_ftree); + osm_log(&p_ftree->p_osm->log, OSM_LOG_INFO, + "__osm_ftree_fabric_perform_ranking: " + "FatTree rank is %u\n", __osm_ftree_fabric_get_rank(p_ftree)); + + /* fix ranking of the switches by reversing the ranking direction */ + cl_qmap_apply_func(&p_ftree->sw_tbl, __osm_ftree_sw_reverse_rank, (void *)p_ftree); + + if ( __osm_ftree_fabric_get_rank(p_ftree) > FAT_TREE_MAX_RANK || + __osm_ftree_fabric_get_rank(p_ftree) < FAT_TREE_MIN_RANK ) + { + osm_log(&p_ftree->p_osm->log, OSM_LOG_ERROR, + "__osm_ftree_fabric_perform_ranking: ERR AB15: " + "Tree rank is %u (should be between %u and %u)\n", + __osm_ftree_fabric_get_rank(p_ftree), + FAT_TREE_MIN_RANK, + FAT_TREE_MAX_RANK); + res = -1; + goto Exit; + } + + Exit: + OSM_LOG_EXIT(&p_ftree->p_osm->log); + return res; +} /* __osm_ftree_fabric_perform_ranking() */ + +/*************************************************** + ***************************************************/ + +static int +__osm_ftree_fabric_populate_ports( + IN ftree_fabric_t * p_ftree) +{ + ftree_hca_t * p_hca; + ftree_hca_t * p_next_hca; + ftree_sw_t * p_sw; + ftree_sw_t * p_next_sw; + int res = 0; + + OSM_LOG_ENTER(&p_ftree->p_osm->log, __osm_ftree_fabric_populate_ports); + + p_next_hca = (ftree_hca_t *)cl_qmap_head(&p_ftree->hca_tbl); + while( p_next_hca != (ftree_hca_t *)cl_qmap_end( &p_ftree->hca_tbl ) ) + { + p_hca = p_next_hca; + p_next_hca = (ftree_hca_t *)cl_qmap_next(&p_hca->map_item ); + if (__osm_ftree_fabric_construct_hca_ports(p_ftree,p_hca) != 0) + { + res = -1; + goto Exit; + } + } + + p_next_sw = (ftree_sw_t *)cl_qmap_head(&p_ftree->sw_tbl); + while( p_next_sw != (ftree_sw_t *)cl_qmap_end( &p_ftree->sw_tbl ) ) + { + p_sw = p_next_sw; + p_next_sw = (ftree_sw_t *)cl_qmap_next(&p_sw->map_item ); + if (__osm_ftree_fabric_construct_sw_ports(p_ftree,p_sw) != 0) + { + res = -1; + goto Exit; + } + } + Exit: + OSM_LOG_EXIT(&p_ftree->p_osm->log); + return res; +} /* __osm_ftree_fabric_populate_ports() */ + +/*************************************************** + ***************************************************/ + +static int +__osm_ftree_construct_fabric( + IN void * context) +{ + ftree_fabric_t * p_ftree = context; + int status = 0; + + OSM_LOG_ENTER(&p_ftree->p_osm->log, __osm_ftree_construct_fabric); + + if (p_ftree->p_osm->subn.opt.lmc > 0) + { + osm_log(&p_ftree->p_osm->log, OSM_LOG_SYS, + "LMC > 0 is not supported by fat-tree routing.\n" + "Falling back to default routing.\n"); + status = -1; + goto Exit; + } + + if ( cl_qmap_count(&p_ftree->p_osm->subn.sw_guid_tbl) < 2 ) + { + osm_log(&p_ftree->p_osm->log, OSM_LOG_SYS, + "Fabric has %u switches - topology is not fat-tree.\n" + "Falling back to default routing.\n", + cl_qmap_count(&p_ftree->p_osm->subn.sw_guid_tbl)); + status = -1; + goto Exit; + } + + if ( (cl_qmap_count(&p_ftree->p_osm->subn.node_guid_tbl) - + cl_qmap_count(&p_ftree->p_osm->subn.sw_guid_tbl)) < 2) + { + osm_log(&p_ftree->p_osm->log, OSM_LOG_SYS, + "Fabric has %u nodes (%u switches) - topology is not fat-tree.\n" + "Falling back to default routing.\n", + cl_qmap_count(&p_ftree->p_osm->subn.node_guid_tbl), + cl_qmap_count(&p_ftree->p_osm->subn.sw_guid_tbl)); + status = -1; + goto Exit; + } + + osm_log(&p_ftree->p_osm->log, OSM_LOG_VERBOSE,"__osm_ftree_construct_fabric: \n" + " |----------------------------------------|\n" + " |- Starting FatTree fabric construction -|\n" + " |----------------------------------------|\n\n"); + + osm_log(&p_ftree->p_osm->log, OSM_LOG_VERBOSE, + "__osm_ftree_construct_fabric: " + "Populating FatTree switch table\n"); + /* ToDo: now that the pointer from node to switch exists, + no need to fill the switch table in a separate loop */ + if (__osm_ftree_fabric_populate_switches(p_ftree) != 0) + { + osm_log(&p_ftree->p_osm->log, OSM_LOG_SYS, + "Fabric topology is not fat-tree - " + "falling back to default routing\n"); + status = -1; + goto Exit; + } + + osm_log(&p_ftree->p_osm->log, OSM_LOG_VERBOSE, + "__osm_ftree_construct_fabric: " + "Populating FatTree HCA table\n"); + if (__osm_ftree_fabric_populate_hcas(p_ftree) != 0) + { + osm_log(&p_ftree->p_osm->log, OSM_LOG_SYS, + "Fabric topology is not fat-tree - " + "falling back to default routing\n"); + status = -1; + goto Exit; + } + + if (cl_qmap_count(&p_ftree->hca_tbl) < 2) + { + osm_log(&p_ftree->p_osm->log, OSM_LOG_SYS, + "Fabric has %u HCAa - topology is not fat-tree.\n" + "Falling back to default routing.\n", + cl_qmap_count(&p_ftree->hca_tbl)); + status = -1; + goto Exit; + } + + osm_log(&p_ftree->p_osm->log, OSM_LOG_VERBOSE, + "__osm_ftree_construct_fabric: Ranking FatTree\n"); + + if (__osm_ftree_fabric_perform_ranking(p_ftree) != 0) + { + if (__osm_ftree_fabric_get_rank(p_ftree) > FAT_TREE_MAX_RANK) + osm_log(&p_ftree->p_osm->log, OSM_LOG_SYS, + "Fabric rank is %u (>%u) - " + "fat-tree routing falls back to default routing\n", + __osm_ftree_fabric_get_rank(p_ftree), FAT_TREE_MAX_RANK); + else if (__osm_ftree_fabric_get_rank(p_ftree) < FAT_TREE_MIN_RANK) + osm_log(&p_ftree->p_osm->log, OSM_LOG_SYS, + "Fabric rank is %u (<%u) - " + "fat-tree routing falls back to default routing\n", + __osm_ftree_fabric_get_rank(p_ftree), FAT_TREE_MIN_RANK); + status = -1; + goto Exit; + } + + /* For each hca and switch, construct array of ports. + This is done after the whole FatTree data structure is ready, because + we want the ports to have pointers to ftree_{sw,hca}_t objects.*/ + osm_log(&p_ftree->p_osm->log, OSM_LOG_VERBOSE, + "__osm_ftree_construct_fabric: " + "Populating HCA & switch ports\n"); + if (__osm_ftree_fabric_populate_ports(p_ftree) != 0) + { + osm_log(&p_ftree->p_osm->log, OSM_LOG_SYS, + "Fabric topology is not a fat-tree - " + "routing falls back to default routing\n"); + status = -1; + goto Exit; + } + + /* Assign index to all the switches and hca's in the fabric. + This function also sorts all the port arrays of the switches + by the remote switch index, creates a leaf switch array + sorted by the switch index, and tracks the maximal number of + hcas per leaf switch. */ + __osm_ftree_fabric_make_indexing(p_ftree); + + /* print general info about fabric topology */ + __osm_ftree_fabric_dump_general_info(p_ftree); + + /* dump full tree topology */ + if (osm_log_is_active(&p_ftree->p_osm->log, OSM_LOG_DEBUG)) + __osm_ftree_fabric_dump(p_ftree); + + if (! __osm_ftree_fabric_validate_topology(p_ftree)) + { + osm_log(&p_ftree->p_osm->log, OSM_LOG_SYS, + "Fabric topology is not a fat-tree - " + "routing falls back to default routing\n"); + status = -1; + goto Exit; + } + + osm_log(&p_ftree->p_osm->log, OSM_LOG_VERBOSE, + "__osm_ftree_construct_fabric: " + "Max LID in switch LFTs (in host order): 0x%x\n", + p_ftree->lft_max_lid_ho); + + Exit: + if (status != 0) + { + osm_log(&p_ftree->p_osm->log, OSM_LOG_VERBOSE, + "__osm_ftree_construct_fabric: " + "Clearing FatTree Fabric data structures\n"); + __osm_ftree_fabric_clear(p_ftree); + } + else + p_ftree->fabric_built = TRUE; + + osm_log(&p_ftree->p_osm->log, OSM_LOG_VERBOSE, + "__osm_ftree_construct_fabric: \n" + " |--------------------------------------------------|\n" + " |- Done constructing FatTree fabric (status = %d) -|\n" + " |--------------------------------------------------|\n\n", + status); + + OSM_LOG_EXIT(&p_ftree->p_osm->log); + return status; +} /* __osm_ftree_construct_fabric() */ + +/*************************************************** + ***************************************************/ + +static int +__osm_ftree_do_routing( + IN void * context) +{ + ftree_fabric_t * p_ftree = context; + + OSM_LOG_ENTER(&p_ftree->p_osm->log, __osm_ftree_do_routing); + + if (!p_ftree->fabric_built) + goto Exit; + + osm_log(&p_ftree->p_osm->log, OSM_LOG_VERBOSE,"__osm_ftree_do_routing: " + "Starting FatTree routing\n"); + + osm_log(&p_ftree->p_osm->log, OSM_LOG_VERBOSE,"__osm_ftree_do_routing: " + "Filling switch forwarding tables for routes to HCAs\n"); + __osm_ftree_fabric_route_to_hcas(p_ftree); + + osm_log(&p_ftree->p_osm->log, OSM_LOG_VERBOSE,"__osm_ftree_do_routing: " + "Filling switch forwarding tables for switch-to-switch pathes\n"); + __osm_ftree_fabric_route_to_switches(p_ftree); + + /* for each switch, set its fwd table */ + cl_qmap_apply_func(&p_ftree->sw_tbl, __osm_ftree_set_sw_fwd_table, (void *)p_ftree); + + /* write out hca ordering file */ + __osm_ftree_fabric_dump_hca_ordering(p_ftree); + + osm_log(&p_ftree->p_osm->log, OSM_LOG_VERBOSE,"__osm_ftree_do_routing: " + "FatTree routing is done\n"); + + Exit: + OSM_LOG_EXIT(&p_ftree->p_osm->log); + return 0; +} + +/*************************************************** + ***************************************************/ + +static void +__osm_ftree_delete( + IN void * context) +{ + if (!context) + return; + __osm_ftree_fabric_destroy((ftree_fabric_t *)context); +} + +/*************************************************** + ***************************************************/ + +int osm_ucast_ftree_setup(osm_opensm_t * p_osm) +{ + ftree_fabric_t * p_ftree = __osm_ftree_fabric_create(); + if (!p_ftree) + return -1; + + p_ftree->p_osm = p_osm; + + p_osm->routing_engine.context = (void *)p_ftree; + p_osm->routing_engine.build_lid_matrices = __osm_ftree_construct_fabric; + p_osm->routing_engine.ucast_build_fwd_tables = __osm_ftree_do_routing; + p_osm->routing_engine.delete = __osm_ftree_delete; + return 0; +} + +/*************************************************** + ***************************************************/ + + diff --git a/trunk/ulp/opensm/user/opensm/osm_ucast_mgr.c b/trunk/ulp/opensm/user/opensm/osm_ucast_mgr.c index 02e88169..27c87680 100644 --- a/trunk/ulp/opensm/user/opensm/osm_ucast_mgr.c +++ b/trunk/ulp/opensm/user/opensm/osm_ucast_mgr.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -35,7 +35,7 @@ /* * Abstract: * Implementation of osm_ucast_mgr_t. - * This file implements the LID Manager object. + * This file implements the Unicast Manager object. * * Environment: * Linux User Mode @@ -43,16 +43,14 @@ * $Revision: 1.14 $ */ -/* - Next available error code: 0x403 -*/ - #if HAVE_CONFIG_H # include #endif /* HAVE_CONFIG_H */ +#include +#include +#include #include -#include #include #include #include @@ -61,6 +59,7 @@ #include #include #include +#include #define LINE_LENGTH 256 @@ -78,7 +77,7 @@ void osm_ucast_mgr_construct( IN osm_ucast_mgr_t* const p_mgr ) { - cl_memclr( p_mgr, sizeof(*p_mgr) ); + memset( p_mgr, 0, sizeof(*p_mgr) ); } /********************************************************************** @@ -91,6 +90,9 @@ osm_ucast_mgr_destroy( OSM_LOG_ENTER( p_mgr->p_log, osm_ucast_mgr_destroy ); + if (p_mgr->lft_buf) + free(p_mgr->lft_buf); + OSM_LOG_EXIT( p_mgr->p_log ); } @@ -101,7 +103,6 @@ osm_ucast_mgr_init( IN osm_ucast_mgr_t* const p_mgr, IN osm_req_t* const p_req, IN osm_subn_t* const p_subn, - IN char* const p_report_buf, IN osm_log_t* const p_log, IN cl_plock_t* const p_lock ) { @@ -119,7 +120,10 @@ osm_ucast_mgr_init( p_mgr->p_subn = p_subn; p_mgr->p_lock = p_lock; p_mgr->p_req = p_req; - p_mgr->p_report_buf = p_report_buf; + + p_mgr->lft_buf = malloc(IB_LID_UCAST_END_HO + 1); + if (!p_mgr->lft_buf) + return IB_INSUFFICIENT_MEMORY; OSM_LOG_EXIT( p_mgr->p_log ); return( status ); @@ -127,10 +131,52 @@ osm_ucast_mgr_init( /********************************************************************** **********************************************************************/ +struct ucast_mgr_dump_context { + osm_ucast_mgr_t *p_mgr; + FILE *file; +}; + +static void +ucast_mgr_dump(osm_ucast_mgr_t *p_mgr, FILE *file, + void (*func)(cl_map_item_t *, void *)) +{ + struct ucast_mgr_dump_context dump_context; + + dump_context.p_mgr = p_mgr; + dump_context.file = file; + + cl_qmap_apply_func(&p_mgr->p_subn->sw_guid_tbl, func, &dump_context); +} + void -osm_ucast_mgr_dump_path_distribution( - IN const osm_ucast_mgr_t* const p_mgr, - IN const osm_switch_t* const p_sw ) +ucast_mgr_dump_to_file(osm_ucast_mgr_t *p_mgr, const char *file_name, + void (*func)(cl_map_item_t *, void *)) +{ + char path[1024]; + FILE *file; + + snprintf(path, sizeof(path), "%s/%s", + p_mgr->p_subn->opt.dump_files_dir, file_name); + + file = fopen(path, "w"); + if (!file) { + osm_log( p_mgr->p_log, OSM_LOG_ERROR, + "ucast_mgr_dump_to_file: ERR 3A12: " + "Failed to open fdb file (%s)\n", path ); + return; + } + + ucast_mgr_dump(p_mgr, file, func); + + fclose(file); +} + +/********************************************************************** + **********************************************************************/ +static void +__osm_ucast_mgr_dump_path_distribution( + IN cl_map_item_t *p_map_item, + IN void *cxt) { osm_node_t *p_node; osm_node_t *p_remote_node; @@ -138,139 +184,103 @@ osm_ucast_mgr_dump_path_distribution( uint8_t num_ports; uint32_t num_paths; ib_net64_t remote_guid_ho; - char line[OSM_REPORT_LINE_SIZE]; + osm_switch_t* p_sw = (osm_switch_t *)p_map_item; + osm_ucast_mgr_t* p_mgr = ((struct ucast_mgr_dump_context *)cxt)->p_mgr; - OSM_LOG_ENTER( p_mgr->p_log, osm_ucast_mgr_dump_path_distribution ); + OSM_LOG_ENTER( p_mgr->p_log, __osm_ucast_mgr_dump_path_distribution ); - if( osm_log_is_active( p_mgr->p_log, OSM_LOG_DEBUG ) ) - { - p_node = osm_switch_get_node_ptr( p_sw ); + p_node = osm_switch_get_node_ptr( p_sw ); + num_ports = osm_switch_get_num_ports( p_sw ); - num_ports = osm_switch_get_num_ports( p_sw ); - sprintf( p_mgr->p_report_buf, "osm_ucast_mgr_dump_path_distribution: " - "Switch 0x%" PRIx64 "\n" - "Port : Path Count Through Port", - cl_ntoh64( osm_node_get_node_guid( p_node ) ) ); + osm_log_printf( p_mgr->p_log, OSM_LOG_DEBUG, + "__osm_ucast_mgr_dump_path_distribution: " + "Switch 0x%" PRIx64 "\n" + "Port : Path Count Through Port", + cl_ntoh64( osm_node_get_node_guid( p_node ) ) ); - for( i = 0; i < num_ports; i++ ) + for( i = 0; i < num_ports; i++ ) + { + num_paths = osm_switch_path_count_get( p_sw , i ); + osm_log_printf( p_mgr->p_log, OSM_LOG_DEBUG,"\n %03u : %u", i, num_paths ); + if( i == 0 ) { - num_paths = osm_switch_path_count_get( p_sw , i ); - sprintf( line, "\n %03u : %u", i, num_paths ); - strcat( p_mgr->p_report_buf, line ); - if( i == 0 ) - { - strcat( p_mgr->p_report_buf, " (switch management port)" ); - continue; - } - - p_remote_node = osm_node_get_remote_node( - p_node, i, NULL ); - - if( p_remote_node == NULL ) - continue; + osm_log_printf( p_mgr->p_log, OSM_LOG_DEBUG, " (switch management port)" ); + continue; + } - remote_guid_ho = cl_ntoh64( - osm_node_get_node_guid( p_remote_node ) ); + p_remote_node = osm_node_get_remote_node( p_node, i, NULL ); + if( p_remote_node == NULL ) + continue; - switch( osm_node_get_remote_type( p_node, i ) ) - { - case IB_NODE_TYPE_SWITCH: - strcat( p_mgr->p_report_buf, " (link to switch" ); - break; - case IB_NODE_TYPE_ROUTER: - strcat( p_mgr->p_report_buf, " (link to router" ); - break; - case IB_NODE_TYPE_CA: - strcat( p_mgr->p_report_buf, " (link to CA" ); - break; - default: - strcat( p_mgr->p_report_buf, " (link to unknown type, node" ); - break; - } + remote_guid_ho = cl_ntoh64( osm_node_get_node_guid( p_remote_node ) ); - sprintf( line, " 0x%" PRIx64 ")", remote_guid_ho ); - strcat( p_mgr->p_report_buf, line ); + switch( osm_node_get_remote_type( p_node, i ) ) + { + case IB_NODE_TYPE_SWITCH: + osm_log_printf( p_mgr->p_log, OSM_LOG_DEBUG, " (link to switch" ); + break; + case IB_NODE_TYPE_ROUTER: + osm_log_printf( p_mgr->p_log, OSM_LOG_DEBUG, " (link to router" ); + break; + case IB_NODE_TYPE_CA: + osm_log_printf( p_mgr->p_log, OSM_LOG_DEBUG, " (link to CA" ); + break; + default: + osm_log_printf( p_mgr->p_log, OSM_LOG_DEBUG, " (link to unknown node type" ); + break; } - strcat( p_mgr->p_report_buf, "\n" ); - - osm_log_raw( p_mgr->p_log, OSM_LOG_ROUTING, p_mgr->p_report_buf ); + osm_log_printf( p_mgr->p_log, OSM_LOG_DEBUG, " 0x%" PRIx64 ")", + remote_guid_ho ); } + osm_log_printf( p_mgr->p_log, OSM_LOG_DEBUG, "\n" ); + OSM_LOG_EXIT( p_mgr->p_log ); } /********************************************************************** **********************************************************************/ -void -osm_ucast_mgr_dump_ucast_routes( - IN const osm_ucast_mgr_t* const p_mgr, - IN const osm_switch_t* const p_sw ) +static void +__osm_ucast_mgr_dump_ucast_routes( + IN cl_map_item_t *p_map_item, + IN void *cxt ) { const osm_node_t* p_node; uint8_t port_num; uint8_t num_hops; uint8_t best_hops; uint8_t best_port; - uint16_t max_lid_ho; - uint16_t lid_ho; - char line[OSM_REPORT_LINE_SIZE]; - uint32_t line_num = 0; - FILE * p_fdbFile; - boolean_t ui_ucast_fdb_assign_func_defined; - char *file_name = NULL; - - OSM_LOG_ENTER( p_mgr->p_log, osm_ucast_mgr_dump_ucast_routes ); + uint16_t max_lid_ho; + uint16_t lid_ho; + osm_switch_t* p_sw = (osm_switch_t *)p_map_item; + osm_ucast_mgr_t* p_mgr = ((struct ucast_mgr_dump_context *)cxt)->p_mgr; + FILE *file = ((struct ucast_mgr_dump_context *)cxt)->file; - if( !osm_log_is_active( p_mgr->p_log, OSM_LOG_ROUTING ) ) - goto Exit; - - file_name = - (char*)cl_malloc(strlen(p_mgr->p_subn->opt.dump_files_dir) + 10); - - CL_ASSERT(file_name); - - strcpy(file_name, p_mgr->p_subn->opt.dump_files_dir); - strcat(file_name,"/osm.fdbs"); - - /* Open the file or error */ - p_fdbFile = fopen(file_name, "a"); - if (! p_fdbFile) - { - osm_log( p_mgr->p_log, OSM_LOG_ERROR, - "osm_ucast_mgr_dump_ucast_routes: ERR 3A12: " - "Failed to open fdb file (%s)\n", - file_name ); - goto Exit; - } + OSM_LOG_ENTER( p_mgr->p_log, __osm_ucast_mgr_dump_ucast_routes ); p_node = osm_switch_get_node_ptr( p_sw ); max_lid_ho = osm_switch_get_max_lid_ho( p_sw ); + fprintf( file, "__osm_ucast_mgr_dump_ucast_routes: " + "Switch 0x%016" PRIx64 "\n" + "LID : Port : Hops : Optimal\n", + cl_ntoh64( osm_node_get_node_guid( p_node ) ) ); for( lid_ho = 1; lid_ho <= max_lid_ho; lid_ho++ ) { - if( line_num == 0 ) - { - sprintf( p_mgr->p_report_buf, "osm_ucast_mgr_dump_ucast_routes: " - "Switch 0x%016" PRIx64 "\n" - "LID : Port : Hops : Optimal\n", - cl_ntoh64( osm_node_get_node_guid( p_node ) ) ); - line_num++; - } + fprintf(file, "0x%04X : ", lid_ho); port_num = osm_switch_get_port_by_lid( p_sw, lid_ho ); if( port_num == OSM_NO_PATH ) { /* This may occur if there are 'holes' in the existing - LID assignemnts. Running SM with --reassign_lids + LID assignments. Running SM with --reassign_lids will reassign and compress the LID range. The subnet should work fine either way. */ - sprintf( line, "0x%04X : UNREACHABLE\n", lid_ho ); - strcat( p_mgr->p_report_buf, line ); - line_num++; + fprintf( file, "UNREACHABLE\n" ); continue; } /* @@ -282,57 +292,133 @@ osm_ucast_mgr_dump_ucast_routes( num_hops = osm_switch_get_hop_count( p_sw, lid_ho, port_num ); if( num_hops == OSM_NO_PATH ) { - sprintf( line, "0x%04X : UNREACHABLE\n", lid_ho ); - strcat( p_mgr->p_report_buf, line ); - line_num++; + fprintf( file, "UNREACHABLE\n" ); continue; } best_hops = osm_switch_get_least_hops( p_sw, lid_ho ); - sprintf( line, "0x%04X : %03u : %02u : ", - lid_ho, port_num, num_hops ); - strcat( p_mgr->p_report_buf, line ); + fprintf( file, "%03u : %02u : ", port_num, num_hops ); if( best_hops == num_hops ) - strcat( p_mgr->p_report_buf, "yes" ); + fprintf( file, "yes" ); else { - if (p_mgr->p_subn->opt.pfn_ui_ucast_fdb_assign) { - ui_ucast_fdb_assign_func_defined = TRUE; - } else { - ui_ucast_fdb_assign_func_defined = FALSE; - } best_port = osm_switch_recommend_path( p_sw, lid_ho, TRUE, - NULL, NULL, NULL, NULL, /* No LMC Optimization */ - 0xffffffff, ui_ucast_fdb_assign_func_defined ); - sprintf( line, "No %u hop path possible via port %u!", + NULL, NULL, NULL, NULL ); /* No LMC Optimization */ + fprintf( file, "No %u hop path possible via port %u!", best_hops, best_port ); - strcat( p_mgr->p_report_buf, line ); } - strcat( p_mgr->p_report_buf, "\n" ); - - if( ++line_num >= OSM_REPORT_BUF_THRESHOLD ) - { - fprintf(p_fdbFile,"%s",p_mgr->p_report_buf ); - line_num = 0; - } + fprintf( file, "\n" ); } - if( line_num != 0 ) - fprintf(p_fdbFile,"%s\n",p_mgr->p_report_buf ); + OSM_LOG_EXIT( p_mgr->p_log ); +} + +/********************************************************************** + **********************************************************************/ +static void +ucast_mgr_dump_lid_matrix(cl_map_item_t *p_map_item, void *cxt) +{ + osm_switch_t* p_sw = (osm_switch_t *)p_map_item; + osm_ucast_mgr_t* p_mgr = ((struct ucast_mgr_dump_context *)cxt)->p_mgr; + FILE *file = ((struct ucast_mgr_dump_context *)cxt)->file; + osm_node_t *p_node = osm_switch_get_node_ptr(p_sw); + unsigned max_lid = osm_switch_get_max_lid_ho(p_sw); + unsigned max_port = osm_switch_get_num_ports(p_sw); + uint16_t lid; + uint8_t port; + + fprintf(file, "Switch: guid 0x%016" PRIx64 "\n", + cl_ntoh64(osm_node_get_node_guid(p_node))); + for (lid = 1; lid <= max_lid; lid++) { + osm_port_t *p_port; + + fprintf(file, "0x%04x:", lid); + for (port = 0 ; port < max_port ; port++) + fprintf(file, " %02x", + osm_switch_get_hop_count(p_sw, lid, port)); + p_port = cl_ptr_vector_get(&p_mgr->p_subn->port_lid_tbl, lid); + if (p_port) + fprintf(file, " # portguid 0x%" PRIx64, + cl_ntoh64(osm_port_get_guid(p_port))); + fprintf(file, "\n"); + } +} - fclose(p_fdbFile); +/********************************************************************** + **********************************************************************/ +void +ucast_mgr_dump_lfts(cl_map_item_t *p_map_item, void *cxt) +{ + osm_switch_t* p_sw = (osm_switch_t *)p_map_item; + osm_ucast_mgr_t* p_mgr = ((struct ucast_mgr_dump_context *)cxt)->p_mgr; + FILE *file = ((struct ucast_mgr_dump_context *)cxt)->file; + osm_node_t *p_node = osm_switch_get_node_ptr(p_sw); + unsigned max_lid = osm_switch_get_max_lid_ho(p_sw); + unsigned max_port = osm_switch_get_num_ports(p_sw); + uint16_t lid; + uint8_t port; + char desc[IB_NODE_DESCRIPTION_SIZE + 1]; + + memcpy(desc, p_node->node_desc.description, IB_NODE_DESCRIPTION_SIZE); + desc[IB_NODE_DESCRIPTION_SIZE] = '\0'; + fprintf(file, "Unicast lids [0x0-0x%x] of switch Lid %u guid 0x%016" + PRIx64 " (\'%s\'):\n", + max_lid, osm_node_get_base_lid(p_node, 0), + cl_ntoh64(osm_node_get_node_guid(p_node)), desc); + for (lid = 0; lid <= max_lid; lid++) { + osm_port_t *p_port; + port = osm_switch_get_port_by_lid(p_sw, lid); + + if (port >= max_port) + continue; + + fprintf(file, "0x%04x %03u # ", lid, port); + + p_port = cl_ptr_vector_get(&p_mgr->p_subn->port_lid_tbl, lid); + if (p_port) { + p_node = osm_port_get_parent_node(p_port); + memcpy(desc, p_node->node_desc.description, + IB_NODE_DESCRIPTION_SIZE); + desc[IB_NODE_DESCRIPTION_SIZE] = '\0'; + fprintf(file, "%s portguid 0x016%" PRIx64 ": \'%s\'", + ib_get_node_type_str(osm_node_get_type(p_node)), + cl_ntoh64(osm_port_get_guid(p_port)), desc); + } + else + fprintf(file, "unknown node and type"); + fprintf(file, "\n"); + } + fprintf(file, "%u lids dumped\n", max_lid); +} - Exit: - if (file_name) - cl_free(file_name); - OSM_LOG_EXIT( p_mgr->p_log ); +/********************************************************************** + **********************************************************************/ +static void __osm_ucast_mgr_dump_tables(osm_ucast_mgr_t *p_mgr) +{ + ucast_mgr_dump_to_file(p_mgr, "opensm-lid-matrix.dump", + ucast_mgr_dump_lid_matrix); + ucast_mgr_dump_to_file(p_mgr, "opensm-lfts.dump", ucast_mgr_dump_lfts); + if( osm_log_is_active( p_mgr->p_log, OSM_LOG_DEBUG ) ) + ucast_mgr_dump(p_mgr, NULL, __osm_ucast_mgr_dump_path_distribution); + ucast_mgr_dump_to_file(p_mgr, "osm.fdbs", __osm_ucast_mgr_dump_ucast_routes); } /********************************************************************** - Add each switch's own LID to its LID matrix. + Starting a rebuild, so notify the switch so it can clear tables, etc... +**********************************************************************/ +static void +__osm_ucast_mgr_clean_switch( + IN cl_map_item_t* const p_map_item, + IN void* context ) +{ + osm_switch_prepare_path_rebuild((osm_switch_t *)p_map_item); +} + +/********************************************************************** + Add each switch's own LID(s) to its LID matrix. **********************************************************************/ static void __osm_ucast_mgr_process_hop_0( @@ -342,8 +428,9 @@ __osm_ucast_mgr_process_hop_0( osm_switch_t* const p_sw = (osm_switch_t*)p_map_item; osm_ucast_mgr_t* const p_mgr = (osm_ucast_mgr_t*)context; osm_node_t *p_node; - uint16_t lid_ho; + uint16_t lid_ho, base_lid_ho, max_lid_ho; cl_status_t status; + uint8_t lmc; OSM_LOG_ENTER( p_mgr->p_log, __osm_ucast_mgr_process_hop_0 ); @@ -352,30 +439,35 @@ __osm_ucast_mgr_process_hop_0( CL_ASSERT( p_node ); CL_ASSERT( osm_node_get_type( p_node ) == IB_NODE_TYPE_SWITCH ); - /* - Starting a rebuild, so notify the switch so it can - clear tables, etc... - */ - osm_switch_prepare_path_rebuild( p_sw ); - - lid_ho = cl_ntoh16( osm_node_get_base_lid( p_node, 0 ) ); + base_lid_ho = cl_ntoh16( osm_node_get_base_lid( p_node, 0 ) ); + if (osm_switch_sp0_is_lmc_capable( p_sw, p_mgr->p_subn )) + lmc = osm_node_get_lmc( p_node, 0 ); + else + lmc = 0; + max_lid_ho = (uint16_t)( base_lid_ho + (1 << lmc) - 1 ); - if( osm_log_is_active( p_mgr->p_log, OSM_LOG_DEBUG ) ) + for (lid_ho = base_lid_ho; lid_ho <= max_lid_ho; lid_ho++) { - osm_log( p_mgr->p_log, OSM_LOG_DEBUG, - "__osm_ucast_mgr_process_hop_0: " - "Processing switch GUID 0x%" PRIx64 ", LID 0x%X\n", - cl_ntoh64( osm_node_get_node_guid( p_node ) ), - lid_ho ); - } + if( osm_log_is_active( p_mgr->p_log, OSM_LOG_DEBUG ) ) + { + osm_log( p_mgr->p_log, OSM_LOG_DEBUG, + "__osm_ucast_mgr_process_hop_0: " + "Processing switch GUID 0x%" PRIx64 ", LID 0x%X\n", + cl_ntoh64( osm_node_get_node_guid( p_node ) ), + lid_ho ); + } - status = osm_switch_set_hops( p_sw, lid_ho, 0, 0 ); - if( status != CL_SUCCESS ) - { - osm_log( p_mgr->p_log, OSM_LOG_ERROR, - "__osm_ucast_mgr_process_hop_0: ERR 3A02: " - "Setting hop count failed (%s)\n", - CL_STATUS_MSG( status ) ); + status = osm_switch_set_hops( p_sw, lid_ho, 0, 0 ); + if( status != CL_SUCCESS ) + { + osm_log( p_mgr->p_log, OSM_LOG_ERROR, + "__osm_ucast_mgr_process_hop_0: ERR 3A02: " + "Setting hop count failed (%s) for " + "switch GUID 0x%" PRIx64 ", LID 0x%X\n", + CL_STATUS_MSG( status ), + cl_ntoh64( osm_node_get_node_guid( p_node ) ), + lid_ho ); + } } OSM_LOG_EXIT( p_mgr->p_log ); @@ -515,16 +607,18 @@ __osm_ucast_mgr_process_leaf( p_remote_node, remote_port_num ) ); lmc = osm_node_get_lmc( p_remote_node, remote_port_num ); break; -/* case IB_NODE_TYPE_SWITCH: */ -/* base_lid_ho = cl_ntoh16( osm_node_get_base_lid( */ -/* p_remote_node, 0 ) ); */ -/* lmc = 0; */ -/* break; */ +#if 0 + case IB_NODE_TYPE_SWITCH: + base_lid_ho = cl_ntoh16( osm_node_get_base_lid( + p_remote_node, 0 ) ); + lmc = 0; + break; +#endif default: osm_log( p_mgr->p_log, OSM_LOG_ERROR, "__osm_ucast_mgr_process_leaf: ERR 3A01: " - "Bad node type %u, GUID = 0x%" PRIx64 "\n", + "Bad node type %u, GUID 0x%" PRIx64 "\n", osm_node_get_type( p_remote_node ), cl_ntoh64( osm_node_get_node_guid( p_node ) )); goto Exit; @@ -594,8 +688,7 @@ __osm_ucast_mgr_process_leaves( (uint8_t)port_num, &remote_port_num ); if( p_remote_node && (p_remote_node != p_node ) - && (osm_node_get_type( p_remote_node ) - != IB_NODE_TYPE_SWITCH )) + && (osm_node_get_type( p_remote_node ) != IB_NODE_TYPE_SWITCH ) ) { __osm_ucast_mgr_process_leaf( p_mgr, @@ -622,9 +715,8 @@ __osm_ucast_mgr_process_port( uint16_t max_lid_ho; uint16_t lid_ho; uint8_t port; - boolean_t ignore_existing, is_ignored_by_port_prof; + boolean_t is_ignored_by_port_prof; ib_net64_t node_guid; - boolean_t ui_ucast_fdb_assign_func_defined; /* The following are temporary structures that will aid in providing better routing in LMC > 0 situations @@ -637,7 +729,7 @@ __osm_ucast_mgr_process_port( OSM_LOG_ENTER( p_mgr->p_log, __osm_ucast_mgr_process_port ); - remote_sys_guids = cl_zalloc( sizeof(uint64_t) * lids_per_port ); + remote_sys_guids = malloc( sizeof(uint64_t) * lids_per_port ); if( remote_sys_guids == NULL ) { osm_log( p_mgr->p_log, OSM_LOG_ERROR, @@ -646,7 +738,9 @@ __osm_ucast_mgr_process_port( goto Exit; } - remote_node_guids = cl_zalloc( sizeof(uint64_t) * lids_per_port ); + memset( remote_sys_guids, 0, sizeof(uint64_t) * lids_per_port ); + + remote_node_guids = malloc( sizeof(uint64_t) * lids_per_port ); if( remote_node_guids == NULL ) { osm_log( p_mgr->p_log, OSM_LOG_ERROR, @@ -655,11 +749,13 @@ __osm_ucast_mgr_process_port( goto Exit; } + memset( remote_node_guids, 0, sizeof(uint64_t) * lids_per_port ); + osm_port_get_lid_range_ho( p_port, &min_lid_ho, &max_lid_ho ); /* If the lids are zero - then there was some problem with the initialization. Don't handle this port. */ - if (min_lid_ho == 0 || max_lid_ho == 0) + if ( min_lid_ho == 0 || max_lid_ho == 0 ) { osm_log( p_mgr->p_log, OSM_LOG_ERROR, "__osm_ucast_mgr_process_port: ERR 3A04: " @@ -680,28 +776,12 @@ __osm_ucast_mgr_process_port( } /* - TO DO - - This should be runtime error, not an CL_ASSERT() + TO DO - This should be runtime error, not a CL_ASSERT() */ CL_ASSERT( max_lid_ho < osm_switch_get_fwd_tbl_size( p_sw ) ); node_guid = osm_node_get_node_guid(osm_switch_get_node_ptr( p_sw ) ); - /* Flag to mark whether or not a ui ucast fdb assign function was given */ - if (p_mgr->p_subn->opt.pfn_ui_ucast_fdb_assign) - ui_ucast_fdb_assign_func_defined = TRUE; - else - ui_ucast_fdb_assign_func_defined = FALSE; - - /* - If the user request a complete subnet reconfiguration, - then ignore existing paths when choosing paths now. - Note that if there is a ui ucast fdb assign function - then the - ignore_existing should be false. - */ - ignore_existing = p_mgr->p_subn->ignore_existing_lfts && - (!ui_ucast_fdb_assign_func_defined) ; - /* The lid matrix contains the number of hops to each lid from each port. From this information we determine @@ -712,19 +792,17 @@ __osm_ucast_mgr_process_port( { /* Use the enhanced algorithm only for LMC > 0 */ if (lids_per_port > 1) - port = osm_switch_recommend_path( p_sw, lid_ho, ignore_existing, + port = osm_switch_recommend_path( p_sw, lid_ho, + p_mgr->p_subn->ignore_existing_lfts, remote_sys_guids, &num_used_sys, - remote_node_guids, &num_used_nodes, - p_mgr->p_subn->opt.max_port_profile, - ui_ucast_fdb_assign_func_defined ); + remote_node_guids, &num_used_nodes ); else - port = osm_switch_recommend_path( p_sw, lid_ho, ignore_existing, - NULL, NULL, NULL, NULL, - p_mgr->p_subn->opt.max_port_profile, - ui_ucast_fdb_assign_func_defined ); + port = osm_switch_recommend_path( p_sw, lid_ho, + p_mgr->p_subn->ignore_existing_lfts, + NULL, NULL, NULL, NULL ); /* - There might be no path to the target: + There might be no path to the target */ if (port == OSM_NO_PATH) { @@ -733,7 +811,7 @@ __osm_ucast_mgr_process_port( /* Up/Down routing can cause unreachable routes between some switches so we do not report that as an error in that case */ - if (!p_mgr->p_subn->opt.updn_activate) + if (!p_mgr->p_subn->p_osm->routing_engine.build_lid_matrices) { osm_log( p_mgr->p_log, OSM_LOG_ERROR, "__osm_ucast_mgr_process_port: ERR 3A08: " @@ -764,7 +842,7 @@ __osm_ucast_mgr_process_port( osm_port_prof_is_ignored_port(p_mgr->p_subn, cl_ntoh64(node_guid), port); /* - We also would ignore this route if the target lid if of a switch + We also would ignore this route if the target lid is of a switch and the port_profile_switch_node is not TRUE */ if (! p_mgr->p_subn->opt.port_profile_switch_nodes) @@ -779,21 +857,23 @@ __osm_ucast_mgr_process_port( We have selected the port for this LID. Write it to the forwarding tables. */ - osm_switch_set_path( p_sw, lid_ho, port, is_ignored_by_port_prof); + p_mgr->lft_buf[lid_ho] = port; + if (!is_ignored_by_port_prof) + osm_switch_count_path(p_sw, port); } Exit: if (remote_sys_guids) - cl_free(remote_sys_guids); + free(remote_sys_guids); if (remote_node_guids) - cl_free(remote_node_guids); + free(remote_node_guids); OSM_LOG_EXIT( p_mgr->p_log ); } /********************************************************************** **********************************************************************/ -static void -__osm_ucast_mgr_set_table( +void +osm_ucast_mgr_set_fwd_table( IN osm_ucast_mgr_t* const p_mgr, IN osm_switch_t* const p_sw ) { @@ -804,10 +884,13 @@ __osm_ucast_mgr_set_table( ib_switch_info_t si; uint32_t block_id_ho = 0; uint8_t block[IB_SMP_DATA_SIZE]; + boolean_t set_swinfo_require = FALSE; + uint16_t lin_top; + uint8_t life_state; CL_ASSERT( p_mgr ); - OSM_LOG_ENTER( p_mgr->p_log, __osm_ucast_mgr_set_table ); + OSM_LOG_ENTER( p_mgr->p_log, osm_ucast_mgr_set_fwd_table ); CL_ASSERT( p_sw ); @@ -823,43 +906,59 @@ __osm_ucast_mgr_set_table( Set the top of the unicast forwarding table. */ si = *osm_switch_get_si_ptr( p_sw ); - si.lin_top = cl_hton16( osm_switch_get_max_lid_ho( p_sw ) ); + lin_top = cl_hton16( osm_switch_get_max_lid_ho( p_sw ) ); + if (lin_top != si.lin_top) + { + set_swinfo_require = TRUE; + si.lin_top = lin_top; + } /* check to see if the change state bit is on. If it is - then we need to clear it. */ - if( ib_switch_info_get_state_change( &si ) ) - si.life_state = ( (p_mgr->p_subn->opt.packet_life_time <<3 ) - | ( si.life_state & IB_SWITCH_PSC ) ) & 0xfc; + if ( ib_switch_info_get_state_change( &si ) ) + life_state = ( (p_mgr->p_subn->opt.packet_life_time <<3 ) + | ( si.life_state & IB_SWITCH_PSC ) ) & 0xfc; else - si.life_state = (p_mgr->p_subn->opt.packet_life_time <<3 ) & 0xf8; + life_state = (p_mgr->p_subn->opt.packet_life_time <<3 ) & 0xf8; - if( osm_log_is_active( p_mgr->p_log, OSM_LOG_DEBUG ) ) + if ( (life_state != si.life_state) || ib_switch_info_get_state_change( &si ) ) { - osm_log( p_mgr->p_log, OSM_LOG_DEBUG, - "__osm_ucast_mgr_set_table: " - "Setting switch FT top to LID 0x%X\n", - osm_switch_get_max_lid_ho( p_sw ) ); + set_swinfo_require = TRUE; + si.life_state = life_state; } - - context.si_context.light_sweep = FALSE; - context.si_context.node_guid = osm_node_get_node_guid( p_node ); - context.si_context.set_method = TRUE; - - status = osm_req_set( p_mgr->p_req, - p_path, - (uint8_t*)&si, - sizeof(si), - IB_MAD_ATTR_SWITCH_INFO, - 0, - CL_DISP_MSGID_NONE, - &context ); - - if( status != IB_SUCCESS ) + + if ( set_swinfo_require ) { - osm_log( p_mgr->p_log, OSM_LOG_ERROR, - "__osm_ucast_mgr_set_table: ERR 3A06: " - "Sending SwitchInfo attribute failed (%s)\n", - ib_get_err_str( status ) ); + if ( osm_log_is_active( p_mgr->p_log, OSM_LOG_DEBUG ) ) + { + osm_log( p_mgr->p_log, OSM_LOG_DEBUG, + "osm_ucast_mgr_set_fwd_table: " + "Setting switch FT top to LID 0x%X\n", + osm_switch_get_max_lid_ho( p_sw ) ); + } + + context.si_context.light_sweep = FALSE; + context.si_context.node_guid = osm_node_get_node_guid( p_node ); + context.si_context.set_method = TRUE; + + status = osm_req_set( p_mgr->p_req, + p_path, + (uint8_t*)&si, + sizeof(si), + IB_MAD_ATTR_SWITCH_INFO, + 0, + CL_DISP_MSGID_NONE, + &context ); + + if( status != IB_SUCCESS ) + { + osm_log( p_mgr->p_log, OSM_LOG_ERROR, + "osm_ucast_mgr_set_fwd_table: ERR 3A06: " + "Sending SwitchInfo attribute failed (%s)\n", + ib_get_err_str( status ) ); + } + else + p_mgr->any_change = TRUE; } /* @@ -871,18 +970,23 @@ __osm_ucast_mgr_set_table( context.lft_context.node_guid = osm_node_get_node_guid( p_node ); context.lft_context.set_method = TRUE; - while( osm_switch_get_fwd_tbl_block( p_sw, block_id_ho, block ) ) + for (block_id_ho = 0; + osm_switch_get_fwd_tbl_block( p_sw, block_id_ho, block ) ; + block_id_ho++ ) { + if (!memcmp(block, p_mgr->lft_buf + block_id_ho * 64, 64)) + continue; + if( osm_log_is_active( p_mgr->p_log, OSM_LOG_DEBUG ) ) { osm_log( p_mgr->p_log, OSM_LOG_DEBUG, - "__osm_ucast_mgr_set_table: " + "osm_ucast_mgr_set_fwd_table: " "Writing FT block %u\n", block_id_ho ); } status = osm_req_set( p_mgr->p_req, p_path, - block, + p_mgr->lft_buf + block_id_ho * 64, sizeof(block), IB_MAD_ATTR_LIN_FWD_TBL, cl_hton32( block_id_ho ), @@ -892,12 +996,21 @@ __osm_ucast_mgr_set_table( if( status != IB_SUCCESS ) { osm_log( p_mgr->p_log, OSM_LOG_ERROR, - "__osm_ucast_mgr_set_table: ERR 3A05: " + "osm_ucast_mgr_set_fwd_table: ERR 3A05: " "Sending linear fwd. tbl. block failed (%s)\n", ib_get_err_str( status ) ); } - - block_id_ho++; + else + { + p_mgr->any_change = TRUE; + /* + HACK: for now we will assume we succeeded to send + and set the local DB based on it. This should allow + us to immediatly dump out our routing. + */ + osm_switch_set_ft_block( + p_sw, p_mgr->lft_buf + block_id_ho * 64, block_id_ho ); + } } OSM_LOG_EXIT( p_mgr->p_log ); @@ -931,6 +1044,9 @@ __osm_ucast_mgr_process_tbl( cl_ntoh64( osm_node_get_node_guid( p_node ) )); } + /* Initialize LIDs in buffer to invalid port number. */ + memset(p_mgr->lft_buf, 0xff, IB_LID_UCAST_END_HO + 1); + p_port_tbl = &p_mgr->p_subn->port_guid_tbl; /* @@ -945,10 +1061,8 @@ __osm_ucast_mgr_process_tbl( __osm_ucast_mgr_process_port( p_mgr, p_sw, p_port ); } - __osm_ucast_mgr_set_table( p_mgr, p_sw ); + osm_ucast_mgr_set_fwd_table( p_mgr, p_sw ); - osm_ucast_mgr_dump_path_distribution( p_mgr, p_sw ); - osm_ucast_mgr_dump_ucast_routes( p_mgr, p_sw ); OSM_LOG_EXIT( p_mgr->p_log ); } @@ -963,8 +1077,6 @@ __osm_ucast_mgr_process_neighbors( osm_ucast_mgr_t* const p_mgr = (osm_ucast_mgr_t*)context; osm_node_t *p_node; osm_node_t *p_remote_node; - ib_net64_t remote_node_guid; - osm_switch_t *p_remote_sw; uint32_t port_num; uint8_t remote_port_num; uint32_t num_ports; @@ -981,8 +1093,8 @@ __osm_ucast_mgr_process_neighbors( { osm_log( p_mgr->p_log, OSM_LOG_DEBUG, "__osm_ucast_mgr_process_neighbors: " - "Processing switch with GUID = 0x%" PRIx64 "\n", - cl_ntoh64( osm_node_get_node_guid( p_node ) )); + "Processing switch with GUID 0x%" PRIx64 "\n", + cl_ntoh64( osm_node_get_node_guid( p_node ) ) ); } num_ports = osm_node_get_num_physp( p_node ); @@ -996,36 +1108,17 @@ __osm_ucast_mgr_process_neighbors( (uint8_t)port_num, &remote_port_num ); if( p_remote_node && (p_remote_node != p_node ) - && (osm_node_get_type( p_remote_node ) - == IB_NODE_TYPE_SWITCH )) + && p_remote_node->sw ) { /* make sure the link is healthy. If it is not - don't propagate through it. */ p_physp = osm_node_get_physp_ptr( p_node, port_num ); - if (!osm_link_is_healthy( p_physp ) ) continue; - - remote_node_guid = osm_node_get_node_guid( p_remote_node ); + if (!osm_link_is_healthy( p_physp ) ) + continue; - p_remote_sw = (osm_switch_t*)cl_qmap_get( - &p_mgr->p_subn->sw_guid_tbl, remote_node_guid ); + __osm_ucast_mgr_process_neighbor(p_mgr, p_sw, p_remote_node->sw, + (uint8_t)port_num, remote_port_num ); - if( p_remote_sw == (osm_switch_t*)cl_qmap_end( - &p_mgr->p_subn->sw_guid_tbl ) ) - { - osm_log( p_mgr->p_log, OSM_LOG_ERROR, - "__osm_ucast_mgr_process_neighbors: ERR 3A07: " - "No switch object for Node GUID = 0x%" PRIx64 "\n", - cl_ntoh64( remote_node_guid ) ); - } - else - { - __osm_ucast_mgr_process_neighbor( - p_mgr, - p_sw, - p_remote_sw, - (uint8_t)port_num, - remote_port_num ); - } } } @@ -1034,28 +1127,23 @@ __osm_ucast_mgr_process_neighbors( /********************************************************************** **********************************************************************/ -osm_signal_t -osm_ucast_mgr_process( +void +osm_ucast_mgr_build_lid_matrices( IN osm_ucast_mgr_t* const p_mgr ) { uint32_t i; uint32_t iteration_max; - osm_signal_t signal; cl_qmap_t *p_sw_guid_tbl; - OSM_LOG_ENTER( p_mgr->p_log, osm_ucast_mgr_process ); - p_sw_guid_tbl = &p_mgr->p_subn->sw_guid_tbl; - CL_PLOCK_EXCL_ACQUIRE( p_mgr->p_lock ); - - osm_log(p_mgr->p_log, OSM_LOG_VERBOSE, - "osm_ucast_mgr_process: " - "Starting switches Min Hop Table Assignment\n"); + osm_log( p_mgr->p_log, OSM_LOG_VERBOSE, + "osm_ucast_mgr_build_lid_matrices: " + "Starting switches Min Hop Table Assignment\n" ); /* - Set the switch matrixes for each switch's own port 0 LID, - then set the lid matrixes for the each switch's leaf nodes. + Set the switch matrices for each switch's own port 0 LID(s) + then set the lid matrices for the each switch's leaf nodes. */ cl_qmap_apply_func( p_sw_guid_tbl, __osm_ucast_mgr_process_hop_0, p_mgr ); @@ -1064,15 +1152,15 @@ osm_ucast_mgr_process( __osm_ucast_mgr_process_leaves, p_mgr ); /* - Get the switch matrixes for each switch's neighbors. + Get the switch matrices for each switch's neighbors. This process requires a number of iterations equal to the number of switches in the subnet minus 1. In each iteration, a switch learns the lid/port/hop - information (as contained by a switch's lid matrix) from its - immediate neighbors. After each - iteration, a switch (and it's neighbors) know more - routing information than it did on the previous iteration. + information (as contained by a switch's lid matrix) from + its immediate neighbors. After each iteration, a switch + (and it's neighbors) know more routing information than + it did on the previous iteration. Thus, by repeatedly absorbing the routing information of neighbor switches, every switch eventually learns how to route all LIDs on the subnet. @@ -1080,7 +1168,7 @@ osm_ucast_mgr_process( Note that there may not be any switches in the subnet if we are in simple p2p configuration. */ - iteration_max = cl_qmap_count( &p_mgr->p_subn->sw_guid_tbl ); + iteration_max = cl_qmap_count( p_sw_guid_tbl ); /* If there are switches in the subnet, iterate until the lid @@ -1106,65 +1194,82 @@ osm_ucast_mgr_process( __osm_ucast_mgr_process_neighbors, p_mgr ); } osm_log( p_mgr->p_log, OSM_LOG_DEBUG, - "osm_ucast_mgr_process: " - "Min-hop propagated in %d steps\n", - i - ); + "osm_ucast_mgr_build_lid_matrices: " + "Min-hop propagated in %d steps\n", i ); + } +} - /* - This is the place where we can load pre-defined routes - into the switches fwd_tbl structures. +/********************************************************************** + **********************************************************************/ +osm_signal_t +osm_ucast_mgr_process( + IN osm_ucast_mgr_t* const p_mgr ) +{ + struct osm_routing_engine *p_routing_eng; + osm_signal_t signal = OSM_SIGNAL_DONE; + cl_qmap_t *p_sw_guid_tbl; + boolean_t default_routing = TRUE; - Later code will use these values if not configured for - re-assignment. - */ - if (p_mgr->p_subn->opt.pfn_ui_ucast_fdb_assign) - { - if( osm_log_is_active( p_mgr->p_log, OSM_LOG_DEBUG ) ) - { - osm_log( p_mgr->p_log, OSM_LOG_DEBUG, - "osm_ucast_mgr_process: " - "Invoking UI function pfn_ui_ucast_fdb_assign\n"); - } - p_mgr->p_subn->opt.pfn_ui_ucast_fdb_assign(p_mgr->p_subn->opt.ui_ucast_fdb_assign_ctx); - } else { - osm_log( p_mgr->p_log, OSM_LOG_DEBUG, - "osm_ucast_mgr_process: " - "UI pfn was not invoked\n"); - } + OSM_LOG_ENTER( p_mgr->p_log, osm_ucast_mgr_process ); - osm_log(p_mgr->p_log, OSM_LOG_INFO, - "osm_ucast_mgr_process: " - "Min Hop Tables configured on all switches\n"); + p_sw_guid_tbl = &p_mgr->p_subn->sw_guid_tbl; + p_routing_eng = &p_mgr->p_subn->p_osm->routing_engine; - /* - Now that the lid matrixes have been built, we can - build and download the switch forwarding tables. - */ + CL_PLOCK_EXCL_ACQUIRE( p_mgr->p_lock ); - /* initialize the fdb dump file: */ - if( osm_log_is_active( p_mgr->p_log, OSM_LOG_ROUTING ) ) - unlink("/tmp/osm.fdbs"); + /* + If there are no switches in the subnet, we are done. + */ + if (cl_qmap_count( p_sw_guid_tbl ) == 0) + goto Exit; - cl_qmap_apply_func( p_sw_guid_tbl, - __osm_ucast_mgr_process_tbl, p_mgr ); + p_mgr->any_change = FALSE; + cl_qmap_apply_func(p_sw_guid_tbl, __osm_ucast_mgr_clean_switch, NULL); - /* - For now dont' bother checking if the switch forwarding tables - actually needed updating. The current code will always update - them, and thus leave transactions pending on the wire. - Therefore, return OSM_SIGNAL_DONE_PENDING. - */ + if (!p_routing_eng->build_lid_matrices || + p_routing_eng->build_lid_matrices(p_routing_eng->context) != 0) + osm_ucast_mgr_build_lid_matrices(p_mgr); + + osm_log( p_mgr->p_log, OSM_LOG_INFO, + "osm_ucast_mgr_process: " + "Min Hop Tables configured on all switches\n" ); + + /* + Now that the lid matrices have been built, we can + build and download the switch forwarding tables. + */ + if ( p_routing_eng->ucast_build_fwd_tables && + (p_routing_eng->ucast_build_fwd_tables(p_routing_eng->context) == 0) ) + default_routing = FALSE; + else + cl_qmap_apply_func( p_sw_guid_tbl, __osm_ucast_mgr_process_tbl, p_mgr ); + + /* dump fdb into file: */ + if ( osm_log_is_active( p_mgr->p_log, OSM_LOG_ROUTING ) ) + { + if ( !default_routing && p_routing_eng->ucast_dump_tables != 0 ) + p_routing_eng->ucast_dump_tables(p_routing_eng->context); + else + __osm_ucast_mgr_dump_tables( p_mgr ); + } + + if (p_mgr->any_change) + { signal = OSM_SIGNAL_DONE_PENDING; + osm_log( p_mgr->p_log, OSM_LOG_VERBOSE, + "osm_ucast_mgr_process: " + "LFT Tables configured on all switches\n"); } else + { signal = OSM_SIGNAL_DONE; + osm_log( p_mgr->p_log, OSM_LOG_VERBOSE, + "osm_ucast_mgr_process: " + "No need to set any LFT Tables on any switches\n"); + } - osm_log(p_mgr->p_log, OSM_LOG_VERBOSE, - "osm_ucast_mgr_process: " - "LFT Tables configured on all switches\n"); - + Exit: CL_PLOCK_RELEASE( p_mgr->p_lock ); OSM_LOG_EXIT( p_mgr->p_log ); return( signal ); diff --git a/trunk/ulp/opensm/user/opensm/osm_ucast_updn.c b/trunk/ulp/opensm/user/opensm/osm_ucast_updn.c index 24fea111..d23b52c4 100644 --- a/trunk/ulp/opensm/user/opensm/osm_ucast_updn.c +++ b/trunk/ulp/opensm/user/opensm/osm_ucast_updn.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -47,38 +47,93 @@ # include #endif /* HAVE_CONFIG_H */ +#include #include #include #include #include -#include -#include +/* //////////////////////////// */ +/* Local types */ +/* //////////////////////////// */ + +/* direction */ +typedef enum _updn_switch_dir +{ + UP = 0, + DOWN +} updn_switch_dir_t; + +/* This enum respresent available states in the UPDN algorithm */ +typedef enum _updn_state +{ + UPDN_INIT = 0, + UPDN_RANK, + UPDN_MIN_HOP_CALC, +} updn_state_t; + +/* Rank value of this node */ +typedef struct _updn_rank +{ + cl_map_item_t map_item; + uint8_t rank; +} updn_rank_t; + +/* Histogram element - the number of occurences of the same hop value */ +typedef struct _updn_hist +{ + cl_map_item_t map_item; + uint32_t bar_value; +} updn_hist_t; + +typedef struct _updn_next_step +{ + updn_switch_dir_t state; + osm_switch_t *p_sw; +} updn_next_step_t; + +/* guids list */ +typedef struct _updn_input +{ + uint32_t num_guids; + uint64_t * guid_list; +} updn_input_t; + +/* updn structure */ +typedef struct _updn +{ + updn_state_t state; + boolean_t auto_detect_root_nodes; + cl_qmap_t guid_rank_tbl; + updn_input_t updn_ucast_reg_inputs; + cl_list_t * p_root_nodes; + osm_opensm_t *p_osm; +} updn_t; /* ///////////////////////////////// */ -/* Globals */ +/* Statics */ /* ///////////////////////////////// */ -/* This var is pre defined and initialized */ -extern osm_opensm_t osm; +static int __osm_updn_find_root_nodes_by_min_hop(OUT updn_t *p_updn); /********************************************************************** **********************************************************************/ /* This function returns direction based on rank and guid info of current & remote ports */ - -updn_switch_dir_t -__updn_get_dir(IN uint8_t cur_rank, - IN uint8_t rem_rank, - IN uint64_t cur_guid, - IN uint64_t rem_guid) +static updn_switch_dir_t +__updn_get_dir( + IN updn_t *p_updn, + IN uint8_t cur_rank, + IN uint8_t rem_rank, + IN uint64_t cur_guid, + IN uint64_t rem_guid ) { - uint32_t i = 0, max_num_guids = osm.p_updn_ucast_routing->updn_ucast_reg_inputs.num_guids; - uint64_t *p_guid = osm.p_updn_ucast_routing->updn_ucast_reg_inputs.guid_list; - boolean_t cur_is_root = FALSE , rem_is_root = FALSE; + uint32_t i = 0, max_num_guids = p_updn->updn_ucast_reg_inputs.num_guids; + uint64_t *p_guid = p_updn->updn_ucast_reg_inputs.guid_list; + boolean_t cur_is_root = FALSE, rem_is_root = FALSE; - /* HACK: comes to solve root nodes connection, in a classic subnet root nodes does not connect + /* HACK: comes to solve root nodes connection, in a classic subnet root nodes do not connect directly, but in case they are we assign to root node an UP direction to allow UPDN discover - correctly (and not from the point of view of the last root node) the subnet . + the subnet correctly (and not from the point of view of the last root node). */ for ( i = 0; i < max_num_guids; i++ ) { @@ -90,7 +145,6 @@ __updn_get_dir(IN uint8_t cur_rank, if (cur_is_root && rem_is_root) return UP; - if (cur_rank < rem_rank) return DOWN; else if (cur_rank > rem_rank) @@ -109,41 +163,46 @@ __updn_get_dir(IN uint8_t cur_rank, **********************************************************************/ /* This function creates a new element of updn_next_step_t type then return its pointer , Null if malloc has failed */ -updn_next_step_t* -__updn_create_updn_next_step_t(IN updn_switch_dir_t state, IN osm_switch_t* const p_sw) +static updn_next_step_t* +__updn_create_updn_next_step_t( + IN updn_switch_dir_t state, + IN osm_switch_t* const p_sw ) { updn_next_step_t *p_next_step; - p_next_step = (updn_next_step_t*) cl_zalloc(sizeof(*p_next_step)); - CL_ASSERT (p_next_step != NULL); + p_next_step = (updn_next_step_t*) malloc(sizeof(*p_next_step)); + if (p_next_step) + { + memset(p_next_step, 0, sizeof(*p_next_step)); + p_next_step->state = state; + p_next_step->p_sw = p_sw; + } - p_next_step->state = state; - p_next_step->p_sw = p_sw; return p_next_step; - } /********************************************************************** **********************************************************************/ /* This function updates an element in the qmap list by guid index and rank value */ /* Return 0 if no need to futher update 1 if brought a new value */ -int +static int __updn_update_rank( IN cl_qmap_t *p_guid_rank_tbl, - IN ib_net64_t guid_index, - IN uint8_t rank) + IN ib_net64_t guid, + IN uint8_t rank ) { updn_rank_t *p_updn_rank; - p_updn_rank = (updn_rank_t*) cl_qmap_get(p_guid_rank_tbl, guid_index); + p_updn_rank = (updn_rank_t*) cl_qmap_get(p_guid_rank_tbl, guid); if (p_updn_rank == (updn_rank_t*) cl_qmap_end(p_guid_rank_tbl)) { - p_updn_rank = (updn_rank_t*) cl_malloc(sizeof(updn_rank_t)); + p_updn_rank = (updn_rank_t*) malloc(sizeof(updn_rank_t)); + CL_ASSERT (p_updn_rank); p_updn_rank->rank = rank; - cl_qmap_insert(p_guid_rank_tbl, guid_index , &p_updn_rank->map_item); + cl_qmap_insert(p_guid_rank_tbl, guid, &p_updn_rank->map_item); return 1; } else @@ -158,14 +217,17 @@ __updn_update_rank( } /********************************************************************** - * This function do the bfs of min hop table calculation by guid index as a - * starting point. + * This function does the bfs of min hop table calculation by guid index + * as a starting point. **********************************************************************/ -int -__updn_bfs_by_node(IN osm_subn_t *p_subn, IN ib_net64_t guid_index, IN cl_qmap_t *p_guid_rank_tbl) +static int +__updn_bfs_by_node( + IN updn_t *p_updn, + IN osm_subn_t *p_subn, + IN osm_port_t *p_port, + IN cl_qmap_t *p_guid_rank_tbl ) { - /* Init local vars */ - osm_port_t *p_port; + /* Init local vars */ osm_switch_t *p_self_node = NULL; uint8_t pn, pn_rem; osm_physp_t *p_physp, *p_remote_physp; @@ -173,44 +235,43 @@ __updn_bfs_by_node(IN osm_subn_t *p_subn, IN ib_net64_t guid_index, IN cl_qmap_t uint16_t root_lid, max_sw_lid; updn_next_step_t *p_updn_switch, *p_tmp; updn_switch_dir_t next_dir, current_dir; + osm_log_t *p_log = &p_updn->p_osm->log; - OSM_LOG_ENTER( &(osm.log), __updn_bfs_by_node); + OSM_LOG_ENTER( p_log, __updn_bfs_by_node ); /* Init the list pointers */ - p_nextList = (cl_list_t*)cl_malloc(sizeof(cl_list_t)); + p_nextList = (cl_list_t*)malloc(sizeof(cl_list_t)); cl_list_construct( p_nextList ); cl_list_init( p_nextList, 10 ); p_currList = p_nextList; - p_port = (osm_port_t*) cl_qmap_get(&(p_subn->port_guid_tbl),guid_index); - /* TODO : check if p_port is not NULL */ p_physp = osm_port_get_default_phys_ptr(p_port); /* Check valid pointer */ if (!p_physp || !osm_physp_is_valid(p_physp )) { - OSM_LOG_EXIT( &(osm.log)); + OSM_LOG_EXIT( p_log ); return 1; } /* The Root BFS - lid */ root_lid = cl_ntoh16(osm_physp_get_base_lid( p_physp )); - /* printf ("-V- BFS through lid : 0x%x\n",root_lid); */ - osm_log(&(osm.log), OSM_LOG_DEBUG, - "__updn_bfs_by_node:" - "Starting lid : 0x%x \n", root_lid); + /* printf ("-V- BFS through lid : 0x%x\n", root_lid); */ + osm_log( p_log, OSM_LOG_DEBUG, + "__updn_bfs_by_node:" + "Starting lid : 0x%x \n", root_lid ); - if (osm_node_get_type( p_port->p_node ) == IB_NODE_TYPE_SWITCH) + if (p_port->p_node->sw) { - p_self_node = osm_get_switch_by_guid(p_subn, guid_index); + p_self_node = p_port->p_node->sw; /* Update its Min Hop Table */ - osm_log(&(osm.log), OSM_LOG_DEBUG, - "__updn_bfs_by_node:" - "Update Min Hop Table of guid 0x%" PRIx64 "\n" - , cl_ntoh64(p_port->guid)); - osm_switch_set_hops(p_self_node, root_lid , 0, 0); + osm_log( p_log, OSM_LOG_DEBUG, + "__updn_bfs_by_node:" + "Update Min Hop Table of GUID 0x%" PRIx64 "\n", + cl_ntoh64(p_port->guid) ); + osm_switch_set_hops(p_self_node, root_lid, 0, 0); } else { - /* This is an HCA need to take its remote port */ + /* This is a CA or router - need to take its remote port */ p_remote_physp = p_physp->p_remote_physp; /* make sure that the following occur: @@ -221,37 +282,38 @@ __updn_bfs_by_node(IN osm_subn_t *p_subn, IN ib_net64_t guid_index, IN cl_qmap_t { /* Check if the remote port is a switch, if it is update root_lid, Min Hop Table */ - if (osm_node_get_type(p_remote_physp->p_node) != IB_NODE_TYPE_SWITCH) + if (!p_remote_physp->p_node->sw) { - osm_log(&(osm.log), OSM_LOG_ERROR, - "__updn_bfs_by_node: ERR AA07: " - "This is a non switched subnet OR non valid connection, cannot perform UPDN algorithm\n"); - OSM_LOG_EXIT( &(osm.log)); + osm_log( p_log, OSM_LOG_ERROR, + "__updn_bfs_by_node: ERR AA07: " + "This is a non switched subnet OR non valid connection, cannot perform UPDN algorithm\n" ); + OSM_LOG_EXIT( p_log ); return 1; - } else + } + else { - p_self_node = osm_get_switch_by_guid(p_subn, - osm_physp_get_port_guid - (p_remote_physp)); + p_self_node = p_remote_physp->p_node->sw; max_sw_lid = osm_switch_get_max_lid_ho(p_self_node); if ((1 <= root_lid) && (root_lid <= max_sw_lid)) /* Update its Min Hop Table */ { /* NOTE : Check if there is a function which prints the Min Hop Table */ - osm_log(&(osm.log), OSM_LOG_DEBUG, - "__updn_bfs_by_node:" - "Update Min Hop Table of guid 0x%" PRIx64 "\n" - , cl_ntoh64(p_remote_physp->port_guid)); - osm_switch_set_hops(p_self_node, root_lid - , p_remote_physp->port_num, 1); - - } else + osm_log( p_log, OSM_LOG_DEBUG, + "__updn_bfs_by_node:" + "Update Min Hop Table of GUID 0x%" PRIx64 "\n", + cl_ntoh64(p_remote_physp->port_guid) ); + osm_switch_set_hops(p_self_node, root_lid, + p_remote_physp->port_num, 1); + + } + else { - osm_log(&(osm.log), OSM_LOG_ERROR, - "__updn_bfs_by_node: ERR AA09: " - " Invalid lid value 0x%x for switch 0x%" PRIx64 "\n", root_lid - , cl_ntoh64(p_self_node->p_node->node_info.port_guid)); - OSM_LOG_EXIT( &(osm.log)); + osm_log( p_log, OSM_LOG_ERROR, + "__updn_bfs_by_node: ERR AA09: " + " Invalid lid value 0x%x for switch 0x%" PRIx64 "\n", + root_lid, + cl_ntoh64(p_self_node->p_node->node_info.port_guid) ); + OSM_LOG_EXIT( p_log ); return 1; } } @@ -260,36 +322,37 @@ __updn_bfs_by_node(IN osm_subn_t *p_subn, IN ib_net64_t guid_index, IN cl_qmap_t CL_ASSERT(p_self_node); - osm_log(&(osm.log), OSM_LOG_DEBUG, - "__updn_bfs_by_node:" - "Starting from switch- port guid 0x%" PRIx64 "\n" - , cl_ntoh64(p_self_node->p_node->node_info.port_guid)); + osm_log( p_log, OSM_LOG_DEBUG, + "__updn_bfs_by_node:" + "Starting from switch - port GUID 0x%" PRIx64 "\n", + cl_ntoh64(p_self_node->p_node->node_info.port_guid) ); /* Update list with the updn_next_step_t new element */ - /* NOTE : When inserting an item which is a pointer to a struct , does remove + /* NOTE : When inserting an item which is a pointer to a struct, does remove action also free its memory */ if (!(p_tmp=__updn_create_updn_next_step_t(UP, p_self_node))) { - osm_log(&(osm.log), OSM_LOG_ERROR, - "__updn_bfs_by_node: ERR AA08: " - "Could not create updn_next_step_t\n"); + osm_log( p_log, OSM_LOG_ERROR, + "__updn_bfs_by_node: ERR AA08: " + "Could not create updn_next_step_t\n" ); return 1; } - cl_list_insert_tail(p_currList,p_tmp ); + cl_list_insert_tail(p_currList, p_tmp); /* BFS the list till no next element */ - osm_log(&(osm.log), OSM_LOG_VERBOSE, - "__updn_bfs_by_node:" - "BFS the subnet [\n"); + osm_log( p_log, OSM_LOG_VERBOSE, + "__updn_bfs_by_node:" + "BFS the subnet [\n" ); while (!cl_is_list_empty(p_currList)) { - osm_log(&(osm.log), OSM_LOG_DEBUG, - "__updn_bfs_by_node:" - "Starting a new iteration with %d elements in current list\n", cl_list_count(p_currList)); + osm_log( p_log, OSM_LOG_DEBUG, + "__updn_bfs_by_node:" + "Starting a new iteration with %zu elements in current list\n", + cl_list_count(p_currList) ); /* Init the switch directed list */ - p_nextList = (cl_list_t*)cl_malloc(sizeof(cl_list_t)); + p_nextList = (cl_list_t*)malloc(sizeof(cl_list_t)); cl_list_construct( p_nextList ); cl_list_init( p_nextList, 10 ); /* Go over all current list items till it's empty */ @@ -299,14 +362,14 @@ __updn_bfs_by_node(IN osm_subn_t *p_subn, IN ib_net64_t guid_index, IN cl_qmap_t while (p_updn_switch) { current_dir = p_updn_switch->state; - osm_log(&(osm.log), OSM_LOG_DEBUG, - "__updn_bfs_by_node:" - "Visiting port guid 0x%" PRIx64 "\n" - , cl_ntoh64(p_updn_switch->p_sw->p_node->node_info.port_guid)); + osm_log( p_log, OSM_LOG_DEBUG, + "__updn_bfs_by_node:" + "Visiting port GUID 0x%" PRIx64 "\n", + cl_ntoh64(p_updn_switch->p_sw->p_node->node_info.port_guid) ); /* Go over all ports of the switch and find unvisited remote nodes */ for ( pn = 0; pn < osm_switch_get_num_ports(p_updn_switch->p_sw); pn++ ) { - /* printf("-V- Inner for in port num %d\n", pn); */ + /* printf("-V- Inner for in port num 0x%X\n", pn); */ osm_node_t *p_remote_node; cl_list_iterator_t updn_switch_iterator; boolean_t HasVisited = FALSE; @@ -325,29 +388,29 @@ __updn_bfs_by_node(IN osm_subn_t *p_subn, IN ib_net64_t guid_index, IN cl_qmap_t continue; /* Fetch remote guid only after validation of remote node */ remote_guid = osm_node_get_node_guid(p_remote_node); - /* printf ("-V- Current guid : 0x%" PRIx64 " Remote guid : 0x%" PRIx64 "\n" */ - /* , cl_ntoh64(current_guid), cl_ntoh64(remote_guid)); */ - p_remote_sw = osm_get_switch_by_guid(p_subn, remote_guid); + /* printf ("-V- Current guid : 0x%" PRIx64 " Remote guid : 0x%" PRIx64 "\n", */ + /* cl_ntoh64(current_guid), cl_ntoh64(remote_guid)); */ + p_remote_sw = p_remote_node->sw; p_rem_rank = (updn_rank_t*)cl_qmap_get(p_guid_rank_tbl, remote_guid); p_cur_rank = (updn_rank_t*)cl_qmap_get(p_guid_rank_tbl, current_guid); /* Decide which direction to mark it (UP/DOWN) */ - next_dir = __updn_get_dir (p_cur_rank->rank, p_rem_rank->rank, + next_dir = __updn_get_dir (p_updn, p_cur_rank->rank, p_rem_rank->rank, current_guid, remote_guid); - osm_log(&(osm.log), OSM_LOG_DEBUG, - "__updn_bfs_by_node:" - "move from 0x%016" PRIx64 " rank: %u " - "to 0x%016" PRIx64" rank: %u\n", - cl_ntoh64(current_guid), p_cur_rank->rank, - cl_ntoh64(remote_guid), p_rem_rank->rank); + osm_log( p_log, OSM_LOG_DEBUG, + "__updn_bfs_by_node:" + "move from 0x%016" PRIx64 " rank: %u " + "to 0x%016" PRIx64" rank: %u\n", + cl_ntoh64(current_guid), p_cur_rank->rank, + cl_ntoh64(remote_guid), p_rem_rank->rank ); /* Check if this is a legal step : the only illegal step is going from DOWN to UP */ if ((current_dir == DOWN) && (next_dir == UP)) { - osm_log(&(osm.log), OSM_LOG_DEBUG, - "__updn_bfs_by_node:" - "Avoiding move from 0x%016" PRIx64 " to 0x%016" PRIx64"\n", - cl_ntoh64(current_guid), cl_ntoh64(remote_guid)); + osm_log( p_log, OSM_LOG_DEBUG, + "__updn_bfs_by_node:" + "Avoiding move from 0x%016" PRIx64 " to 0x%016" PRIx64"\n", + cl_ntoh64(current_guid), cl_ntoh64(remote_guid) ); /* Illegal step */ continue; } @@ -355,23 +418,25 @@ __updn_bfs_by_node(IN osm_subn_t *p_subn, IN ib_net64_t guid_index, IN cl_qmap_t current_min_hop = osm_switch_get_least_hops(p_updn_switch->p_sw,root_lid); /* Check hop count if better insert into NextState list && update the remote node Min Hop Table */ - remote_min_hop = osm_switch_get_hop_count(p_remote_sw,root_lid, pn_rem); + remote_min_hop = osm_switch_get_hop_count(p_remote_sw, root_lid, pn_rem); if (current_min_hop + 1 < remote_min_hop) { - osm_log(&(osm.log), OSM_LOG_DEBUG, - "__updn_bfs_by_node (less):" - "Setting Min Hop Table of switch: 0x%" PRIx64 - "\n\t\tCurrent hop count is: %d, next hop count: %d" - "\n\tlid to set: 0x%x" - "\n\tport number: %d" - " \n\thops number: %d\n" - , cl_ntoh64(remote_guid), remote_min_hop,current_min_hop + 1, root_lid, pn_rem, current_min_hop + 1); - set_hop_return_value=osm_switch_set_hops(p_remote_sw, root_lid, pn_rem, current_min_hop + 1); + osm_log( p_log, OSM_LOG_DEBUG, + "__updn_bfs_by_node (less):" + "Setting Min Hop Table of switch: 0x%" PRIx64 + "\n\t\tCurrent hop count is: %d, next hop count: %d" + "\n\tlid to set: 0x%x" + "\n\tport number: 0x%X" + " \n\thops number: %d\n", + cl_ntoh64(remote_guid), remote_min_hop,current_min_hop + 1, + root_lid, pn_rem, current_min_hop + 1 ); + set_hop_return_value = osm_switch_set_hops(p_remote_sw, root_lid, pn_rem, current_min_hop + 1); if (set_hop_return_value) { - osm_log(&(osm.log), OSM_LOG_ERROR, - "__updn_bfs_by_node (less) ERR AA01: " - "Invalid value returned from set min hop is: %d\n", set_hop_return_value); + osm_log( p_log, OSM_LOG_ERROR, + "__updn_bfs_by_node (less) ERR AA01: " + "Invalid value returned from set min hop is: %d\n", + set_hop_return_value ); } /* Check if remote port is allready has been visited */ updn_switch_iterator = cl_list_head(p_nextList); @@ -392,66 +457,68 @@ __updn_bfs_by_node(IN osm_subn_t *p_subn, IN ib_net64_t guid_index, IN cl_qmap_t /* Insert updn_switch item into the next list */ if(!(p_tmp=__updn_create_updn_next_step_t(next_dir, p_remote_sw))) { - osm_log(&(osm.log), OSM_LOG_ERROR, - "__updn_bfs_by_node: ERR AA11: " - "Could not create updn_next_step_t\n"); + osm_log( p_log, OSM_LOG_ERROR, + "__updn_bfs_by_node: ERR AA11: " + "Could not create updn_next_step_t\n" ); return 1; } - osm_log(&(osm.log), OSM_LOG_DEBUG, - "__updn_bfs_by_node: " - "Inserting a new element to the next list: guid=0x%" PRIx64 " %s\n" - , cl_ntoh64(p_tmp->p_sw->p_node->node_info.port_guid), - (p_tmp->state == UP ? "UP" : "DOWN") - ); + osm_log( p_log, OSM_LOG_DEBUG, + "__updn_bfs_by_node: " + "Inserting new element to the next list: guid=0x%" PRIx64 " %s\n", + cl_ntoh64(p_tmp->p_sw->p_node->node_info.port_guid), + (p_tmp->state == UP ? "UP" : "DOWN") + ); cl_list_insert_tail(p_nextList, p_tmp); } /* If the same value only update entry - at the min hop table */ - } else if (current_min_hop + 1 == osm_switch_get_hop_count(p_remote_sw - , root_lid - , pn_rem)) + } else if (current_min_hop + 1 == osm_switch_get_hop_count(p_remote_sw, + root_lid, + pn_rem)) { - osm_log(&(osm.log), OSM_LOG_DEBUG, - "__updn_bfs_by_node (equal):" - "Setting Min Hop Table of switch: 0x%" PRIx64 - "\n\t\tCurrent hop count is: %d, next hop count: %d" - "\n\tlid to set: 0x%x" - "\n\tport number: %d" - "\n\thops number: %d\n" - , cl_ntoh64(remote_guid), osm_switch_get_hop_count(p_remote_sw, root_lid, pn_rem) - , current_min_hop + 1, root_lid, pn_rem, current_min_hop + 1); + osm_log( p_log, OSM_LOG_DEBUG, + "__updn_bfs_by_node (equal):" + "Setting Min Hop Table of switch: 0x%" PRIx64 + "\n\t\tCurrent hop count is: %d, next hop count: %d" + "\n\tlid to set: 0x%x" + "\n\tport number: 0x%X" + "\n\thops number: %d\n", + cl_ntoh64(remote_guid), + osm_switch_get_hop_count(p_remote_sw, root_lid, pn_rem), + current_min_hop + 1, root_lid, pn_rem, current_min_hop + 1 ); set_hop_return_value = osm_switch_set_hops(p_remote_sw, root_lid, pn_rem, current_min_hop + 1); if (set_hop_return_value) { - osm_log(&(osm.log), OSM_LOG_ERROR, - "__updn_bfs_by_node (less) ERR AA12: " - "Invalid value returned from set min hop is: %d\n", set_hop_return_value); + osm_log( p_log, OSM_LOG_ERROR, + "__updn_bfs_by_node (less) ERR AA12: " + "Invalid value returned from set min hop is: %d\n", + set_hop_return_value ); } } } - cl_free (p_updn_switch); + free (p_updn_switch); p_updn_switch = (updn_next_step_t*)cl_list_remove_head( p_currList ); } /* Cleanup p_currList */ cl_list_destroy( p_currList ); - cl_free (p_currList); + free (p_currList); /* Reassign p_currList to p_nextList */ p_currList = p_nextList; } /* Cleanup p_currList - Had the pointer to cl_list_t */ cl_list_destroy( p_currList ); - cl_free (p_currList); - osm_log(&(osm.log), OSM_LOG_VERBOSE, - "__updn_bfs_by_node:" - "BFS the subnet ]\n"); - OSM_LOG_EXIT( &(osm.log)); + free (p_currList); + osm_log( p_log, OSM_LOG_VERBOSE, + "__updn_bfs_by_node:" + "BFS the subnet ]\n" ); + OSM_LOG_EXIT( p_log ); return 0; } /********************************************************************** **********************************************************************/ -void +static void updn_destroy( IN updn_t* const p_updn ) { @@ -462,67 +529,69 @@ updn_destroy( p_map_item = cl_qmap_head( &p_updn->guid_rank_tbl); while( p_map_item != cl_qmap_end( &p_updn->guid_rank_tbl)) { - osm_log (&(osm.log), OSM_LOG_DEBUG, - "osm_subn_calc_up_down_min_hop_table: " - "guid = 0x%" PRIx64 " rank = %u\n", - cl_ntoh64(cl_qmap_key(p_map_item)), ((updn_rank_t *)p_map_item)->rank); + osm_log ( &p_updn->p_osm->log, OSM_LOG_DEBUG, + "osm_subn_calc_up_down_min_hop_table: " + "guid = 0x%" PRIx64 " rank = %u\n", + cl_ntoh64(cl_qmap_key(p_map_item)), + ((updn_rank_t *)p_map_item)->rank ); cl_qmap_remove_item( &p_updn->guid_rank_tbl, p_map_item); - cl_free( (updn_rank_t *)p_map_item); + free( (updn_rank_t *)p_map_item); p_map_item = cl_qmap_head( &p_updn->guid_rank_tbl); } /* free the array of guids */ if (p_updn->updn_ucast_reg_inputs.guid_list) - cl_free(p_updn->updn_ucast_reg_inputs.guid_list); + free(p_updn->updn_ucast_reg_inputs.guid_list); /* destroy the list of root nodes */ while ((p_guid_list_item = cl_list_remove_head( p_updn->p_root_nodes ))) - cl_free( p_guid_list_item ); + free( p_guid_list_item ); cl_list_remove_all( p_updn->p_root_nodes ); cl_list_destroy( p_updn->p_root_nodes ); - cl_free ( p_updn->p_root_nodes ); - cl_free (p_updn); + free ( p_updn->p_root_nodes ); + free (p_updn); } -updn_t* -updn_construct(void) +/********************************************************************** + **********************************************************************/ +static updn_t* +updn_construct(osm_log_t *p_log) { updn_t* p_updn; - OSM_LOG_ENTER( &(osm.log), updn_construct); - p_updn = cl_zalloc(sizeof(updn_t)); - OSM_LOG_EXIT( &(osm.log) ); + OSM_LOG_ENTER( p_log, updn_construct ); + p_updn = malloc(sizeof(updn_t)); + if (p_updn) + memset(p_updn, 0, sizeof(updn_t)); + OSM_LOG_EXIT( p_log ); return(p_updn); } /********************************************************************** **********************************************************************/ -cl_status_t +static cl_status_t updn_init( - IN updn_t* const p_updn ) + IN updn_t* const p_updn, + IN osm_opensm_t *p_osm ) { cl_list_t * p_list; - FILE* p_updn_guid_file; - char line[MAX_UPDN_GUID_FILE_LINE_LENGTH]; - uint64_t * p_tmp; + FILE* p_updn_guid_file; + char line[MAX_UPDN_GUID_FILE_LINE_LENGTH]; + uint64_t * p_tmp; cl_list_iterator_t guid_iterator; ib_api_status_t status = IB_SUCCESS; - OSM_LOG_ENTER( &(osm.log), updn_init ); - /* Make sure the p_updn isn't NULL */ - if (!p_updn) - { - status = IB_ERROR; - goto Exit_Bad; - } + OSM_LOG_ENTER( &p_osm->log, updn_init ); + + p_updn->p_osm = p_osm; p_updn->state = UPDN_INIT; - cl_qmap_init( &p_updn->guid_rank_tbl); - p_list = (cl_list_t*)cl_malloc(sizeof(cl_list_t)); + cl_qmap_init( &p_updn->guid_rank_tbl ); + p_list = (cl_list_t*)malloc(sizeof(cl_list_t)); if (!p_list) { status = IB_ERROR; - goto Exit_Bad; + goto Exit; } cl_list_construct( p_list ); @@ -531,78 +600,71 @@ updn_init( p_updn->updn_ucast_reg_inputs.num_guids = 0; p_updn->updn_ucast_reg_inputs.guid_list = NULL; p_updn->auto_detect_root_nodes = FALSE; - /* Check if updn is activated , then fetch root nodes */ - if (osm.subn.opt.updn_activate) + + /* + Check the source for root node list, if file parse it, otherwise + wait for a callback to activate auto detection + */ + if (p_osm->subn.opt.updn_guid_file) { - /* - Check the source for root node list, if file parse it, otherwise - wait for a callback to activate auto detection - */ - if (osm.subn.opt.updn_guid_file) + /* Now parse guid from file */ + p_updn_guid_file = fopen(p_osm->subn.opt.updn_guid_file, "r"); + if (p_updn_guid_file == NULL) { - /* Now parse guid from file */ - p_updn_guid_file = fopen(osm.subn.opt.updn_guid_file, "r"); - if (p_updn_guid_file == NULL) - { - osm_log( &osm.log, OSM_LOG_ERROR, - "osm_opensm_init : ERR AA02: " - "Failed to open guid list file (%s)\n", - osm.subn.opt.updn_guid_file); - status = IB_NOT_FOUND; - goto Exit; - } + osm_log( &p_osm->log, OSM_LOG_ERROR, + "osm_opensm_init : ERR AA02: " + "Failed to open guid list file (%s)\n", + p_osm->subn.opt.updn_guid_file ); + status = IB_NOT_FOUND; + goto Exit; + } - while ( fgets(line, MAX_UPDN_GUID_FILE_LINE_LENGTH, p_updn_guid_file) ) + while ( fgets(line, MAX_UPDN_GUID_FILE_LINE_LENGTH, p_updn_guid_file) ) + { + if (strcspn(line, " ,;.") == strlen(line)) { - if (strcspn(line, " ,;.") == strlen(line)) - { - /* Skip Empty Lines anywhere in the file - only one char means the Null termination */ - if (strlen(line) > 1) - { - p_tmp = cl_malloc(sizeof(uint64_t)); - *p_tmp = strtoull(line, NULL, 16); - cl_list_insert_tail(osm.p_updn_ucast_routing->p_root_nodes, p_tmp); - } - } - else + /* Skip empty lines anywhere in the file - only one char means the Null termination */ + if (strlen(line) > 1) { - osm_log( &osm.log, OSM_LOG_ERROR, - "osm_opensm_init: ERR AA03: " - "Bad formatted guid in file (%s) : %s\n" - , osm.subn.opt.updn_guid_file,line); - status = IB_NOT_FOUND; - break; + p_tmp = malloc(sizeof(uint64_t)); + *p_tmp = strtoull(line, NULL, 16); + cl_list_insert_tail(p_updn->p_root_nodes, p_tmp); } } - - /* For Debug Purposes ... */ - osm_log( &osm.log, OSM_LOG_DEBUG, - "osm_opensm_init: " - "UPDN - Root nodes fetching by file %s\n", - osm.subn.opt.updn_guid_file); - guid_iterator = cl_list_head(osm.p_updn_ucast_routing->p_root_nodes); - while( guid_iterator != cl_list_end(osm.p_updn_ucast_routing->p_root_nodes) ) + else { - osm_log( &osm.log, OSM_LOG_DEBUG, - "osm_opensm_init: " - "Inserting guid 0x%" PRIx64 " as root node\n", - *((uint64_t*)cl_list_obj(guid_iterator)) ); - guid_iterator = cl_list_next(guid_iterator); + osm_log( &p_osm->log, OSM_LOG_ERROR, + "osm_opensm_init: ERR AA03: " + "Bad formatted guid in file (%s): %s\n", + p_osm->subn.opt.updn_guid_file, line ); + status = IB_NOT_FOUND; + break; } } - else + + /* For Debug Purposes ... */ + osm_log( &p_osm->log, OSM_LOG_DEBUG, + "osm_opensm_init: " + "UPDN - Root nodes fetching by file %s\n", + p_osm->subn.opt.updn_guid_file ); + guid_iterator = cl_list_head(p_updn->p_root_nodes); + while( guid_iterator != cl_list_end(p_updn->p_root_nodes) ) { - osm.p_updn_ucast_routing->auto_detect_root_nodes = TRUE; + osm_log( &p_osm->log, OSM_LOG_DEBUG, + "osm_opensm_init: " + "Inserting GUID 0x%" PRIx64 " as root node\n", + *((uint64_t*)cl_list_obj(guid_iterator)) ); + guid_iterator = cl_list_next(guid_iterator); } - /* If auto mode detection reuired - will be executed in main b4 the assignment of UI Ucast */ } + else + { + p_updn->auto_detect_root_nodes = TRUE; + } + /* If auto mode detection required - will be executed in main b4 the assignment of UI Ucast */ - goto Exit; - - Exit_Bad : - return 1; - Exit : - OSM_LOG_EXIT( &(osm.log) ); +Exit : + OSM_LOG_EXIT( &p_osm->log ); return (status); } @@ -610,11 +672,11 @@ updn_init( **********************************************************************/ /* NOTE : PLS check if we need to decide that the first */ /* rank is a SWITCH for BFS purpose */ -int +static int updn_subn_rank( IN uint64_t root_guid, IN uint8_t base_rank, - IN updn_t* p_updn) + IN updn_t* p_updn ) { /* Init local vars */ osm_port_t *p_root_port = NULL; @@ -624,46 +686,46 @@ updn_subn_rank( cl_list_t *p_currList,*p_nextList; cl_status_t did_cause_update; uint8_t num_ports, port_num; + osm_log_t *p_log = &p_updn->p_osm->log; - OSM_LOG_ENTER( &(osm.log), updn_subn_rank); + OSM_LOG_ENTER( p_log, updn_subn_rank ); - osm_log(&(osm.log), OSM_LOG_VERBOSE, - "updn_subn_rank: " - "Ranking Starts from guid 0x%" PRIx64 "\n", root_guid); + osm_log( p_log, OSM_LOG_VERBOSE, + "updn_subn_rank: " + "Ranking starts from GUID 0x%" PRIx64 "\n", root_guid ); /* Init the list pointers */ - p_nextList = (cl_list_t*)cl_malloc(sizeof(cl_list_t)); + p_nextList = (cl_list_t*)malloc(sizeof(cl_list_t)); cl_list_construct( p_nextList ); cl_list_init( p_nextList, 10 ); p_currList = p_nextList; /* Check valid subnet & guid */ - tbl_size = (uint16_t)(cl_qmap_count(&(osm.subn.port_guid_tbl))); + tbl_size = (uint16_t)(cl_qmap_count(&p_updn->p_osm->subn.port_guid_tbl)); if (tbl_size == 0) { - osm_log(&(osm.log), OSM_LOG_ERROR, - "updn_subn_rank: ERR AA04: " - "Port guid table is empty, cannot perform ranking\n"); - OSM_LOG_EXIT( &(osm.log)); + osm_log( p_log, OSM_LOG_ERROR, + "updn_subn_rank: ERR AA04: " + "Port guid table is empty, cannot perform ranking\n" ); + OSM_LOG_EXIT( p_log ); return 1; } - p_root_port = (osm_port_t*) cl_qmap_get(&(osm.subn.port_guid_tbl), \ + p_root_port = (osm_port_t*) cl_qmap_get(&p_updn->p_osm->subn.port_guid_tbl, cl_ntoh64(root_guid)); - if( p_root_port == (osm_port_t*)cl_qmap_end( &(osm.subn.port_guid_tbl) ) ) + if( p_root_port == (osm_port_t*)cl_qmap_end( &p_updn->p_osm->subn.port_guid_tbl ) ) { - - osm_log(&(osm.log), OSM_LOG_ERROR, - "updn_subn_rank: ERR AA05: " - "Wrong guid value: 0x%" PRIx64 "\n", root_guid); - OSM_LOG_EXIT( &(osm.log)); + osm_log( p_log, OSM_LOG_ERROR, + "updn_subn_rank: ERR AA05: " + "Wrong guid value: 0x%" PRIx64 "\n", root_guid ); + OSM_LOG_EXIT( p_log ); return 1; } /* Rank the first chosen guid anyway since its the base rank */ - osm_log(&(osm.log), OSM_LOG_DEBUG, - "updn_subn_rank: " - "Ranking port guid 0x%" PRIx64 "\n",root_guid); + osm_log( p_log, OSM_LOG_DEBUG, + "updn_subn_rank: " + "Ranking port GUID 0x%" PRIx64 "\n", root_guid ); __updn_update_rank(&p_updn->guid_rank_tbl, cl_ntoh64(root_guid), rank); /* @@ -680,14 +742,14 @@ updn_subn_rank( p_currList = p_nextList; /* BFS the list till its empty */ - osm_log(&(osm.log), OSM_LOG_VERBOSE, - "updn_subn_rank: " - "BFS the subnet [\n"); + osm_log( p_log, OSM_LOG_VERBOSE, + "updn_subn_rank: " + "BFS the subnet [\n" ); while (!cl_is_list_empty(p_currList)) { rank++; - p_nextList = (cl_list_t*)cl_malloc(sizeof(cl_list_t)); + p_nextList = (cl_list_t*)malloc(sizeof(cl_list_t)); cl_list_construct( p_nextList ); cl_list_init( p_nextList, 10 ); p_physp = (osm_physp_t*)cl_list_remove_head( p_currList ); @@ -696,9 +758,10 @@ updn_subn_rank( while ( p_physp != NULL ) { num_ports = osm_node_get_num_physp( p_physp->p_node ); - osm_log(&(osm.log), OSM_LOG_DEBUG, - "updn_subn_rank: " - "Handling port guid 0x%" PRIx64 "\n", cl_ntoh64(p_physp->port_guid)); + osm_log( p_log, OSM_LOG_DEBUG, + "updn_subn_rank: " + "Handling port GUID 0x%" PRIx64 "\n", + cl_ntoh64(p_physp->port_guid) ); for (port_num = 1; port_num < num_ports; port_num++) { ib_net64_t port_guid; @@ -708,7 +771,7 @@ updn_subn_rank( p_remote_physp = p_physp_temp->p_remote_physp; /* - make sure that all the following occure on p_remote_physp: + make sure that all the following occur on p_remote_physp: 1. The port isn't NULL 2. The port is a valid port */ @@ -716,23 +779,23 @@ updn_subn_rank( osm_physp_is_valid ( p_remote_physp )) { port_guid = p_remote_physp->port_guid; - osm_log(&(osm.log), OSM_LOG_DEBUG, - "updn_subn_rank: " - "Visiting remote port guid 0x%" PRIx64 "\n" - , cl_ntoh64(port_guid)); + osm_log( p_log, OSM_LOG_DEBUG, + "updn_subn_rank: " + "Visiting remote port GUID 0x%" PRIx64 "\n", + cl_ntoh64(port_guid) ); /* Was it visited ? Only if the pointer equal to cl_qmap_end its not found in the list */ - osm_log(&(osm.log), OSM_LOG_DEBUG, - "updn_subn_rank: " - "Ranking port guid 0x%" PRIx64 "\n", cl_ntoh64(port_guid)); + osm_log( p_log, OSM_LOG_DEBUG, + "updn_subn_rank: " + "Ranking port GUID 0x%" PRIx64 "\n", cl_ntoh64(port_guid) ); did_cause_update = __updn_update_rank(&p_updn->guid_rank_tbl, port_guid, rank); - osm_log(&(osm.log), OSM_LOG_VERBOSE, - "updn_subn_rank: " - "Rank of port guid 0x%" PRIx64 " = %u\n", cl_ntoh64(port_guid), - ((updn_rank_t*)cl_qmap_get(&p_updn->guid_rank_tbl, port_guid))->rank - ); + osm_log( p_log, OSM_LOG_VERBOSE, + "updn_subn_rank: " + "Rank of port GUID 0x%" PRIx64 " = %u\n", cl_ntoh64(port_guid), + ((updn_rank_t*)cl_qmap_get(&p_updn->guid_rank_tbl, port_guid))->rank + ); if (did_cause_update) { @@ -745,134 +808,130 @@ updn_subn_rank( } /* First free the allocation of cl_list pointer then reallocate */ cl_list_destroy( p_currList ); - cl_free(p_currList); + free(p_currList); /* p_currList is empty - need to assign it to p_nextList */ p_currList = p_nextList; } - osm_log(&(osm.log), OSM_LOG_VERBOSE, - "updn_subn_rank: " - "BFS the subnet ]\n"); + osm_log( p_log, OSM_LOG_VERBOSE, + "updn_subn_rank: " + "BFS the subnet ]\n" ); cl_list_destroy( p_currList ); - cl_free(p_currList); + free(p_currList); /* Print Summary of ranking */ - osm_log(&(osm.log), OSM_LOG_VERBOSE, - "updn_subn_rank: " - "Rank Info :\n\t Root Guid = 0x%" PRIx64 "\n\t Max Node Rank = %d\n" - , cl_ntoh64(p_root_port->guid),rank); + osm_log( p_log, OSM_LOG_VERBOSE, + "updn_subn_rank: " + "Rank Info :\n\t Root Guid = 0x%" PRIx64 "\n\t Max Node Rank = %d\n", + cl_ntoh64(p_root_port->guid), rank ); p_updn->state = UPDN_RANK; - OSM_LOG_EXIT( &(osm.log)); + OSM_LOG_EXIT( p_log ); return 0; } /********************************************************************** **********************************************************************/ -int -osm_subn_set_up_down_min_hop_table( - IN updn_t* p_updn) +static int +__osm_subn_set_up_down_min_hop_table( + IN updn_t* p_updn ) { /* Init local vars */ - osm_subn_t *p_subn = &(osm.subn); + osm_subn_t *p_subn = &p_updn->p_osm->subn; + osm_log_t *p_log = &p_updn->p_osm->log; osm_switch_t *p_next_sw,*p_sw; osm_port_t *p_next_port,*p_port; ib_net64_t port_guid; - OSM_LOG_ENTER( &(osm.log), osm_subn_set_up_down_min_hop_table ); + OSM_LOG_ENTER( p_log, __osm_subn_set_up_down_min_hop_table ); if (p_updn->state == UPDN_INIT) { - osm_log(&(osm.log), OSM_LOG_ERROR, - "osm_subn_set_up_down_min_hop_table: ERR AA06: " - "Calculating Min Hop only allowed after ranking\n"); - OSM_LOG_EXIT( &(osm.log) ); + osm_log( p_log, OSM_LOG_ERROR, + "__osm_subn_set_up_down_min_hop_table: ERR AA06: " + "Calculating Min Hop only allowed after ranking\n" ); + OSM_LOG_EXIT( p_log ); return 1; } /* Check if its a non switched subnet .. */ if ( cl_is_qmap_empty( &p_subn->sw_guid_tbl ) ) { - osm_log(&(osm.log), OSM_LOG_ERROR, - "osm_subn_set_up_down_min_hop_table: ERR AA10: " - "This is a non switched subnet, cannot perform UPDN algorithm\n"); - OSM_LOG_EXIT( &(osm.log)); + osm_log( p_log, OSM_LOG_ERROR, + "__osm_subn_set_up_down_min_hop_table: ERR AA10: " + "This is a non switched subnet, cannot perform UPDN algorithm\n" ); + OSM_LOG_EXIT( p_log ); return 1; } /* Go over all the switches in the subnet - for each init their Min Hop Table */ - osm_log(&(osm.log), OSM_LOG_VERBOSE, - "osm_subn_set_up_down_min_hop_table: " - "Init Min Hop Table of all switches [\n"); + osm_log( p_log, OSM_LOG_VERBOSE, + "__osm_subn_set_up_down_min_hop_table: " + "Init Min Hop Table of all switches [\n" ); p_next_sw = (osm_switch_t*)cl_qmap_head( &p_subn->sw_guid_tbl ); while( p_next_sw != (osm_switch_t*)cl_qmap_end( &p_subn->sw_guid_tbl ) ) { - uint16_t max_lid_ho, lid_ho; - p_sw = p_next_sw; p_next_sw = (osm_switch_t*)cl_qmap_next( &p_sw->map_item ); - /* Clear Min Hop Table && FWD Tbls - This should caused opensm to - rebuild its FWD tables , post setting Min Hop Tables */ + /* Clear Min Hop Table */ osm_lid_matrix_clear(&(p_sw->lmx)); - max_lid_ho = osm_switch_get_max_lid_ho(p_sw); - for (lid_ho = 1; lid_ho <= max_lid_ho; lid_ho++) - osm_switch_set_path(p_sw, lid_ho, OSM_NO_PATH,TRUE); } - osm_log(&(osm.log), OSM_LOG_VERBOSE, - "osm_subn_set_up_down_min_hop_table: " - "Init Min Hop Table of all switches ]\n"); + osm_log( p_log, OSM_LOG_VERBOSE, + "__osm_subn_set_up_down_min_hop_table: " + "Init Min Hop Table of all switches ]\n" ); /* Now do the BFS for each port in the subnet */ - osm_log(&(osm.log), OSM_LOG_VERBOSE, - "osm_subn_set_up_down_min_hop_table: " - "BFS through all port guids in the subnet [\n"); + osm_log( p_log, OSM_LOG_VERBOSE, + "__osm_subn_set_up_down_min_hop_table: " + "BFS through all port guids in the subnet [\n" ); p_next_port = (osm_port_t*)cl_qmap_head( &p_subn->port_guid_tbl ); while( p_next_port != (osm_port_t*)cl_qmap_end( &p_subn->port_guid_tbl ) ) { p_port = p_next_port; p_next_port = (osm_port_t*)cl_qmap_next( &p_port->map_item ); port_guid = cl_qmap_key(&(p_port->map_item)); - osm_log(&(osm.log), OSM_LOG_DEBUG, - "BFS through port guid 0x%" PRIx64 "\n" - , cl_ntoh64(port_guid)); - if(__updn_bfs_by_node(p_subn,port_guid, + osm_log( p_log, OSM_LOG_DEBUG, + "__osm_subn_set_up_down_min_hop_table: " + "BFS through port GUID 0x%" PRIx64 "\n", + cl_ntoh64(port_guid) ); + if(__updn_bfs_by_node(p_updn, p_subn, p_port, &p_updn->guid_rank_tbl)) { - OSM_LOG_EXIT( &(osm.log) ); + OSM_LOG_EXIT( p_log ); return 1; } } - osm_log(&(osm.log), OSM_LOG_INFO, - "osm_subn_set_up_down_min_hop_table: " - "BFS through all port guids in the subnet ]\n"); + osm_log( p_log, OSM_LOG_VERBOSE, + "__osm_subn_set_up_down_min_hop_table: " + "BFS through all port guids in the subnet ]\n" ); /* Cleanup */ - OSM_LOG_EXIT( &(osm.log) ); + OSM_LOG_EXIT( p_log ); return 0; } /********************************************************************** **********************************************************************/ -int -osm_subn_calc_up_down_min_hop_table( +static int +__osm_subn_calc_up_down_min_hop_table( IN uint32_t num_guids, IN uint64_t * guid_list, - IN updn_t* p_updn) + IN updn_t* p_updn ) { uint8_t idx = 0; cl_map_item_t *p_map_item; int status; - OSM_LOG_ENTER( &(osm.log), osm_subn_calc_up_down_min_hop_table ); - osm_log(&(osm.log), OSM_LOG_VERBOSE, - "osm_subn_calc_up_down_min_hop_table: " - "Ranking all port guids in the list\n"); + OSM_LOG_ENTER( &p_updn->p_osm->log, osm_subn_calc_up_down_min_hop_table ); + osm_log( &p_updn->p_osm->log, OSM_LOG_VERBOSE, + "__osm_subn_calc_up_down_min_hop_table: " + "Ranking all port guids in the list\n" ); if (num_guids == 0) { - osm_log(&(osm.log), OSM_LOG_ERROR, - "osm_subn_calc_up_down_min_hop_table: " - "No guids were given or number of guids is 0\n"); + osm_log( &p_updn->p_osm->log, OSM_LOG_ERROR, + "__osm_subn_calc_up_down_min_hop_table: ERR AA0A: " + "No guids were given or number of guids is 0\n" ); return 1; } @@ -882,134 +941,121 @@ osm_subn_calc_up_down_min_hop_table( updn_subn_rank(guid_list[idx], 0, p_updn); } /* After multiple ranking need to set Min Hop Table by UpDn algorithm */ - osm_log(&(osm.log), OSM_LOG_VERBOSE, - "osm_subn_calc_up_down_min_hop_table: " - "Setting all switches' Min Hop Table\n"); + osm_log( &p_updn->p_osm->log, OSM_LOG_VERBOSE, + "__osm_subn_calc_up_down_min_hop_table: " + "Setting all switches' Min Hop Table\n" ); - status = osm_subn_set_up_down_min_hop_table (p_updn); + status = __osm_subn_set_up_down_min_hop_table (p_updn); /* Cleanup updn rank tbl */ p_map_item = cl_qmap_head( &p_updn->guid_rank_tbl); while( p_map_item != cl_qmap_end( &p_updn->guid_rank_tbl)) { - osm_log (&(osm.log), OSM_LOG_DEBUG, - "osm_subn_calc_up_down_min_hop_table: " + osm_log( &p_updn->p_osm->log, OSM_LOG_DEBUG, + "__osm_subn_calc_up_down_min_hop_table: " "guid = 0x%" PRIx64 " rank = %u\n", - cl_ntoh64(cl_qmap_key(p_map_item)), ((updn_rank_t *)p_map_item)->rank); + cl_ntoh64(cl_qmap_key(p_map_item)), + ((updn_rank_t *)p_map_item)->rank ); cl_qmap_remove_item( &p_updn->guid_rank_tbl, p_map_item); - cl_free( (updn_rank_t *)p_map_item); + free( (updn_rank_t *)p_map_item); p_map_item = cl_qmap_head( &p_updn->guid_rank_tbl); } - OSM_LOG_EXIT( &(osm.log)); + OSM_LOG_EXIT( &p_updn->p_osm->log ); return status; - } /********************************************************************** **********************************************************************/ /* UPDN callback function */ -int __osm_updn_call(void *ctx) +static int +__osm_updn_call( + void *ctx ) { - OSM_LOG_ENTER(&(osm.log), __osm_updn_call); + updn_t *p_updn = ctx; + + OSM_LOG_ENTER( &p_updn->p_osm->log, __osm_updn_call ); + /* First auto detect root nodes - if required */ - if ( ((updn_t*)ctx)->auto_detect_root_nodes ) + if ( p_updn->auto_detect_root_nodes ) { - /* printf ("-V- b4 osm_updn_find_root_nodes_by_min_hop\n");*/ - osm_updn_find_root_nodes_by_min_hop( ((updn_t*)ctx) ); + osm_ucast_mgr_build_lid_matrices( &p_updn->p_osm->sm.ucast_mgr ); + /* printf ("-V- b4 osm_updn_find_root_nodes_by_min_hop\n"); */ + __osm_updn_find_root_nodes_by_min_hop( p_updn ); } - /* printf ("-V- after osm_updn_find_root_nodes_by_min_hop\n"); */ + /* printf ("-V- after osm_updn_find_root_nodes_by_min_hop\n"); */ /* Only if there are assigned root nodes do the algorithm , otherwise perform do nothing */ - if ( ((updn_t*)ctx)->updn_ucast_reg_inputs.num_guids > 0) + if ( p_updn->updn_ucast_reg_inputs.num_guids > 0) { - osm_log (&(osm.log), OSM_LOG_DEBUG, + osm_log( &(p_updn->p_osm->log), OSM_LOG_DEBUG, "__osm_updn_call: " - "activating UPDN algorithm\n"); - osm_subn_calc_up_down_min_hop_table( ((updn_t*)ctx)->updn_ucast_reg_inputs.num_guids, - ((updn_t*)ctx)->updn_ucast_reg_inputs.guid_list - , ((updn_t*)ctx) ); + "activating UPDN algorithm\n" ); + __osm_subn_calc_up_down_min_hop_table( p_updn->updn_ucast_reg_inputs.num_guids, + p_updn->updn_ucast_reg_inputs.guid_list, + p_updn ); } else - osm_log (&(osm.log), OSM_LOG_INFO, + osm_log( &p_updn->p_osm->log, OSM_LOG_INFO, "__osm_updn_call: " - "disable UPDN algorithm, no root nodes were found\n"); + "disable UPDN algorithm, no root nodes were found\n" ); - OSM_LOG_EXIT(&(osm.log)); + OSM_LOG_EXIT( &p_updn->p_osm->log ); return 0; } /********************************************************************** **********************************************************************/ /* UPDN convert cl_list to guid array in updn struct */ -void __osm_updn_convert_list2array(IN updn_t * p_updn) +static void +__osm_updn_convert_list2array( + IN updn_t * p_updn ) { uint32_t i = 0, max_num = 0; uint64_t *p_guid; - OSM_LOG_ENTER(&(osm.log), __osm_updn_convert_list2array); + OSM_LOG_ENTER( &p_updn->p_osm->log, __osm_updn_convert_list2array ); + p_updn->updn_ucast_reg_inputs.num_guids = cl_list_count( p_updn->p_root_nodes); if (p_updn->updn_ucast_reg_inputs.guid_list) - cl_free(p_updn->updn_ucast_reg_inputs.guid_list); - p_updn->updn_ucast_reg_inputs.guid_list = (uint64_t *)cl_zalloc( + free(p_updn->updn_ucast_reg_inputs.guid_list); + p_updn->updn_ucast_reg_inputs.guid_list = (uint64_t *)malloc( p_updn->updn_ucast_reg_inputs.num_guids*sizeof(uint64_t)); + if (p_updn->updn_ucast_reg_inputs.guid_list) + memset(p_updn->updn_ucast_reg_inputs.guid_list, 0, + p_updn->updn_ucast_reg_inputs.num_guids*sizeof(uint64_t)); if (!cl_is_list_empty(p_updn->p_root_nodes)) { while( (p_guid = (uint64_t*)cl_list_remove_head(p_updn->p_root_nodes)) ) { p_updn->updn_ucast_reg_inputs.guid_list[i] = *p_guid; - cl_free(p_guid); + free(p_guid); i++; } max_num = i; for (i = 0; i < max_num; i++ ) - osm_log (&(osm.log), OSM_LOG_DEBUG, + osm_log( &p_updn->p_osm->log, OSM_LOG_DEBUG, "__osm_updn_convert_list2array: " - "Map guid 0x%" PRIx64 " into UPDN array\n", - p_updn->updn_ucast_reg_inputs.guid_list[i]); + "Map GUID 0x%" PRIx64 " into UPDN array\n", + p_updn->updn_ucast_reg_inputs.guid_list[i] ); } /* Since we need the template list for other sweeps, we wont destroy & free it */ - OSM_LOG_EXIT(&(osm.log)); -} - -/********************************************************************** - **********************************************************************/ -/* Registration function to ucast routing manager (instead of - Min Hop Algorithm) */ -int -osm_updn_reg_calc_min_hop_table( - IN updn_t * p_updn, - IN osm_subn_opt_t* p_opt ) -{ - OSM_LOG_ENTER(&(osm.log), osm_updn_reg_calc_min_hop_table); - /* - If root nodes were supplied by the user - we need to convert into array - otherwise, will be created & converted in callback function activation - */ - if (!p_updn->auto_detect_root_nodes) - { - __osm_updn_convert_list2array(p_updn); - } - osm_log (&(osm.log), OSM_LOG_DEBUG, - "osm_updn_reg_calc_min_hop_table: " - "assigning ucast fdb UI function with updn callback\n"); - p_opt->pfn_ui_ucast_fdb_assign = __osm_updn_call; - p_opt->ui_ucast_fdb_assign_ctx = (void *)p_updn; - OSM_LOG_EXIT(&(osm.log)); - return 0; + OSM_LOG_EXIT( &p_updn->p_osm->log ); } /********************************************************************** **********************************************************************/ /* Find Root nodes automatically by Min Hop Table info */ -int -osm_updn_find_root_nodes_by_min_hop( OUT updn_t * p_updn ) +static int +__osm_updn_find_root_nodes_by_min_hop( + OUT updn_t * p_updn ) { + osm_opensm_t *p_osm = p_updn->p_osm; osm_switch_t *p_next_sw, *p_sw; osm_port_t *p_next_port, *p_port; osm_physp_t *p_physp; uint32_t numCas = 0; - uint32_t numSws = cl_qmap_count(&osm.subn.sw_guid_tbl); + uint32_t numSws = cl_qmap_count(&p_osm->subn.sw_guid_tbl); cl_qmap_t min_hop_hist; /* Histogram container */ updn_hist_t *p_updn_hist, *p_up_ht; uint8_t maxHops = 0; /* contain the max histogram index */ @@ -1018,55 +1064,56 @@ osm_updn_find_root_nodes_by_min_hop( OUT updn_t * p_updn ) cl_map_t ca_by_lid_map; /* map holding all CA lids */ uint16_t self_lid_ho; - OSM_LOG_ENTER(&(osm.log), osm_updn_find_root_nodes_by_min_hop); - osm_log (&(osm.log), OSM_LOG_DEBUG, - "osm_updn_find_root_nodes_by_min_hop: " + OSM_LOG_ENTER( &p_osm->log, osm_updn_find_root_nodes_by_min_hop ); + + osm_log( &p_osm->log, OSM_LOG_DEBUG, + "__osm_updn_find_root_nodes_by_min_hop: " "current number of ports in the subnet is %d\n", - cl_qmap_count(&osm.subn.port_guid_tbl)); + cl_qmap_count(&p_osm->subn.port_guid_tbl) ); /* Init the required vars */ cl_qmap_init( &min_hop_hist ); cl_map_construct( &ca_by_lid_map ); cl_map_init( &ca_by_lid_map, 10 ); /* EZ: - p_ca_list = (cl_list_t*)cl_malloc(sizeof(cl_list_t)); + p_ca_list = (cl_list_t*)malloc(sizeof(cl_list_t)); cl_list_construct( p_ca_list ); cl_list_init( p_ca_list, 10 ); */ - /* Find the Maximum number of Cas for `histogram normalization */ - osm_log (&(osm.log), OSM_LOG_VERBOSE, - "osm_updn_find_root_nodes_by_min_hop: " - "Find the number of CA and store them in cl_list\n"); - p_next_port = (osm_port_t*)cl_qmap_head( &osm.subn.port_guid_tbl ); - while( p_next_port != (osm_port_t*)cl_qmap_end( &osm.subn.port_guid_tbl ) ) { + /* Find the Maximum number of CAs (and routers) for histogram normalization */ + osm_log( &p_osm->log, OSM_LOG_VERBOSE, + "__osm_updn_find_root_nodes_by_min_hop: " + "Find the number of CAs and store them in cl_list\n" ); + p_next_port = (osm_port_t*)cl_qmap_head( &p_osm->subn.port_guid_tbl ); + while( p_next_port != (osm_port_t*)cl_qmap_end( &p_osm->subn.port_guid_tbl ) ) { p_port = p_next_port; p_next_port = (osm_port_t*)cl_qmap_next( &p_next_port->map_item ); - if ( osm_node_get_type(p_port->p_node) == IB_NODE_TYPE_CA ) + if ( osm_node_get_type(p_port->p_node) != IB_NODE_TYPE_SWITCH ) { p_physp = osm_port_get_default_phys_ptr(p_port); self_lid_ho = cl_ntoh16( osm_physp_get_base_lid(p_physp) ); numCas++; /* EZ: - self = cl_malloc(sizeof(uint16_t)); + self = malloc(sizeof(uint16_t)); *self = self_lid_ho; cl_list_insert_tail(p_ca_list, self); */ cl_map_insert( &ca_by_lid_map, self_lid_ho, (void *)0x1); - osm_log (&(osm.log), OSM_LOG_DEBUG, - "osm_updn_find_root_nodes_by_min_hop: " - "Inserting into array guid 0x%" PRIx64 ", Lid: 0x%x\n", - cl_ntoh64(osm_port_get_guid(p_port)), self_lid_ho); + osm_log( &p_osm->log, OSM_LOG_DEBUG, + "__osm_updn_find_root_nodes_by_min_hop: " + "Inserting into array GUID 0x%" PRIx64 ", Lid: 0x%X\n", + cl_ntoh64(osm_port_get_guid(p_port)), self_lid_ho ); } } - osm_log (&(osm.log), OSM_LOG_DEBUG, - "osm_updn_find_root_nodes_by_min_hop: " - "Found %u CA, %u SW in the subnet\n", numCas, numSws); - p_next_sw = (osm_switch_t*)cl_qmap_head( &osm.subn.sw_guid_tbl ); - osm_log (&(osm.log), OSM_LOG_VERBOSE, - "osm_updn_find_root_nodes_by_min_hop: " - "Passing through all switches to collect Min Hop info\n"); - while( p_next_sw != (osm_switch_t*)cl_qmap_end( &osm.subn.sw_guid_tbl ) ) + osm_log( &p_osm->log, OSM_LOG_DEBUG, + "__osm_updn_find_root_nodes_by_min_hop: " + "Found %u CA, %u SW in the subnet\n", numCas, numSws ); + p_next_sw = (osm_switch_t*)cl_qmap_head( &p_osm->subn.sw_guid_tbl ); + osm_log( &p_osm->log, OSM_LOG_VERBOSE, + "__osm_updn_find_root_nodes_by_min_hop: " + "Passing through all switches to collect Min Hop info\n" ); + while( p_next_sw != (osm_switch_t*)cl_qmap_end( &p_osm->subn.sw_guid_tbl ) ) { uint16_t max_lid_ho, lid_ho; uint8_t hop_val; @@ -1083,9 +1130,9 @@ osm_updn_find_root_nodes_by_min_hop( OUT updn_t * p_updn ) max_lid_ho = osm_switch_get_max_lid_ho(p_sw); /* Get base lid of switch by retrieving port 0 lid of node pointer */ self_lid_ho = cl_ntoh16( osm_node_get_base_lid( p_sw->p_node, 0 ) ); - osm_log (&(osm.log), OSM_LOG_DEBUG, - "osm_updn_find_root_nodes_by_min_hop: " - "Passing through switch lid 0x%x\n", self_lid_ho); + osm_log( &p_osm->log, OSM_LOG_DEBUG, + "__osm_updn_find_root_nodes_by_min_hop: " + "Passing through switch lid 0x%X\n", self_lid_ho ); for (lid_ho = 1; lid_ho <= max_lid_ho; lid_ho++) { /* Skip lids which are not CAs - @@ -1116,23 +1163,23 @@ osm_updn_find_root_nodes_by_min_hop( OUT updn_t * p_updn ) if ( p_updn_hist == (updn_hist_t*)cl_qmap_end( &min_hop_hist)) { /* New entry in the histogram , first create it */ - p_updn_hist = (updn_hist_t*) cl_malloc(sizeof(updn_hist_t)); + p_updn_hist = (updn_hist_t*) malloc(sizeof(updn_hist_t)); CL_ASSERT (p_updn_hist); p_updn_hist->bar_value = 1; cl_qmap_insert(&min_hop_hist, (uint64_t)hop_val, &p_updn_hist->map_item); - osm_log (&(osm.log), OSM_LOG_DEBUG, - "osm_updn_find_root_nodes_by_min_hop: " + osm_log( &p_osm->log, OSM_LOG_DEBUG, + "__osm_updn_find_root_nodes_by_min_hop: " "Creating new entry in histogram %u with bar value 1\n", - hop_val); + hop_val ); } else { /* Entry exist in the table , just increment the value */ p_updn_hist->bar_value++; - osm_log (&(osm.log), OSM_LOG_DEBUG, - "osm_updn_find_root_nodes_by_min_hop: " - "Updating entry in histogram %u with bar value %d\n", hop_val, - p_updn_hist->bar_value); + osm_log( &p_osm->log, OSM_LOG_DEBUG, + "__osm_updn_find_root_nodes_by_min_hop: " + "Updating entry in histogram %u with bar value %d\n", + hop_val, p_updn_hist->bar_value ); } } } @@ -1141,10 +1188,10 @@ osm_updn_find_root_nodes_by_min_hop( OUT updn_t * p_updn ) number of CAs */ thd1 = numCas * 0.9; thd2 = numCas * 0.05; - osm_log (&(osm.log), OSM_LOG_DEBUG, - "osm_updn_find_root_nodes_by_min_hop: " + osm_log( &p_osm->log, OSM_LOG_DEBUG, + "__osm_updn_find_root_nodes_by_min_hop: " "Pass over the histogram value and find only one root node above " - "thd1 = %f && thd2 = %f\n", thd1, thd2); + "thd1 = %f && thd2 = %f\n", thd1, thd2 ); p_updn_hist = (updn_hist_t*) cl_qmap_head( &min_hop_hist ); while( p_updn_hist != (updn_hist_t*)cl_qmap_end( &min_hop_hist ) ) @@ -1155,36 +1202,36 @@ osm_updn_find_root_nodes_by_min_hop( OUT updn_t * p_updn ) numHopBarsOverThd1++; if ( p_up_ht->bar_value > thd2 ) numHopBarsOverThd2++; - osm_log (&(osm.log), OSM_LOG_DEBUG, - "osm_updn_find_root_nodes_by_min_hop: " + osm_log( &p_osm->log, OSM_LOG_DEBUG, + "__osm_updn_find_root_nodes_by_min_hop: " "Passing through histogram - Hop Index %u: " "numHopBarsOverThd1 = %u, numHopBarsOverThd2 = %u\n", - (uint16_t)cl_qmap_key((cl_map_item_t*)p_up_ht), numHopBarsOverThd1 , - numHopBarsOverThd2); + (uint16_t)cl_qmap_key((cl_map_item_t*)p_up_ht), + numHopBarsOverThd1, numHopBarsOverThd2 ); } /* destroy the qmap table and all its content - no longer needed */ - osm_log (&(osm.log), OSM_LOG_DEBUG, - "osm_updn_find_root_nodes_by_min_hop: " + osm_log( &p_osm->log, OSM_LOG_DEBUG, + "__osm_updn_find_root_nodes_by_min_hop: " "Cleanup: delete histogram " - "UPDN - Root nodes fetching by auto detect\n"); + "UPDN - Root nodes fetching by auto detect\n" ); p_updn_hist = (updn_hist_t*) cl_qmap_head( &min_hop_hist ); while ( p_updn_hist != (updn_hist_t*)cl_qmap_end( &min_hop_hist ) ) { cl_qmap_remove_item( &min_hop_hist, (cl_map_item_t*)p_updn_hist ); - cl_free( p_updn_hist ); + free( p_updn_hist ); p_updn_hist = (updn_hist_t*) cl_qmap_head( &min_hop_hist ); } /* If thd conditions are valid insert the root node to the list */ if ( (numHopBarsOverThd1 == 1) && (numHopBarsOverThd2 == 1) ) { - p_guid = cl_malloc(sizeof(uint64_t)); + p_guid = malloc(sizeof(uint64_t)); *p_guid = cl_ntoh64(osm_node_get_node_guid(p_sw->p_node)); - osm_log (&(osm.log), OSM_LOG_DEBUG, - "osm_updn_find_root_nodes_by_min_hop: " - "Inserting guid 0x%" PRIx64 " as root node\n", - *p_guid); + osm_log( &p_osm->log, OSM_LOG_DEBUG, + "__osm_updn_find_root_nodes_by_min_hop: " + "Inserting GUID 0x%" PRIx64 " as root node\n", + *p_guid ); cl_list_insert_tail(p_root_nodes_list, p_guid); } } @@ -1196,6 +1243,39 @@ osm_updn_find_root_nodes_by_min_hop( OUT updn_t * p_updn ) /* Now convert the cl_list to array */ __osm_updn_convert_list2array(p_updn); - OSM_LOG_EXIT(&(osm.log)); + OSM_LOG_EXIT( &p_osm->log ); return 0; } + +/********************************************************************** + **********************************************************************/ +static void +__osm_updn_delete( + void *context ) +{ + updn_t *p_updn = context; + + updn_destroy(p_updn); +} + +int +osm_ucast_updn_setup( + osm_opensm_t *p_osm ) +{ + updn_t *p_updn; + + p_updn = updn_construct(&p_osm->log); + if (!p_updn) + return -1; + p_osm->routing_engine.context = p_updn; + p_osm->routing_engine.delete = __osm_updn_delete; + p_osm->routing_engine.build_lid_matrices = __osm_updn_call; + + if (updn_init(p_updn, p_osm) != IB_SUCCESS) + return -1; + if (!p_updn->auto_detect_root_nodes) + __osm_updn_convert_list2array(p_updn); + + return 0; +} + diff --git a/trunk/ulp/opensm/user/opensm/osm_vl15intf.c b/trunk/ulp/opensm/user/opensm/osm_vl15intf.c index 12e70081..7548789a 100644 --- a/trunk/ulp/opensm/user/opensm/osm_vl15intf.c +++ b/trunk/ulp/opensm/user/opensm/osm_vl15intf.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Implementation of osm_vl15_t. @@ -44,16 +45,12 @@ * $Revision: 1.6 $ */ -/* - Next available error code: 0x403 -*/ - #if HAVE_CONFIG_H # include #endif /* HAVE_CONFIG_H */ +#include #include -#include #include #include #include @@ -279,7 +276,7 @@ void osm_vl15_construct( IN osm_vl15_t* const p_vl ) { - cl_memclr( p_vl, sizeof(*p_vl) ); + memset( p_vl, 0, sizeof(*p_vl) ); p_vl->state = OSM_VL15_STATE_INIT; p_vl->thread_state = OSM_THREAD_STATE_NONE; cl_event_construct( &p_vl->signal ); @@ -544,3 +541,4 @@ osm_vl15_shutdown( OSM_LOG_EXIT( p_vl->p_log ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_vl_arb_rcv.c b/trunk/ulp/opensm/user/opensm/osm_vl_arb_rcv.c index d93b74e3..2bb9690f 100644 --- a/trunk/ulp/opensm/user/opensm/osm_vl_arb_rcv.c +++ b/trunk/ulp/opensm/user/opensm/osm_vl_arb_rcv.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Implementation of osm_vla_rcv_t. @@ -48,8 +49,8 @@ # include #endif /* HAVE_CONFIG_H */ +#include #include -#include #include #include #include @@ -71,7 +72,7 @@ void osm_vla_rcv_construct( IN osm_vla_rcv_t* const p_rcv ) { - cl_memclr( p_rcv, sizeof(*p_rcv) ); + memset( p_rcv, 0, sizeof(*p_rcv) ); } /********************************************************************** @@ -153,14 +154,14 @@ osm_vla_rcv_process( cl_plock_excl_acquire( p_rcv->p_lock ); p_port = (osm_port_t*)cl_qmap_get( p_guid_tbl, port_guid ); - if( p_port == (osm_port_t*)cl_qmap_end( p_guid_tbl) ) + if( p_port == (osm_port_t*)cl_qmap_end( p_guid_tbl ) ) { cl_plock_release( p_rcv->p_lock ); osm_log( p_rcv->p_log, OSM_LOG_ERROR, "osm_vla_rcv_process: ERR 3F06: " - "No Port object for port with GUID = 0x%" PRIx64 - "\n\t\t\t\tfor parent node GUID = 0x%" PRIx64 - ", TID = 0x%" PRIx64 "\n", + "No port object for port with GUID 0x%" PRIx64 + "\n\t\t\t\tfor parent node GUID 0x%" PRIx64 + ", TID 0x%" PRIx64 "\n", cl_ntoh64( port_guid ), cl_ntoh64( node_guid ), cl_ntoh64( p_smp->trans_id ) ); @@ -172,7 +173,7 @@ osm_vla_rcv_process( block_num = (uint8_t)(cl_ntoh32(p_smp->attr_mod) >> 16); /* in case of a non switch node the attr modifier should be ignored */ - if (osm_node_get_type( p_node ) == IB_NODE_TYPE_SWITCH) + if (osm_node_get_type( p_node ) == IB_NODE_TYPE_SWITCH) { port_num = (uint8_t)(cl_ntoh32(p_smp->attr_mod) & 0x000000FF); p_physp = osm_node_get_physp_ptr( p_node, port_num ); @@ -193,9 +194,9 @@ osm_vla_rcv_process( { osm_log( p_rcv->p_log, OSM_LOG_VERBOSE, "osm_vla_rcv_process: " - "Got GetResp(VLArb) block:%u port_num %u with GUID = 0x%" PRIx64 - " for parent node GUID = 0x%" PRIx64 - ", TID = 0x%" PRIx64 "\n", + "Got GetResp(VLArb) block:%u port_num %u with GUID 0x%" PRIx64 + " for parent node GUID 0x%" PRIx64 + ", TID 0x%" PRIx64 "\n", block_num, port_num, cl_ntoh64( port_guid ), cl_ntoh64( node_guid ), @@ -208,13 +209,10 @@ osm_vla_rcv_process( */ if( !osm_physp_is_valid( p_physp ) ) { - if( osm_log_is_active( p_rcv->p_log, OSM_LOG_VERBOSE ) ) - { - osm_log( p_rcv->p_log, OSM_LOG_ERROR, - "osm_vla_rcv_process: " - "Got invalid port number 0x%X\n", - port_num ); - } + osm_log( p_rcv->p_log, OSM_LOG_ERROR, + "osm_vla_rcv_process: " + "Got invalid port number 0x%X\n", + port_num ); goto Exit; } @@ -239,3 +237,4 @@ osm_vla_rcv_process( OSM_LOG_EXIT( p_rcv->p_log ); } + diff --git a/trunk/ulp/opensm/user/opensm/osm_vl_arb_rcv_ctrl.c b/trunk/ulp/opensm/user/opensm/osm_vl_arb_rcv_ctrl.c index c78b6eee..8dde5a87 100644 --- a/trunk/ulp/opensm/user/opensm/osm_vl_arb_rcv_ctrl.c +++ b/trunk/ulp/opensm/user/opensm/osm_vl_arb_rcv_ctrl.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* * Abstract: * Implementation of osm_vla_rcv_ctrl_t. @@ -44,15 +45,11 @@ * $Revision: 1.4 $ */ -/* - Next available error code: 0x203 -*/ - #if HAVE_CONFIG_H # include #endif /* HAVE_CONFIG_H */ -#include +#include #include #include @@ -74,7 +71,7 @@ void osm_vla_rcv_ctrl_construct( IN osm_vla_rcv_ctrl_t* const p_ctrl ) { - cl_memclr( p_ctrl, sizeof(*p_ctrl) ); + memset( p_ctrl, 0, sizeof(*p_ctrl) ); p_ctrl->h_disp = CL_DISP_INVALID_HANDLE; } @@ -127,3 +124,4 @@ osm_vla_rcv_ctrl_init( return( status ); } + diff --git a/trunk/ulp/opensm/user/opensm/st.c b/trunk/ulp/opensm/user/opensm/st.c index de8b8bd4..c6d1d998 100644 --- a/trunk/ulp/opensm/user/opensm/st.c +++ b/trunk/ulp/opensm/user/opensm/st.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -32,6 +32,7 @@ */ + /* static char sccsid[] = "@(#) st.c 5.1 89/12/14 Crucible"; */ #if HAVE_CONFIG_H @@ -181,7 +182,7 @@ static int init_st = 0; static void stat_col() { - FILE *f = fopen("/tmp/col", "w"); + FILE *f = fopen("/var/log/osm_st_col", "w"); fprintf(f, "collision: %d\n", collision); fclose(f); } @@ -303,7 +304,8 @@ st_lookup(table, key, value) { return 0; } - else { + else + { if (value != 0) *value = ptr->record; return 1; @@ -347,7 +349,8 @@ st_insert(table, key, value) ADD_DIRECT(table, key, value, hash_val, bin_pos); return 0; } - else { + else + { ptr->record = value; return 1; } @@ -559,7 +562,8 @@ st_foreach(table, func, arg) { table->bins[i] = ptr->next; } - else { + else + { last->next = ptr->next; } ptr = ptr->next; @@ -618,3 +622,4 @@ numhash(n) { return (st_ptr_t)n; } + diff --git a/trunk/ulp/opensm/user/osmtest/SOURCES b/trunk/ulp/opensm/user/osmtest/SOURCES index ebd11c57..0fe94590 100644 --- a/trunk/ulp/opensm/user/osmtest/SOURCES +++ b/trunk/ulp/opensm/user/osmtest/SOURCES @@ -62,6 +62,7 @@ INCLUDES= \ USER_C_FLAGS=$(USER_C_FLAGS) /MD #Add preproccessor definitions C_DEFINES=$(C_DEFINES) -DWIN32 -D__WIN__ -D__i386__ -Dinline=__inline -DMT_LITTLE_ENDIAN -DOSM_VENDOR_INTF_AL +C_DEFINES=$(C_DEFINES) -I.. -DHAVE_CONFIG_H !if !$(FREEBUILD) #C_DEFINES=$(C_DEFINES) -D_DEBUG -DDEBUG -DDBG C_DEFINES=$(C_DEFINES) diff --git a/trunk/ulp/opensm/user/osmtest/include/error.h b/trunk/ulp/opensm/user/osmtest/include/error.h index b2760c8c..ef80b337 100644 --- a/trunk/ulp/opensm/user/osmtest/include/error.h +++ b/trunk/ulp/opensm/user/osmtest/include/error.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -31,6 +31,7 @@ * $Id$ */ + /* * Abstract: * Declaration of error code ranges for the various osmtest modules. @@ -53,3 +54,4 @@ 0x0300 - 0x03FF */ + diff --git a/trunk/ulp/opensm/user/osmtest/include/osmt_inform.h b/trunk/ulp/opensm/user/osmtest/include/osmt_inform.h index 22b369a8..f0262541 100644 --- a/trunk/ulp/opensm/user/osmtest/include/osmt_inform.h +++ b/trunk/ulp/opensm/user/osmtest/include/osmt_inform.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -31,6 +31,7 @@ * $Id$ */ + #ifndef __OSMT_INFORM__ #define __OSMT_INFORM__ @@ -84,3 +85,4 @@ osmt_init_inform_info_by_trap (IN osmtest_t * const p_osmt, OUT ib_inform_info_t* p_ii); #endif /* __OSMT_INFORM__ */ + diff --git a/trunk/ulp/opensm/user/osmtest/include/osmt_mtl_regular_qp.h b/trunk/ulp/opensm/user/osmtest/include/osmt_mtl_regular_qp.h index b22acc4a..0466b76c 100644 --- a/trunk/ulp/opensm/user/osmtest/include/osmt_mtl_regular_qp.h +++ b/trunk/ulp/opensm/user/osmtest/include/osmt_mtl_regular_qp.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -31,6 +31,7 @@ * $Id$ */ + /* * mad.h - * Header file for common special QP resources creation code. @@ -183,3 +184,4 @@ VAPI_ret_t osmt_mtl_mad_poll4cqe( #endif + diff --git a/trunk/ulp/opensm/user/osmtest/include/osmtest.h b/trunk/ulp/opensm/user/osmtest/include/osmtest.h index 42197499..58feec98 100644 --- a/trunk/ulp/opensm/user/osmtest/include/osmtest.h +++ b/trunk/ulp/opensm/user/osmtest/include/osmtest.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -31,6 +31,7 @@ * $Id$ */ + /* * Abstract: * Declaration of osmtest_t. @@ -77,8 +78,7 @@ typedef struct _osmtest_opt uint8_t wait_time; char *log_file; boolean_t ignore_path_records; -} -osmtest_opt_t; +} osmtest_opt_t; /* * FIELDS @@ -445,7 +445,6 @@ osmt_run_slvl_and_vlarb_records_flow( IN osmtest_t * const p_osmt ); * SEE ALSO *********/ - /****f* OSMTest/osmt_run_mcast_flow * NAME * osmt_run_mcast_flow @@ -456,7 +455,7 @@ osmt_run_slvl_and_vlarb_records_flow( IN osmtest_t * const p_osmt ); * SYNOPSIS */ ib_api_status_t - osmt_run_mcast_flow( IN osmtest_t * const p_osmt ); +osmt_run_mcast_flow( IN osmtest_t * const p_osmt ); /* * PARAMETERS * p_osmt @@ -500,4 +499,19 @@ osmtest_get_all_recs( IN osmtest_t * const p_osmt, IN ib_net16_t const attr_id, IN size_t const attr_size, IN OUT osmtest_req_context_t * const p_context ); + +ib_api_status_t +osmtest_get_local_port_lmc( IN osmtest_t * const p_osmt, + IN ib_net16_t lid, + OUT uint8_t * const p_lmc ); + + +/* + * A few auxiliary macros for logging + */ + +#define EXPECTING_ERRORS_START "[[ ===== Expecting Errors - START ===== " +#define EXPECTING_ERRORS_END " ===== Expecting Errors - END ===== ]]" + #endif /* _OSMTEST_H_ */ + diff --git a/trunk/ulp/opensm/user/osmtest/include/osmtest_base.h b/trunk/ulp/opensm/user/osmtest/include/osmtest_base.h index 914896ec..f3716d3d 100644 --- a/trunk/ulp/opensm/user/osmtest/include/osmtest_base.h +++ b/trunk/ulp/opensm/user/osmtest/include/osmtest_base.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -31,6 +31,7 @@ * $Id$ */ + /* * Abstract: * Declaration of osmtest_t. @@ -68,3 +69,4 @@ extern const char *const p_file; #endif /* _OSMTEST_BASE_H_ */ + diff --git a/trunk/ulp/opensm/user/osmtest/include/osmtest_subnet.h b/trunk/ulp/opensm/user/osmtest/include/osmtest_subnet.h index 5dcc5d3b..418dd366 100644 --- a/trunk/ulp/opensm/user/osmtest/include/osmtest_subnet.h +++ b/trunk/ulp/opensm/user/osmtest/include/osmtest_subnet.h @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -31,6 +31,7 @@ * $Id$ */ + /* * Abstract: * Declaration of osmtest_t. @@ -45,6 +46,7 @@ #ifndef _OSMTEST_SUBNET_H_ #define _OSMTEST_SUBNET_H_ +#include #include #include #include @@ -66,9 +68,7 @@ typedef struct _generic { cl_map_item_t map_item; /* must be first element! */ uint32_t count; /* must be second element! */ - -} -generic_t; +} generic_t; /* * FIELDS @@ -92,9 +92,7 @@ typedef struct _node uint32_t count; /* must be second element! */ ib_node_record_t rec; ib_node_record_t comp; - -} -node_t; +} node_t; /* * FIELDS @@ -122,14 +120,16 @@ node_new( void ) { node_t *p_obj; - p_obj = cl_zalloc( sizeof( *p_obj ) ); + p_obj = malloc( sizeof( *p_obj ) ); + if (p_obj) + memset( p_obj, 0, sizeof( *p_obj ) ); return ( p_obj ); } static inline void node_delete( IN node_t * p_obj ) { - cl_free( p_obj ); + free( p_obj ); } /****s* Subnet Database/port_t @@ -146,13 +146,12 @@ typedef struct _port { cl_map_item_t map_item; /* must be first element! */ uint32_t count; /* must be second element! */ - /* Since there is no uniq identifier for all ports we + /* Since there is no unique identifier for all ports we must be able to have such a key by the lid and port num */ uint64_t port_id; ib_portinfo_record_t rec; ib_portinfo_record_t comp; -} -port_t; +} port_t; /* * FIELDS @@ -181,17 +180,18 @@ port_new( void ) { port_t *p_obj; - p_obj = cl_zalloc( sizeof( *p_obj ) ); + p_obj = malloc( sizeof( *p_obj ) ); + if (p_obj) + memset( p_obj, 0, sizeof( *p_obj ) ); return ( p_obj ); } static inline void port_delete( IN port_t * p_obj ) { - cl_free( p_obj ); + free( p_obj ); } - static inline uint64_t port_gen_id( IN ib_net16_t const lid, @@ -243,9 +243,7 @@ typedef struct _path uint32_t count; /* must be second element! */ ib_path_rec_t rec; ib_path_rec_t comp; - -} -path_t; +} path_t; /* * FIELDS @@ -273,14 +271,16 @@ path_new( void ) { path_t *p_obj; - p_obj = cl_zalloc( sizeof( *p_obj ) ); + p_obj = malloc( sizeof( *p_obj ) ); + if (p_obj) + memset( p_obj, 0, sizeof( *p_obj ) ); return ( p_obj ); } static inline void path_delete( IN path_t * p_obj ) { - cl_free( p_obj ); + free( p_obj ); } /****s* Subnet Database/subnet_t @@ -302,9 +302,7 @@ typedef struct _subnet cl_qmap_t port_key_tbl; cl_qmap_t link_tbl; cl_qmap_t path_tbl; - -} -subnet_t; +} subnet_t; /* * FIELDS @@ -312,9 +310,9 @@ subnet_t; * SEE ALSO *********/ -/****f* Subnet Database/subnet_init +/****f* Subnet Database/subnet_construct * NAME -* subnet_init +* subnet_construct * * DESCRIPTION * This function constructs an subnet database object. @@ -348,3 +346,4 @@ cl_status_t subnet_init( IN subnet_t * const p_subn ); *********/ #endif + diff --git a/trunk/ulp/opensm/user/osmtest/osmt_inform.c b/trunk/ulp/opensm/user/osmtest/osmt_inform.c index e03c4305..94c74df4 100644 --- a/trunk/ulp/opensm/user/osmtest/osmt_inform.c +++ b/trunk/ulp/opensm/user/osmtest/osmt_inform.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -31,6 +31,7 @@ * $Id$ */ + #ifdef OSM_VENDOR_INTF_MTL /* * Abstract: @@ -46,21 +47,17 @@ * $Revision: 1.2 $ */ -/* next error code: 16A */ - #include #include #include #include #include -#include - #include #include "osmtest.h" #include "osmt_inform.h" /* - * Prepare an a synchronous QP (rcv) for sending inform info and + * Prepare an asynchronous QP (rcv) for sending inform info and * handling the incoming reports. * */ @@ -83,12 +80,12 @@ osmt_bind_inform_qp( IN osmtest_t * const p_osmt, osm_log( p_log, OSM_LOG_DEBUG, "osmt_bind_inform_qp: " - "Binding to port 0x%" PRIx64 ".\n", cl_ntoh64( port_guid ) ); + "Binding to port 0x%" PRIx64 "\n", cl_ntoh64( port_guid ) ); /* obtain the hca name and port num from the guid */ osm_log( p_log, OSM_LOG_DEBUG, "osmt_bind_inform_qp: " - "Finding CA and Port that owns port guid 0x%" PRIx64 ".\n", + "Finding CA and Port that owns port guid 0x%" PRIx64 "\n", port_guid ); mgt_ret = @@ -104,6 +101,7 @@ osmt_bind_inform_qp( IN osmtest_t * const p_osmt, osm_log( p_log, OSM_LOG_ERROR, "osmt_bind_inform_qp: ERR 0109: " "Unable to obtain CA and port (%d).\n" ); + status = IB_ERROR; goto Exit; } @@ -134,7 +132,7 @@ osmt_bind_inform_qp( IN osmtest_t * const p_osmt, p_qp_ctx->p_recv_buf = (uint8_t *)p_qp_ctx->qp_bind_hndl.buf_ptr + 2 * (GRH_LEN + MAD_BLOCK_SIZE); /* Need to clear assigned memory of p_send_buf - before using it to send any data */ - cl_memclr(p_qp_ctx->p_send_buf, MAD_BLOCK_SIZE); + memset(p_qp_ctx->p_send_buf, 0, MAD_BLOCK_SIZE); status = IB_SUCCESS; osm_log( p_log, OSM_LOG_DEBUG, @@ -153,7 +151,7 @@ osmt_bind_inform_qp( IN osmtest_t * const p_osmt, { osm_log( p_log, OSM_LOG_ERROR, "osmt_bind_inform_qp: ERR 0115: " - "Error obtaining IB_MGT handle to SMI.\n" ); + "Error obtaining IB_MGT handle to SMI\n" ); status = IB_ERROR; goto Exit; } @@ -179,7 +177,7 @@ osmt_unbind_inform_qp( IN osmtest_t * const p_osmt, osm_log( p_log, OSM_LOG_DEBUG, "osmt_unbind_inform_qp: " - "Unbind QP handles.\n" ); + "Unbind QP handles\n" ); OSM_LOG_EXIT( &p_osmt->log ); } @@ -220,20 +218,20 @@ osmt_reg_unreg_inform_info( IN osmtest_t *p_osmt, p_sa_mad->attr_id = IB_MAD_ATTR_INFORM_INFO; /* copy the reference inform info */ - cl_memcpy(p_ii, p_inform_info, sizeof(ib_inform_info_t)); + memcpy(p_ii, p_inform_info, sizeof(ib_inform_info_t)); if (reg_flag) { osm_log( &p_osmt->log, OSM_LOG_INFO, "osmt_reg_unreg_inform_info: " - "Subscribing InformInfo: Traps from lid:0x%X to 0x%X, trap num :0x%X.\n", + "Subscribing InformInfo: Traps from lid:0x%X to 0x%X, trap num :0x%X\n", p_ii->lid_range_begin,p_ii->lid_range_end,p_ii->g_or_v.generic.trap_num); } else { osm_log( &p_osmt->log, OSM_LOG_INFO, "osmt_reg_unreg_inform_info: " - "UnSubscribing InformInfo: Traps from lid:0x%X to 0x%X.\n", + "UnSubscribing InformInfo: Traps from lid:0x%X to 0x%X\n", p_ii->lid_range_begin, p_ii->lid_range_end); } @@ -265,35 +263,37 @@ osmt_reg_unreg_inform_info( IN osmtest_t *p_osmt, wrid) != 1) { osm_log( p_log, OSM_LOG_ERROR, "osmt_reg_unreg_inform_info: ERR 0120: " - "Error posting recv bufs.\n"); + "Error posting recv bufs\n"); status = IB_ERROR; goto Exit; } osm_log( p_log, OSM_LOG_DEBUG, "osmt_reg_unreg_inform_info: " - "Posted recv bufs.\n"); + "Posted recv bufs\n"); vapi_ret = osmt_mtl_create_av(&p_qp_ctx->qp_bind_hndl, p_osmt->local_port.sm_lid, &avh); if (vapi_ret != VAPI_OK) { osm_log( p_log, OSM_LOG_ERROR, "osmt_reg_unreg_inform_info: ERR 0121: " - "Error Preparing AVH (%s).\n", + "Error Preparing AVH (%s)\n", VAPI_strerror_sym(vapi_ret) ); status = IB_ERROR; goto Exit; } osm_log( p_log, OSM_LOG_DEBUG, "osmt_reg_unreg_inform_info: " - "Prepared AVH .\n"); + "Prepared AVH\n"); if( osm_log_is_active( p_log, OSM_LOG_DEBUG ) ) { osm_dump_sa_mad( p_log, (ib_sa_mad_t *)(p_qp_ctx->p_send_buf), OSM_LOG_DEBUG); - /* for (i = 56; i < 253; i++) { */ - /* if ( i % 8 == 0 ) { printf("\n %d : ", i);} */ - /* printf("0x%02X ", p_qp_ctx->p_send_buf[i]); */ - /* } */ +#if 0 + for (i = 56; i < 253; i++) { + if ( i % 8 == 0 ) { printf("\n %d : ", i); } + printf("0x%02X ", p_qp_ctx->p_send_buf[i]); + } +#endif printf("\n"); } @@ -310,7 +310,7 @@ osmt_reg_unreg_inform_info( IN osmtest_t *p_osmt, { osm_log( p_log, OSM_LOG_ERROR, "osmt_reg_unreg_inform_info: ERR 0122: " - "Error sending mad (%s).\n", + "Error sending mad (%s)\n", VAPI_strerror_sym(vapi_ret) ); status = IB_ERROR; goto Exit; @@ -326,7 +326,7 @@ osmt_reg_unreg_inform_info( IN osmtest_t *p_osmt, { osm_log( p_log, OSM_LOG_ERROR, "osmt_reg_unreg_inform_info: ERR 0123: " - "Error getting send completion (%s).\n", + "Error getting send completion (%s)\n", VAPI_strerror_sym(vapi_ret) ); status = IB_ERROR; goto Exit; @@ -336,14 +336,14 @@ osmt_reg_unreg_inform_info( IN osmtest_t *p_osmt, { osm_log( p_log, OSM_LOG_ERROR, "osmt_reg_unreg_inform_info: ERR 0124: " - "Error on send completion (%s) (%d).\n", + "Error on send completion (%s) (%d)\n", VAPI_strerror_sym(wc_desc.status), wc_desc.status ); status = IB_ERROR; goto Exit; } osm_log( p_log, OSM_LOG_DEBUG, "osmt_reg_unreg_inform_info: " - "Sent MAD .\n"); + "Sent MAD\n"); /* --------------------- RECV ------------------------- */ vapi_ret = osmt_mtl_mad_poll4cqe(p_qp_ctx->qp_bind_hndl.hca_hndl, @@ -362,7 +362,7 @@ osmt_reg_unreg_inform_info( IN osmtest_t *p_osmt, { osm_log( p_log, OSM_LOG_ERROR, "osmt_reg_unreg_inform_info: ERR 0125: " - "Error receiving mad (%s).\n", + "Error receiving mad (%s)\n", VAPI_strerror_sym(vapi_ret) ); status = IB_ERROR; } @@ -376,7 +376,7 @@ osmt_reg_unreg_inform_info( IN osmtest_t *p_osmt, { osm_log( &p_osmt->log, OSM_LOG_ERROR, "osmt_reg_unreg_inform_info: " - "Remote error = %s.\n", + "Remote error = %s\n", ib_get_mad_status_str( (ib_mad_t *)p_sa_mad )); status = IB_REMOTE_ERROR; goto Exit; @@ -386,7 +386,7 @@ osmt_reg_unreg_inform_info( IN osmtest_t *p_osmt, { osm_log( &p_osmt->log, OSM_LOG_ERROR, "osmt_reg_unreg_inform_info: " - "Expected a IB_MAD_METHOD_GET_RESP but got:(%X).\n", + "Expected IB_MAD_METHOD_GET_RESP but got:(%X)\n", p_sa_mad->method); status = IB_REMOTE_ERROR; goto Exit; @@ -396,7 +396,7 @@ osmt_reg_unreg_inform_info( IN osmtest_t *p_osmt, { osm_log( &p_osmt->log, OSM_LOG_ERROR, "osmt_reg_unreg_inform_info: " - "Expected a IB_MAD_ATTR_INFORM_INFO but got:(%X).\n", + "Expected IB_MAD_ATTR_INFORM_INFO but got:(%X)\n", cl_ntoh16(p_sa_mad->attr_id)); status = IB_REMOTE_ERROR; goto Exit; @@ -407,7 +407,7 @@ osmt_reg_unreg_inform_info( IN osmtest_t *p_osmt, { osm_log( p_log, OSM_LOG_ERROR, "osmt_reg_unreg_inform_info: ERR 0126: " - "Subscribe/Unsubscribe Failed.\n"); + "Subscribe/Unsubscribe Failed\n"); status = IB_REMOTE_ERROR; } @@ -439,15 +439,15 @@ osmt_send_trap_wait_for_forward( IN osmtest_t * const p_osmt, osm_log_t *p_log = &p_osmt->log; ib_api_status_t status = IB_SUCCESS; - OSM_LOG_ENTER( &p_osmt->log, osmt_send_trap_wait_for_forward ); + OSM_LOG_ENTER( p_log, osmt_send_trap_wait_for_forward ); - osm_log( &p_osmt->log, OSM_LOG_INFO, + osm_log( p_log, OSM_LOG_INFO, "osmt_send_trap_wait_for_forward: " - "Sending Traps to QP0 of SA LID:%X\n", + "Sending Traps to QP0 of SA LID:0x%X\n", p_osmt->local_port.sm_lid); /* init the MAD */ - cl_memclr(p_smp, sizeof(ib_smp_t)); + memset(p_smp, 0, sizeof(ib_smp_t)); ib_mad_init_new( (ib_mad_t*)p_smp, IB_MCLASS_SUBN_LID, ( uint8_t ) 2, @@ -461,7 +461,7 @@ osmt_send_trap_wait_for_forward( IN osmtest_t * const p_osmt, /* prepare the notice */ p_ntc->generic_type = 0x82;/* generic, type = 2 */ - ib_notice_set_prod_type(p_ntc, 1); + ib_notice_set_prod_type_ho(p_ntc, 1); p_ntc->g_or_v.generic.trap_num = cl_hton16(0x26); p_ntc->issuer_lid = cl_hton16(2); @@ -473,13 +473,13 @@ osmt_send_trap_wait_for_forward( IN osmtest_t * const p_osmt, wrid) != 1) { osm_log( p_log, OSM_LOG_ERROR, "osmt_send_trap_wait_for_forward: ERR 0127: " - "Error posting recv bufs .\n"); + "Error posting recv bufs\n"); status = IB_ERROR; goto Exit; } osm_log( p_log, OSM_LOG_DEBUG, "osmt_send_trap_wait_for_forward: " - "Posted recv bufs .\n"); + "Posted recv bufs\n"); av.dlid = p_osmt->local_port.sm_lid; av.grh_flag = FALSE; @@ -494,8 +494,8 @@ osmt_send_trap_wait_for_forward( IN osmtest_t * const p_osmt, osm_log( p_log, OSM_LOG_DEBUG, "osmt_send_trap_wait_for_forward: " "av.dlid 0x%X, " - "av.static_rate %d, " - "av.path_bits %d.\n", + "av.static_rate %d, " + "av.path_bits %d\n", cl_ntoh16( av.dlid ), av.static_rate, av.src_path_bits ); } @@ -508,7 +508,7 @@ osmt_send_trap_wait_for_forward( IN osmtest_t * const p_osmt, { osm_log( p_log, OSM_LOG_ERROR, "osmt_send_trap_wait_for_forward: ERR 0128: " - "Error sending mad (%d).\n", mgt_res ); + "Error sending mad (%d)\n", mgt_res ); status = IB_ERROR; goto Exit; } @@ -518,18 +518,18 @@ osmt_send_trap_wait_for_forward( IN osmtest_t * const p_osmt, { osm_log( p_log, OSM_LOG_ERROR, "osmt_send_trap_wait_for_forward: ERR 0129: " - "Error Preparing AVH (%s).\n", + "Error Preparing AVH (%s)\n", VAPI_strerror_sym(vapi_ret) ); status = IB_ERROR; goto Exit; } osm_log( p_log, OSM_LOG_DEBUG, "osmt_send_trap_wait_for_forward: " - "Prepared AVH .\n"); + "Prepared AVH\n"); osm_log( p_log, OSM_LOG_DEBUG, "osmt_send_trap_wait_for_forward: " - "Trap MAD Sent.\n"); + "Trap MAD Sent\n"); /* --------------------- RECV ------------------------- */ vapi_ret = osmt_mtl_mad_poll4cqe(p_qp_ctx->qp_bind_hndl.hca_hndl, @@ -544,7 +544,7 @@ osmt_send_trap_wait_for_forward( IN osmtest_t * const p_osmt, { osm_log( p_log, OSM_LOG_ERROR, "osmt_send_trap_wait_for_forward: ERR 0130: " - "Timeout receiving mad (%s).\n", + "Timeout receiving mad (%s)\n", VAPI_strerror_sym(vapi_ret) ); status = IB_TIMEOUT; } @@ -552,7 +552,7 @@ osmt_send_trap_wait_for_forward( IN osmtest_t * const p_osmt, { osm_log( p_log, OSM_LOG_ERROR, "osmt_send_trap_wait_for_forward: ERR 0131: " - "Error receiving mad (%s).\n", + "Error receiving mad (%s)\n", VAPI_strerror_sym(vapi_ret) ); status = IB_ERROR; } @@ -566,31 +566,33 @@ osmt_send_trap_wait_for_forward( IN osmtest_t * const p_osmt, { if (p_sa_mad->attr_id == IB_MAD_ATTR_NOTICE) { - osm_log( &p_osmt->log, OSM_LOG_INFO, + osm_log( p_log, OSM_LOG_INFO, "osmt_send_trap_wait_for_forward: " - "Received the Report !\n"); + "Received the Report!\n"); status = IB_SUCCESS; } else { - osm_log( &p_osmt->log, OSM_LOG_ERROR, + osm_log( p_log, OSM_LOG_ERROR, "osmt_send_trap_wait_for_forward: ERR 1020" - "Did not receive a Report(Notice) but attr:%d.\n", + "Did not receive a Report(Notice) but attr:%d\n", cl_ntoh16(p_sa_mad->attr_id) ); + status = IB_ERROR; } } else { - osm_log( &p_osmt->log, OSM_LOG_ERROR, + osm_log( p_log, OSM_LOG_ERROR, "osmt_send_trap_wait_for_forward: ERR 1020" - "Received an Unexpected Method:%d.\n", + "Received an Unexpected Method:%d\n", p_smp->method ); + status = IB_ERROR; } Exit: - OSM_LOG_EXIT( &p_osmt->log ); + OSM_LOG_EXIT( p_log ); return status; } @@ -610,9 +612,9 @@ osmt_trap_wait( IN osmtest_t * const p_osmt, osm_log_t *p_log = &p_osmt->log; ib_api_status_t status = IB_SUCCESS; - OSM_LOG_ENTER( &p_osmt->log, osmt_trap_wait ); + OSM_LOG_ENTER( p_log, osmt_trap_wait ); - osm_log( &p_osmt->log, OSM_LOG_INFO, + osm_log( p_log, OSM_LOG_INFO, "osmt_trap_wait: " "Waiting for Traps under QP:0x%X of SA LID:0x%X\n", cl_ntoh16(p_osmt->local_port.sm_lid)); @@ -631,7 +633,7 @@ osmt_trap_wait( IN osmtest_t * const p_osmt, { osm_log( p_log, OSM_LOG_ERROR, "osmt_trap_wait: ERR 0130: " - "Timeout receiving mad (%s).\n", + "Timeout receiving mad (%s)\n", VAPI_strerror_sym(vapi_ret) ); status = IB_TIMEOUT; } @@ -639,7 +641,7 @@ osmt_trap_wait( IN osmtest_t * const p_osmt, { osm_log( p_log, OSM_LOG_ERROR, "osmt_trap_wait: ERR 0131: " - "Error receiving mad (%s).\n", + "Error receiving mad (%s)\n", VAPI_strerror_sym(vapi_ret) ); status = IB_ERROR; } @@ -655,29 +657,31 @@ osmt_trap_wait( IN osmtest_t * const p_osmt, { osm_log( &p_osmt->log, OSM_LOG_INFO, "osmt_trap_wait: " - "Received the Report !\n"); + "Received the Report!\n"); status = IB_SUCCESS; } else { osm_log( &p_osmt->log, OSM_LOG_ERROR, "osmt_trap_wait: ERR 1020" - "Did not receive a Report(Notice) but attr:%d.\n", + "Did not receive a Report(Notice) but attr:%d\n", cl_ntoh16(p_sa_mad->attr_id) ); + status = IB_ERROR; } } else { osm_log( &p_osmt->log, OSM_LOG_ERROR, "osmt_trap_wait: ERR 1020" - "Received an Unexpected Method:%d.\n", + "Received an Unexpected Method:%d\n", p_smp->method ); + status = IB_ERROR; } Exit: - OSM_LOG_EXIT( &p_osmt->log ); + OSM_LOG_EXIT( p_log ); return status; } @@ -690,7 +694,7 @@ ib_api_status_t osmt_init_inform_info(IN osmtest_t * const p_osmt, OUT ib_inform_info_t* p_ii) { - cl_memclr(p_ii, sizeof(ib_inform_info_t)); + memset(p_ii, 0, sizeof(ib_inform_info_t)); /* p_ii->lid_range_begin = cl_hton16(1); */ p_ii->lid_range_begin = 0xFFFF; p_ii->lid_range_end = cl_hton16(p_osmt->max_lid); @@ -707,7 +711,7 @@ osmt_init_inform_info_by_trap (IN osmtest_t * const p_osmt, IN ib_net16_t trap_num, OUT ib_inform_info_t* p_ii) { - cl_memclr(p_ii, sizeof(ib_inform_info_t)); + memset(p_ii, 0, sizeof(ib_inform_info_t)); /* p_ii->lid_range_begin = cl_hton16(1); */ p_ii->lid_range_begin = 0xFFFF; p_ii->lid_range_end = cl_hton16(p_osmt->max_lid); @@ -814,7 +818,7 @@ osmt_run_inform_info_flow( IN osmtest_t * const p_osmt ) { { osm_log( &p_osmt->log, OSM_LOG_INFO, "osmt_run_inform_info_flow:" - "Remote Error during UnSubscribe.\n"); + "Remote Error during UnSubscribe\n"); status = IB_ERROR; goto Exit; } @@ -875,14 +879,14 @@ osmt_run_trap64_65_flow( IN osmtest_t * const p_osmt) { 1) != 1) { osm_log( &p_osmt->log, OSM_LOG_ERROR, "osmt_run_trap64_65_flow: ERR 0127: " - "Error posting recv bufs for trap 64.\n"); + "Error posting recv bufs for trap 64\n"); status = IB_ERROR; goto Exit; } osm_log( &p_osmt->log, OSM_LOG_DEBUG, "osmt_run_trap64_65_flow: " - "Posted recv bufs for trap 64.\n"); + "Posted recv bufs for trap 64\n"); /* init the inform info */ osmt_init_inform_info_by_trap(p_osmt, @@ -908,15 +912,18 @@ osmt_run_trap64_65_flow( IN osmtest_t * const p_osmt) { 1) != 1) { osm_log( &p_osmt->log, OSM_LOG_ERROR, "osmt_run_trap64_65_flow: ERR 0127: " - "Error posting recv bufs for trap 65.\n"); + "Error posting recv bufs for trap 65\n"); status = IB_ERROR; goto Exit; } osm_log( &p_osmt->log, OSM_LOG_DEBUG, "osmt_run_trap64_65_flow: " - "Posted recv bufs for trap 65.\n"); + "Posted recv bufs for trap 65\n"); + /* Sleep for x seconds in order to allow external script trap generation */ - /* sleep (p_osmt->opt.wait_time); */ +#if 0 + sleep (p_osmt->opt.wait_time); +#endif /* wait for a trap on QPN */ status = osmt_trap_wait(p_osmt, &qp_ctx); @@ -951,3 +958,4 @@ osmt_run_trap64_65_flow( IN osmtest_t * const p_osmt) { } #endif /* OSM_VENDOR_INTF_MTL */ + diff --git a/trunk/ulp/opensm/user/osmtest/osmt_mtl_regular_qp.c b/trunk/ulp/opensm/user/osmtest/osmt_mtl_regular_qp.c index a3ac3c15..e1f8c3cc 100644 --- a/trunk/ulp/opensm/user/osmtest/osmt_mtl_regular_qp.c +++ b/trunk/ulp/opensm/user/osmtest/osmt_mtl_regular_qp.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -31,6 +31,7 @@ * $Id$ */ + #ifdef OSM_VENDOR_INTF_MTL /* - Mellanox Confidential and Proprietary - @@ -443,3 +444,4 @@ VAPI_ret_t osmt_mtl_mad_poll4cqe(VAPI_hca_hndl_t hca,VAPI_cq_hndl_t cq, } #endif /* OSM_VENDOR_INTF_MTL */ + diff --git a/trunk/ulp/opensm/user/osmtest/osmt_multicast.c b/trunk/ulp/opensm/user/osmtest/osmt_multicast.c index e9f7bf94..7082e7d4 100644 --- a/trunk/ulp/opensm/user/osmtest/osmt_multicast.c +++ b/trunk/ulp/opensm/user/osmtest/osmt_multicast.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -31,6 +31,7 @@ * $Id$ */ + /* * Abstract: * Implementation of Multicast Member testing flow.. @@ -41,8 +42,6 @@ * $Revision: 1.2 $ */ -/* next error code: 16A */ - #ifndef __WIN__ #include #endif @@ -50,12 +49,92 @@ #include #include #include -#include #include #include "osmtest.h" -static -cl_status_t +/********************************************************************** + **********************************************************************/ + +static void +__osmt_print_all_multicast_records( + IN osmtest_t * const p_osmt ) +{ + uint32_t i; + ib_api_status_t status; + osmv_query_req_t req; + osmv_user_query_t user; + osmtest_req_context_t context; + ib_member_rec_t *mcast_record; + + memset( &context, 0, sizeof( context ) ); + memset( &req, 0, sizeof( req ) ); + memset( &user, 0, sizeof( user ) ); + + user.attr_id = IB_MAD_ATTR_MCMEMBER_RECORD; + user.attr_offset = ib_get_attr_offset(sizeof(*mcast_record)); + + req.query_type = OSMV_QUERY_USER_DEFINED; + req.timeout_ms = p_osmt->opt.transaction_timeout; + req.retry_cnt = 1; + req.flags = OSM_SA_FLAGS_SYNC; + context.p_osmt = p_osmt; + req.query_context = &context; + req.pfn_query_cb = osmtest_query_res_cb; + req.p_query_input = &user; + + /* UnTrusted (SMKey of 0) - get the multicast groups */ + status = osmv_query_sa(p_osmt->h_bind, &req); + + if (status != IB_SUCCESS || context.result.status != IB_SUCCESS) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "__osmt_print_all_multicast_records: ERR 02B5: " + "Failed getting the multicast groups records - %s/%s\n", + ib_get_err_str(status), + ib_get_err_str(context.result.status) ); + return; + } + + osm_log( &p_osmt->log, OSM_LOG_INFO, + "\n |------------------------------------------|" + "\n | Remaining Multicast Groups |" + "\n |------------------------------------------|\n" ); + + for (i = 0; i < context.result.result_cnt; i++) { + mcast_record = osmv_get_query_mc_rec(context.result.p_result_madw, i); + osm_dump_mc_record(&p_osmt->log, mcast_record,OSM_LOG_INFO); + } + + /* Trusted - now get the multicast group members */ + req.sm_key = OSM_DEFAULT_SM_KEY; + status = osmv_query_sa(p_osmt->h_bind, &req); + + if (status != IB_SUCCESS || context.result.status != IB_SUCCESS) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "__osmt_print_all_multicast_records: ERR 02B6: " + "Failed getting the multicast group members records - %s/%s\n", + ib_get_err_str(status), + ib_get_err_str(context.result.status) ); + return; + } + + osm_log( &p_osmt->log, OSM_LOG_INFO, + "\n |--------------------------------------------------|" + "\n | Remaining Multicast Group Members |" + "\n |--------------------------------------------------|\n" ); + + for (i = 0; i < context.result.result_cnt; i++) { + mcast_record = osmv_get_query_mc_rec(context.result.p_result_madw, i); + osm_dump_mc_record(&p_osmt->log, mcast_record,OSM_LOG_INFO); + } + +} + +/********************************************************************** + **********************************************************************/ + +static cl_status_t __match_mgids( IN const void* const p_object, IN void* context ) @@ -64,18 +143,16 @@ __match_mgids( ib_gid_t* p_mgid_list_item = (ib_gid_t*)p_object; int32_t count; - count = cl_memcmp( - p_mgid_context, - p_mgid_list_item, - sizeof(ib_gid_t)); - + count = memcmp(p_mgid_context, p_mgid_list_item, sizeof(ib_gid_t)); if(count == 0) return CL_SUCCESS; else return CL_NOT_FOUND; - } +/********************************************************************** + **********************************************************************/ + ib_api_status_t osmt_query_mcast( IN osmtest_t * const p_osmt ) { ib_api_status_t status = IB_SUCCESS; @@ -92,6 +169,7 @@ osmt_query_mcast( IN osmtest_t * const p_osmt ) { osmtest_mgrp_t *p_mgrp; OSM_LOG_ENTER( &p_osmt->log, osmt_query_mcast ); + /* * Do a blocking query for all Multicast Records in the subnet. * The result is returned in the result field of the caller's @@ -100,13 +178,12 @@ osmt_query_mcast( IN osmtest_t * const p_osmt ) { * The query structures are locals. */ - cl_memclr( &req, sizeof( req ) ); - cl_memclr( &user, sizeof( user ) ); + memset( &req, 0, sizeof( req ) ); + memset( &user, 0, sizeof( user ) ); context.p_osmt = p_osmt; user.attr_id = IB_MAD_ATTR_MCMEMBER_RECORD; user.attr_offset = ib_get_attr_offset( sizeof( ib_member_rec_t ) ); - user.comp_mask = 0; req.query_type = OSMV_QUERY_USER_DEFINED; req.timeout_ms = p_osmt->opt.transaction_timeout; @@ -115,7 +192,6 @@ osmt_query_mcast( IN osmtest_t * const p_osmt ) { req.query_context = &context; req.pfn_query_cb = osmtest_query_res_cb; req.p_query_input = &user; - req.sm_key = 0; status = osmv_query_sa( p_osmt->h_bind, &req ); @@ -154,7 +230,7 @@ osmt_query_mcast( IN osmtest_t * const p_osmt ) { p_item = p_next_item; p_next_item = cl_qmap_next( p_item ); cl_qmap_remove_item(&p_osmt->exp_subn.mgrp_mlid_tbl,p_item); - cl_free( p_item ); + free( p_item ); } @@ -168,10 +244,9 @@ osmt_query_mcast( IN osmtest_t * const p_osmt ) { for( i = 0; i < num_recs; i++ ) { - p_rec = - osmv_get_query_result( context.result.p_result_madw, i ); + p_rec = osmv_get_query_result( context.result.p_result_madw, i ); p_mgids_res = cl_list_find_from_head ( p_mgids_list,__match_mgids,&(p_rec->mgid)); - /* If returns iterator other than end of list - same mgid exist already */ + /* If returns iterator other than end of list, same mgid exists already */ if( p_mgids_res != cl_list_end( p_mgids_list ) ) { osm_log( &p_osmt->log, OSM_LOG_ERROR, @@ -190,20 +265,20 @@ osmt_query_mcast( IN osmtest_t * const p_osmt ) { { osm_log( &p_osmt->log, OSM_LOG_ERROR, "osmt_query_mcast: ERR 0205: " - "Could not add MGID to cl_list\n"); + "Could not add MGID to cl_list\n" ); status = IB_ERROR; goto Exit; } - p_mgrp = (osmtest_mgrp_t*)cl_malloc( sizeof(*p_mgrp) ); + p_mgrp = (osmtest_mgrp_t*)malloc( sizeof(*p_mgrp) ); if (!p_mgrp) { osm_log( &p_osmt->log, OSM_LOG_ERROR, "osmt_query_mcast: ERR 0204: " - "Could not allocate new MCG\n"); + "Could not allocate new MCG\n" ); status = IB_ERROR; goto Exit; } - cl_memcpy(&p_mgrp->mcmember_rec,p_rec,sizeof(p_mgrp->mcmember_rec)); + memcpy(&p_mgrp->mcmember_rec,p_rec,sizeof(p_mgrp->mcmember_rec)); cl_qmap_insert(&p_osmt->exp_subn.mgrp_mlid_tbl, cl_ntoh16(p_rec->mlid),&p_mgrp->map_item); } @@ -219,13 +294,16 @@ osmt_query_mcast( IN osmtest_t * const p_osmt ) { return ( status ); } +/********************************************************************** + **********************************************************************/ + /* given a multicast request send and wait for response. */ ib_api_status_t osmt_send_mcast_request( IN osmtest_t * const p_osmt, IN uint8_t is_set, IN ib_member_rec_t *p_mc_req, IN uint64_t comp_mask, - OUT ib_sa_mad_t *p_res + OUT ib_sa_mad_t *p_res ) { osmtest_req_context_t context; ib_api_status_t status = IB_SUCCESS; @@ -239,10 +317,10 @@ osmt_send_mcast_request( IN osmtest_t * const p_osmt, * * The query structures are locals. */ - cl_memclr( &req, sizeof( req ) ); - cl_memclr( &user, sizeof( user ) ); - cl_memclr( &context, sizeof( context ) ); - cl_memclr( p_res, sizeof(ib_sa_mad_t ) ); + memset( &req, 0, sizeof( req ) ); + memset( &user, 0, sizeof( user ) ); + memset( &context, 0, sizeof( context ) ); + memset( p_res, 0, sizeof( ib_sa_mad_t ) ); context.p_osmt = p_osmt; @@ -257,7 +335,7 @@ osmt_send_mcast_request( IN osmtest_t * const p_osmt, } else if (is_set == 0xee) { osm_log( &p_osmt->log, OSM_LOG_VERBOSE, - "osmt_send_mcast_request: Set USER DEFINED QUERY\n"); + "osmt_send_mcast_request: Set USER DEFINED QUERY\n" ); req.query_type = OSMV_QUERY_USER_DEFINED; user.method = IB_MAD_METHOD_GET; user.attr_id = IB_MAD_ATTR_MCMEMBER_RECORD; @@ -265,7 +343,7 @@ osmt_send_mcast_request( IN osmtest_t * const p_osmt, } else if (is_set == 0xff) { osm_log( &p_osmt->log, OSM_LOG_VERBOSE, - "osmt_send_mcast_request: Set USER DEFINED QUERY\n"); + "osmt_send_mcast_request: Set USER DEFINED QUERY\n" ); req.query_type = OSMV_QUERY_USER_DEFINED; user.method = IB_MAD_METHOD_SET; user.attr_id = IB_MAD_ATTR_MCMEMBER_RECORD; @@ -288,7 +366,6 @@ osmt_send_mcast_request( IN osmtest_t * const p_osmt, req.query_context = &context; req.pfn_query_cb = osmtest_query_res_cb; req.p_query_input = &user; - req.sm_key = 0; status = osmv_query_sa( p_osmt->h_bind, &req ); @@ -301,14 +378,17 @@ osmt_send_mcast_request( IN osmtest_t * const p_osmt, } /* ok it worked */ - cl_memcpy(p_res, - osm_madw_get_mad_ptr(context.result.p_result_madw), - sizeof(ib_sa_mad_t)); + memcpy(p_res, + osm_madw_get_mad_ptr(context.result.p_result_madw), + sizeof(ib_sa_mad_t)); status = context.result.status; if( status != IB_SUCCESS ) { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmt_send_mcast_request: ERR 0224: " + "ib_query failed (%s)\n", ib_get_err_str( status ) ); if( status == IB_REMOTE_ERROR ) { osm_log( &p_osmt->log, OSM_LOG_ERROR, @@ -331,20 +411,22 @@ osmt_send_mcast_request( IN osmtest_t * const p_osmt, OSM_LOG_EXIT( &p_osmt->log ); return ( status ); - } +/********************************************************************** + **********************************************************************/ + void osmt_init_mc_query_rec(IN osmtest_t * const p_osmt, IN OUT ib_member_rec_t *p_mc_req) { /* use default values so we can change only what we want later */ - cl_memclr(p_mc_req,sizeof(ib_member_rec_t)); + memset(p_mc_req, 0, sizeof(ib_member_rec_t)); - /* we leave the MGID to the user */ - cl_memcpy(&p_mc_req->port_gid.unicast.interface_id, - &p_osmt->local_port.port_guid, - sizeof(p_osmt->local_port.port_guid) - ); + /* we leave the MGID to the user */ + memcpy(&p_mc_req->port_gid.unicast.interface_id, + &p_osmt->local_port.port_guid, + sizeof(p_osmt->local_port.port_guid) + ); /* use our own subnet prefix: */ p_mc_req->port_gid.unicast.prefix = CL_HTON64(0xFE80000000000000ULL); @@ -365,7 +447,7 @@ osmt_init_mc_query_rec(IN osmtest_t * const p_osmt, * UD Multicast testing flow: * o15.0.1.3: * - Request new MCG with not enough components in comp_mask : - * ERR_INSUFFICIANT_COMPONENTS + * ERR_INSUFFICIENT_COMPONENTS * o15.0.1.8: * - Request a join with irrelevant RATE and get a ERR_INVALID_REQ * o15.0.1.4: @@ -397,34 +479,42 @@ osmt_init_mc_query_rec(IN osmtest_t * const p_osmt, * - Try full delete (JoinState and should be 0) * - Wait for trap 67. * - Try joining (not full mem) again to see the group was deleted. - * (should fail) + * (should fail - o15.0.1.13) * o15.0.1.15: * - Try deletion of the IPoIB MCG and get: ERR_REQ_INVALID * o15.0.1.16: * - Try GetTable with PortGUID wildcarded and get back some groups. ***********************************************************************/ + +/* The following macro can be used only within the osmt_run_mcast_flow() function */ +#define IS_IPOIB_MGID(p_mgid) \ + ( !memcmp(&osm_ipoib_good_mgid, (p_mgid), sizeof(osm_ipoib_good_mgid)) || \ + !memcmp(&osm_ts_ipoib_good_mgid, (p_mgid), sizeof(osm_ts_ipoib_good_mgid)) ) + ib_api_status_t osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { ib_api_status_t status; ib_member_rec_t mc_req_rec; ib_member_rec_t *p_mc_res; - ib_sa_mad_t res_sa_mad; - uint64_t comp_mask=0; - ib_net64_t remote_port_guid=0x0; + ib_sa_mad_t res_sa_mad; + uint64_t comp_mask = 0; + ib_net64_t remote_port_guid = 0x0; cl_qmap_t *p_mgrp_mlid_tbl; osmtest_mgrp_t *p_mgrp; - ib_gid_t special_mgid,tmp_mgid,proxy_mgid; - ib_net16_t invalid_mlid=0x0; - ib_net16_t max_mlid = cl_hton16(0xFFFE),tmp_mlid; + ib_gid_t special_mgid, tmp_mgid, proxy_mgid; + ib_net16_t invalid_mlid = 0x0; + ib_net16_t max_mlid = cl_hton16(0xFFFE), tmp_mlid; boolean_t ReachedMlidLimit = FALSE; - int start_cnt=0,cnt,middle_cnt=0,end_cnt=0; - int IPoIBIsFound=0,mcg_outside_test_cnt=0,fail_to_delete_mcg=0; + int start_cnt = 0, cnt, middle_cnt = 0, end_cnt = 0; + int start_ipoib_cnt = 0, end_ipoib_cnt = 0; + int mcg_outside_test_cnt = 0, fail_to_delete_mcg = 0; osmtest_req_context_t context; ib_node_record_t *p_rec; - uint32_t num_recs = 0,i; - uint8_t mtu_phys = 0,rate_phys = 0; + uint32_t num_recs = 0, i; + uint8_t mtu_phys = 0, rate_phys = 0; cl_map_t test_created_mlids; /* List of all mlids created in this test */ ib_member_rec_t* p_recvd_rec; + boolean_t got_error = FALSE; static ib_gid_t good_mgid = { { @@ -436,33 +526,32 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { }; static ib_gid_t osm_ipoib_mgid = { { - 0xff, /* multicat field */ - 0x12, /* scope */ - 0x40, 0x1b, /* IPv4 signature */ - 0xff, 0xff, /* 16 bits of P_Key (to be filled in) */ - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 48 bits of zeros */ - 0xff, 0xff, 0xff, 0xee, /* 32 bit IPv4 broadcast address */ + 0xff, /* multicast field */ + 0x12, /* scope */ + 0x40, 0x1b, /* IPv4 signature */ + 0xff, 0xff, /* 16 bits of P_Key (to be filled in) */ + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 48 bits of zeros */ + 0xff, 0xff, 0xff, 0xee, /* 32 bit IPv4 broadcast address */ }, }; - static ib_gid_t osm_ts_ipoib_good_mgid = { { - 0xff, /* multicast field */ - 0x12, /* non-permanent bit,scope */ - 0x40, 0x1b, /* IPv4 signature */ - 0xff, 0xff, /* 16 bits of P_Key (to be filled in) */ - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 48 bits of zeros */ - 0x00, 0x00, 0x00, 0x01, /* 32 bit IPv4 broadcast address */ + 0xff, /* multicast field */ + 0x12, /* non-permanent bit,scope */ + 0x40, 0x1b, /* IPv4 signature */ + 0xff, 0xff, /* 16 bits of P_Key (to be filled in) */ + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 48 bits of zeros */ + 0x00, 0x00, 0x00, 0x01, /* 32 bit IPv4 broadcast address */ }, }; static ib_gid_t osm_ipoib_good_mgid = { { - 0xff, /* multicast field */ - 0x12, /* non-permanent bit,scope */ - 0x40, 0x1b, /* IPv4 signature */ - 0xff, 0xff, /* 16 bits of P_Key (to be filled in) */ - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 48 bits of zeros */ - 0xff, 0xff, 0xff, 0xff, /* 32 bit IPv4 broadcast address */ + 0xff, /* multicast field */ + 0x12, /* non-permanent bit,scope */ + 0x40, 0x1b, /* IPv4 signature */ + 0xff, 0xff, /* 16 bits of P_Key (to be filled in) */ + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 48 bits of zeros */ + 0xff, 0xff, 0xff, 0xff, /* 32 bit IPv4 broadcast address */ }, }; static ib_gid_t osm_link_local_mgid = { @@ -474,7 +563,6 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { }, }; - OSM_LOG_ENTER( &p_osmt->log, osmt_run_mcast_flow ); osm_log( &p_osmt->log, OSM_LOG_INFO, @@ -486,9 +574,8 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { { osm_log( &p_osmt->log, OSM_LOG_ERROR, "osmt_run_mcast_flow: ERR 2FF " - "GetTable of all records has failed!\n"); + "GetTable of all records has failed!\n" ); goto Exit; - } /* Initialize the test_created_mgrps map */ @@ -506,7 +593,7 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { start_cnt = cl_qmap_count(p_mgrp_mlid_tbl); osm_log( &p_osmt->log, OSM_LOG_INFO, "osmt_run_mcast_flow (start): " - "Number of MC Records found in SA DB is %d\n",start_cnt); + "Number of MC Records found in SA DB is %d\n", start_cnt); } /* This flow is being added due to bug discovered using SilverStorm stack - @@ -525,25 +612,35 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { while( p_mgrp != (osmtest_mgrp_t*)cl_qmap_end( p_mgrp_mlid_tbl ) ) { /* search for ipoib mgid */ - if (!cl_memcmp(&osm_ipoib_good_mgid,&p_mgrp->mcmember_rec.mgid,sizeof(osm_ipoib_good_mgid)) || - !cl_memcmp(&osm_ts_ipoib_good_mgid,&p_mgrp->mcmember_rec.mgid,sizeof(osm_ts_ipoib_good_mgid))) + if (IS_IPOIB_MGID(&p_mgrp->mcmember_rec.mgid)) { - IPoIBIsFound=1; + start_ipoib_cnt++; } else + { + osm_log( &p_osmt->log, OSM_LOG_INFO, + "osmt_run_mcast_flow: " + "Non-IPoIB MC Groups exist: mgid=0x%016" PRIx64 ":0x%016" PRIx64 "\n", + cl_ntoh64(p_mgrp->mcmember_rec.mgid.unicast.prefix), + cl_ntoh64(p_mgrp->mcmember_rec.mgid.unicast.interface_id) ); mcg_outside_test_cnt++; + } p_mgrp = (osmtest_mgrp_t*)cl_qmap_next( &p_mgrp->map_item ); } - if (IPoIBIsFound) + osm_log( &p_osmt->log, OSM_LOG_INFO, + "osmt_run_mcast_flow: " + "Found %d non-IPoIB MC Groups\n", mcg_outside_test_cnt ); + + if (start_ipoib_cnt) { /* o15-0.2.4 - Check a join request to already created MCG */ osm_log( &p_osmt->log, OSM_LOG_INFO, "osmt_run_mcast_flow: " - "Found IPoIB MC Group, so we run SilverStorm Bug Flow...\n"); + "Found IPoIB MC Group, so we run SilverStorm Bug Flow...\n" ); /* Try to join first like IPoIB of SilverStorm */ - cl_memcpy(&mc_req_rec.mgid,&osm_ipoib_good_mgid,sizeof(ib_gid_t)); + memcpy(&mc_req_rec.mgid,&osm_ipoib_good_mgid,sizeof(ib_gid_t)); /* Request Join */ ib_member_set_join_state(&mc_req_rec, IB_MC_REC_STATE_FULL_MEMBER); comp_mask = @@ -552,11 +649,14 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { IB_MCR_COMPMASK_JOIN_STATE; status = osmt_send_mcast_request( - p_osmt, 0xff, /* User Defined query Set */ + p_osmt, 0xff, /* User Defined query Set */ &mc_req_rec, comp_mask, &res_sa_mad ); + osm_log(&p_osmt->log, OSM_LOG_INFO, + "osmt_run_mcast_flow: " + "Joining an existing IPoIB multicast group\n"); osm_log(&p_osmt->log, OSM_LOG_INFO, "osmt_run_mcast_flow: " "Sent Join request with :\n\t\tport_gid=0x%016"PRIx64 @@ -568,6 +668,14 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { cl_ntoh64(mc_req_rec.mgid.unicast.interface_id), (mc_req_rec.scope_state & 0x0F), ib_get_err_str(status)); + if (status != IB_SUCCESS) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmt_run_mcast_flow: ERR 02B3: " + "Failed joining existing IPoIB MCGroup - got %s\n", + ib_get_err_str(status)); + goto Exit; + } /* Check MTU & Rate Value and resend with SA suggested values */ p_mc_res = ib_sa_mad_get_payload_ptr(&res_sa_mad); @@ -584,14 +692,14 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { "Received attributes of MCG : \n\t\tMTU=0x%02X, RATE=0x%02X\n" , p_mc_res->mtu,p_mc_res->rate); - mc_req_rec.mtu = p_mc_res->mtu ; - mc_req_rec.rate = p_mc_res->rate ; + mc_req_rec.mtu = p_mc_res->mtu; + mc_req_rec.rate = p_mc_res->rate; /* Set feasible mtu & rate that will allow check the exact statement of OpenSM */ - mtu_phys = p_mc_res->mtu ; - rate_phys = p_mc_res->rate ; + mtu_phys = p_mc_res->mtu; + rate_phys = p_mc_res->rate; - cl_memcpy(&mc_req_rec.mgid,&osm_ipoib_good_mgid,sizeof(ib_gid_t)); + memcpy(&mc_req_rec.mgid, &osm_ipoib_good_mgid, sizeof(ib_gid_t)); /* Request Join */ ib_member_set_join_state(&mc_req_rec, IB_MC_REC_STATE_FULL_MEMBER); comp_mask = @@ -606,8 +714,8 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { osm_log(&p_osmt->log, OSM_LOG_INFO, "osmt_run_mcast_flow: " "Sending attributes of MCG : \n\t\tMTU=0x%02X, RATE=0x%02X\n" - , mc_req_rec.mtu,mc_req_rec.rate); - status = osmt_send_mcast_request( p_osmt, 0xff, /* User Defined query */ + , mc_req_rec.mtu, mc_req_rec.rate); + status = osmt_send_mcast_request( p_osmt, 0xff, /* User Defined query */ &mc_req_rec, comp_mask, &res_sa_mad ); @@ -618,7 +726,7 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { if (status != IB_SUCCESS) { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: ERR 02ef: " + "osmt_run_mcast_flow: ERR 02EF: " "Query as Full Member of already existing ipoib group 0x%016" PRIx64 ":0x%016" PRIx64 " has failed\n", cl_ntoh64(mc_req_rec.mgid.unicast.prefix), @@ -626,11 +734,6 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { goto Exit; } - else - { - mtu_phys = 0 ; - rate_phys = 0 ; - } /* We do not want to leave the MCG since its IPoIB */ } @@ -644,13 +747,17 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { /* Request Get */ ib_member_set_join_state(&mc_req_rec, IB_MC_REC_STATE_FULL_MEMBER); mc_req_rec.mlid = invalid_mlid; - comp_mask = - IB_MCR_COMPMASK_MLID; + comp_mask = IB_MCR_COMPMASK_MLID; - status = osmt_send_mcast_request( p_osmt, 0xee, /* User Defined query Get */ + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmt_run_mcast_flow: " EXPECTING_ERRORS_START "\n" ); + status = osmt_send_mcast_request( p_osmt, 0xee, /* User Defined query Get */ &mc_req_rec, comp_mask, &res_sa_mad ); + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmt_run_mcast_flow: " EXPECTING_ERRORS_END "\n" ); + if (status == IB_SUCCESS) { osm_log( &p_osmt->log, OSM_LOG_ERROR, @@ -674,19 +781,23 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { /* Request Get */ ib_member_set_join_state(&mc_req_rec, IB_MC_REC_STATE_FULL_MEMBER); - cl_memclr(&mc_req_rec.port_gid.unicast.interface_id,sizeof(ib_net64_t)); - comp_mask = - IB_MCR_COMPMASK_GID; + memset(&mc_req_rec.port_gid.unicast.interface_id, 0, sizeof(ib_net64_t)); + comp_mask = IB_MCR_COMPMASK_GID; - status = osmt_send_mcast_request( p_osmt, 0xee, /* User Defined query Get */ + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmt_run_mcast_flow: " EXPECTING_ERRORS_START "\n" ); + status = osmt_send_mcast_request( p_osmt, 0xee, /* User Defined query Get */ &mc_req_rec, comp_mask, &res_sa_mad ); + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmt_run_mcast_flow: " EXPECTING_ERRORS_END "\n" ); + if (status == IB_SUCCESS) { osm_log( &p_osmt->log, OSM_LOG_ERROR, "osmt_run_mcast_flow : ERR 2E4 " - "SubnAdmGet with invalid port guid succeeded\n"); + "SubnAdmGet with invalid port guid succeeded\n" ); status = IB_ERROR; goto Exit; } @@ -695,20 +806,16 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { osmt_init_mc_query_rec(p_osmt, &mc_req_rec); /**************************************************************************/ - /* o15.0.1.3: */ - /* - Request Join with insufficiant comp_mask */ + /* o15.0.1.3: */ + /* - Request Join with insufficient comp_mask */ osm_log( &p_osmt->log, OSM_LOG_INFO, "osmt_run_mcast_flow: " - "Checking Join with insufficiant comp mask qkey & pkey (o15.0.1.3)...\n" + "Checking Join with insufficient comp mask qkey & pkey (o15.0.1.3)...\n" ); - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: " - " Expecting Errors: ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^\n" - ); /* no MGID */ - cl_memclr(&mc_req_rec.mgid,sizeof(ib_gid_t)); + memset(&mc_req_rec.mgid, 0, sizeof(ib_gid_t)); /* Request Join */ ib_member_set_join_state(&mc_req_rec, IB_MC_REC_STATE_FULL_MEMBER); @@ -720,23 +827,24 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { IB_MCR_COMPMASK_SL | IB_MCR_COMPMASK_FLOW | IB_MCR_COMPMASK_JOIN_STATE | - IB_MCR_COMPMASK_TCLASS | /* all above are required */ + IB_MCR_COMPMASK_TCLASS | /* all above are required */ IB_MCR_COMPMASK_RATE_SEL | IB_MCR_COMPMASK_RATE; + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmt_run_mcast_flow: " EXPECTING_ERRORS_START "\n" ); status = osmt_send_mcast_request( p_osmt, 1, &mc_req_rec, comp_mask, &res_sa_mad ); osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: " - " Expected Errors: vvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvv\n" - ); + "osmt_run_mcast_flow: " EXPECTING_ERRORS_END "\n" ); + if (status != IB_REMOTE_ERROR || (( ib_net16_t ) (res_sa_mad.status & IB_SMP_STATUS_MASK )) != IB_SA_MAD_STATUS_INSUF_COMPS) { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: ERR 02eg: " + "osmt_run_mcast_flow: ERR 02EE: " "Expectedd REMOTE ERROR IB_SA_MAD_STATUS_INSUF_COMPS got:%s/%s\n", ib_get_err_str( status ), ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) ) @@ -750,12 +858,8 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { "Checking Join with insufficient comp mask - sl (15.0.1.3)...\n" ); - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: " - " Expecting Errors: ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^\n" - ); /* no MGID */ - cl_memclr(&mc_req_rec.mgid,sizeof(ib_gid_t)); + memset(&mc_req_rec.mgid, 0, sizeof(ib_gid_t)); /* Request Join */ ib_member_set_join_state(&mc_req_rec,IB_MC_REC_STATE_FULL_MEMBER ); @@ -767,23 +871,24 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { /* IB_MCR_COMPMASK_SL | */ IB_MCR_COMPMASK_FLOW | IB_MCR_COMPMASK_JOIN_STATE | - IB_MCR_COMPMASK_TCLASS | /* all above are required */ + IB_MCR_COMPMASK_TCLASS | /* all above are required */ IB_MCR_COMPMASK_RATE_SEL | IB_MCR_COMPMASK_RATE; + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmt_run_mcast_flow: " EXPECTING_ERRORS_START "\n" ); status = osmt_send_mcast_request( p_osmt, 1, &mc_req_rec, comp_mask, &res_sa_mad ); osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: " - " Expected Errors: vvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvv\n" - ); + "osmt_run_mcast_flow: " EXPECTING_ERRORS_END "\n" ); + if (status != IB_REMOTE_ERROR || (( ib_net16_t ) (res_sa_mad.status & IB_SMP_STATUS_MASK )) != IB_SA_MAD_STATUS_INSUF_COMPS) { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: ERR 02eh: " + "osmt_run_mcast_flow: ERR 02ED: " "Expectedd REMOTE ERROR IB_SA_MAD_STATUS_INSUF_COMPS got:%s/%s\n", ib_get_err_str( status ), ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) ) @@ -794,7 +899,7 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { osmt_init_mc_query_rec(p_osmt, &mc_req_rec); /* no MGID */ - cl_memclr(&mc_req_rec.mgid,sizeof(ib_gid_t)); + memset(&mc_req_rec.mgid, 0, sizeof(ib_gid_t)); mc_req_rec.mgid.raw[15] = 0x01; @@ -805,11 +910,6 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { "Checking Join with insufficient comp mask - flow label (o15.0.1.3)...\n" ); - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: " - " Expecting Errors: ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^\n" - ); - /* Request Join */ ib_member_set_join_state(&mc_req_rec, IB_MC_REC_STATE_FULL_MEMBER); @@ -821,23 +921,24 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { IB_MCR_COMPMASK_SL | /* IB_MCR_COMPMASK_FLOW | intentionaly missed to raise the error */ IB_MCR_COMPMASK_JOIN_STATE | - IB_MCR_COMPMASK_TCLASS | /* all above are required */ + IB_MCR_COMPMASK_TCLASS | /* all above are required */ IB_MCR_COMPMASK_RATE_SEL | IB_MCR_COMPMASK_RATE; + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmt_run_mcast_flow: " EXPECTING_ERRORS_START "\n" ); status = osmt_send_mcast_request( p_osmt, 1, &mc_req_rec, comp_mask, &res_sa_mad ); osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: " - " Expected Errors: vvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvv\n" - ); + "osmt_run_mcast_flow: " EXPECTING_ERRORS_END "\n" ); + if (status != IB_REMOTE_ERROR || (( ib_net16_t ) (res_sa_mad.status & IB_SMP_STATUS_MASK )) != IB_SA_MAD_STATUS_INSUF_COMPS) { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: ERR 02ei: " + "osmt_run_mcast_flow: ERR 02EC: " "Expected REMOTE ERROR IB_SA_MAD_STATUS_INSUF_COMPS got:%s/%s\n", ib_get_err_str( status ), ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) ) @@ -852,12 +953,7 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { osm_log( &p_osmt->log, OSM_LOG_INFO, "osmt_run_mcast_flow: " - "Checking Join with insufficiant comp mask - tclass (o15.0.1.3)...\n" - ); - - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: " - " Expecting Errors: ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^\n" + "Checking Join with insufficient comp mask - tclass (o15.0.1.3)...\n" ); /* Request Join */ @@ -875,20 +971,20 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { IB_MCR_COMPMASK_RATE_SEL | IB_MCR_COMPMASK_RATE; + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmt_run_mcast_flow: " EXPECTING_ERRORS_START "\n" ); status = osmt_send_mcast_request( p_osmt, 1, &mc_req_rec, comp_mask, &res_sa_mad ); osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: " - " Expected Errors: vvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvv\n" - ); + "osmt_run_mcast_flow: " EXPECTING_ERRORS_END "\n" ); if (status != IB_REMOTE_ERROR || (( ib_net16_t ) (res_sa_mad.status & IB_SMP_STATUS_MASK )) != IB_SA_MAD_STATUS_INSUF_COMPS) { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: ERR 02ej: " + "osmt_run_mcast_flow: ERR 02EA: " "Expected REMOTE ERROR IB_SA_MAD_STATUS_INSUF_COMPS got:%s/%s\n", ib_get_err_str( status ), ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) ) @@ -906,12 +1002,8 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { "Checking Join with insufficient comp mask - tclass qkey (o15.0.1.3)...\n" ); - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: " - " Expecting Errors: ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^\n" - ); /* no MGID */ - /* cl_memclr(&mc_req_rec.mgid,sizeof(ib_gid_t)); */ + /* memset(&mc_req_rec.mgid, 0, sizeof(ib_gid_t)); */ /* Request Join */ ib_member_set_join_state(&mc_req_rec, IB_MC_REC_STATE_FULL_MEMBER); @@ -927,20 +1019,20 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { IB_MCR_COMPMASK_RATE_SEL | IB_MCR_COMPMASK_RATE; + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmt_run_mcast_flow: " EXPECTING_ERRORS_START "\n" ); status = osmt_send_mcast_request( p_osmt, 1, &mc_req_rec, comp_mask, &res_sa_mad ); osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: " - " Expected Errors: vvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvv\n" - ); + "osmt_run_mcast_flow: " EXPECTING_ERRORS_END "\n" ); if (status != IB_REMOTE_ERROR || (( ib_net16_t ) (res_sa_mad.status & IB_SMP_STATUS_MASK )) != IB_SA_MAD_STATUS_INSUF_COMPS) { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: ERR 02ek: " + "osmt_run_mcast_flow: ERR 02E9: " "Expected REMOTE ERROR IB_SA_MAD_STATUS_INSUF_COMPS got:%s/%s\n", ib_get_err_str( status ), ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) ) @@ -949,8 +1041,8 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { goto Exit; } - /* o15.0.1.8: */ - /* - Request join with irrelevant RATE : get a ERR_INSUFFICIANT_COMPONENTS */ + /* o15.0.1.8: */ + /* - Request join with irrelevant RATE : get a ERR_INSUFFICIENT_COMPONENTS */ osm_log( &p_osmt->log, OSM_LOG_INFO, "osmt_run_mcast_flow: " "Checking Join with unrealistic rate (o15.0.1.8)...\n" @@ -969,14 +1061,19 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { IB_MCR_COMPMASK_SL | IB_MCR_COMPMASK_FLOW | IB_MCR_COMPMASK_JOIN_STATE | - IB_MCR_COMPMASK_TCLASS | /* all above are required */ + IB_MCR_COMPMASK_TCLASS | /* all above are required */ IB_MCR_COMPMASK_RATE_SEL | IB_MCR_COMPMASK_RATE; + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmt_run_mcast_flow: " EXPECTING_ERRORS_START "\n" ); status = osmt_send_mcast_request( p_osmt, 1, &mc_req_rec, comp_mask, &res_sa_mad ); + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmt_run_mcast_flow: " EXPECTING_ERRORS_END "\n" ); + if (status != IB_REMOTE_ERROR || res_sa_mad.status != IB_SA_MAD_STATUS_REQ_INVALID) { osm_log( &p_osmt->log, OSM_LOG_ERROR, @@ -1008,14 +1105,19 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { IB_MCR_COMPMASK_SL | IB_MCR_COMPMASK_FLOW | IB_MCR_COMPMASK_JOIN_STATE | - IB_MCR_COMPMASK_TCLASS | /* all above are required */ + IB_MCR_COMPMASK_TCLASS | /* all above are required */ IB_MCR_COMPMASK_RATE_SEL | IB_MCR_COMPMASK_RATE; + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmt_run_mcast_flow: " EXPECTING_ERRORS_START "\n" ); status = osmt_send_mcast_request( p_osmt, 1, &mc_req_rec, comp_mask, &res_sa_mad ); + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmt_run_mcast_flow: " EXPECTING_ERRORS_END "\n" ); + if (status != IB_REMOTE_ERROR || res_sa_mad.status != IB_SA_MAD_STATUS_REQ_INVALID) { osm_log( &p_osmt->log, OSM_LOG_ERROR, @@ -1047,18 +1149,23 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { IB_MCR_COMPMASK_SL | IB_MCR_COMPMASK_FLOW | IB_MCR_COMPMASK_JOIN_STATE | - IB_MCR_COMPMASK_TCLASS | /* all above are required */ + IB_MCR_COMPMASK_TCLASS | /* all above are required */ IB_MCR_COMPMASK_RATE_SEL | IB_MCR_COMPMASK_RATE; + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmt_run_mcast_flow: " EXPECTING_ERRORS_START "\n" ); status = osmt_send_mcast_request( p_osmt, 1, &mc_req_rec, comp_mask, &res_sa_mad ); + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmt_run_mcast_flow: " EXPECTING_ERRORS_END "\n" ); + if (status != IB_REMOTE_ERROR || res_sa_mad.status != IB_SA_MAD_STATUS_REQ_INVALID) { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: ERR 02ab: " + "osmt_run_mcast_flow: ERR 02AB: " "Expected REMOTE ERROR IB_SA_MAD_STATUS_REQ_INVALID got:%s/%s\n", ib_get_err_str( status ), ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) ) @@ -1070,7 +1177,8 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { /* Checking above max value of MTU which is impossible */ osm_log( &p_osmt->log, OSM_LOG_INFO, "osmt_run_mcast_flow: " - "Checking Join with unrealistic mtu (o15.0.1.8)...\n" + "Checking Join with unrealistic mtu : \n\t\tmore than 4096 -" + " max (o15.0.1.8)...\n" ); /* impossible requested mtu */ @@ -1084,17 +1192,23 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { IB_MCR_COMPMASK_SL | IB_MCR_COMPMASK_FLOW | IB_MCR_COMPMASK_JOIN_STATE | - IB_MCR_COMPMASK_TCLASS | /* all above are required */ + IB_MCR_COMPMASK_TCLASS | /* all above are required */ IB_MCR_COMPMASK_MTU_SEL | IB_MCR_COMPMASK_MTU; + + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmt_run_mcast_flow: " EXPECTING_ERRORS_START "\n" ); status = osmt_send_mcast_request( p_osmt, 1, &mc_req_rec, comp_mask, &res_sa_mad ); + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmt_run_mcast_flow: " EXPECTING_ERRORS_END "\n" ); + if (status != IB_REMOTE_ERROR || res_sa_mad.status != IB_SA_MAD_STATUS_REQ_INVALID) { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: ERR 02ac: " + "osmt_run_mcast_flow: ERR 02AC: " "Expected REMOTE ERROR IB_SA_MAD_STATUS_REQ_INVALID got:%s/%s\n", ib_get_err_str( status ), ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) ) @@ -1103,11 +1217,7 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { goto Exit; } - osm_log( &p_osmt->log, OSM_LOG_INFO, - "osmt_run_mcast_flow: " - "Checking Join with unrealistic mtu (o15.0.1.8)...\n" - ); -/* Checking above max value of MTU which is impossible */ + /* Checking below min value of MTU which is impossible */ osm_log( &p_osmt->log, OSM_LOG_INFO, "osmt_run_mcast_flow: " "Checking Join with unrealistic mtu : \n\t\tless than 256 -" @@ -1125,18 +1235,23 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { IB_MCR_COMPMASK_SL | IB_MCR_COMPMASK_FLOW | IB_MCR_COMPMASK_JOIN_STATE | - IB_MCR_COMPMASK_TCLASS | /* all above are required */ + IB_MCR_COMPMASK_TCLASS | /* all above are required */ IB_MCR_COMPMASK_MTU_SEL | IB_MCR_COMPMASK_MTU; + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmt_run_mcast_flow: " EXPECTING_ERRORS_START "\n" ); status = osmt_send_mcast_request( p_osmt, 1, &mc_req_rec, comp_mask, &res_sa_mad ); + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmt_run_mcast_flow: " EXPECTING_ERRORS_END "\n" ); + if (status != IB_REMOTE_ERROR || res_sa_mad.status != IB_SA_MAD_STATUS_REQ_INVALID) { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: ERR 02ad: " + "osmt_run_mcast_flow: ERR 02AD: " "Expected REMOTE ERROR IB_SA_MAD_STATUS_REQ_INVALID got:%s/%s\n", ib_get_err_str( status ), ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) ) @@ -1161,18 +1276,23 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { IB_MCR_COMPMASK_SL | IB_MCR_COMPMASK_FLOW | IB_MCR_COMPMASK_JOIN_STATE | - IB_MCR_COMPMASK_TCLASS | /* all above are required */ + IB_MCR_COMPMASK_TCLASS | /* all above are required */ IB_MCR_COMPMASK_MTU_SEL | IB_MCR_COMPMASK_MTU; + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmt_run_mcast_flow: " EXPECTING_ERRORS_START "\n" ); status = osmt_send_mcast_request( p_osmt, 1, &mc_req_rec, comp_mask, &res_sa_mad ); + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmt_run_mcast_flow: " EXPECTING_ERRORS_END "\n" ); + if (status != IB_REMOTE_ERROR || res_sa_mad.status != IB_SA_MAD_STATUS_REQ_INVALID) { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: ERR 02ae: " + "osmt_run_mcast_flow: ERR 02AE: " "Expected REMOTE ERROR IB_SA_MAD_STATUS_REQ_INVALID got:%s/%s\n", ib_get_err_str( status ), ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) ) @@ -1200,18 +1320,23 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { IB_MCR_COMPMASK_SL | IB_MCR_COMPMASK_FLOW | IB_MCR_COMPMASK_JOIN_STATE | - IB_MCR_COMPMASK_TCLASS | /* all above are required */ + IB_MCR_COMPMASK_TCLASS | /* all above are required */ IB_MCR_COMPMASK_LIFE | IB_MCR_COMPMASK_LIFE_SEL; + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmt_run_mcast_flow: " EXPECTING_ERRORS_START "\n" ); status = osmt_send_mcast_request( p_osmt, 1, &mc_req_rec, comp_mask, &res_sa_mad ); + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmt_run_mcast_flow: " EXPECTING_ERRORS_END "\n" ); + if (status != IB_REMOTE_ERROR || res_sa_mad.status != IB_SA_MAD_STATUS_REQ_INVALID) { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: ERR 02af: " + "osmt_run_mcast_flow: ERR 02AF: " "Expected REMOTE ERROR IB_SA_MAD_STATUS_REQ_INVALID got:%s/%s\n", ib_get_err_str( status ), ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) ) @@ -1221,25 +1346,21 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { } #endif - /* o15.0.1.4: */ - /* - Create an MGID by asking for a join with MGID = 0 */ - /* providing P_Key, Q_Key, SL, FlowLabel, Tclass. */ + /* o15.0.1.4: */ + /* - Create an MGID by asking for a join with MGID = 0 */ + /* providing P_Key, Q_Key, SL, FlowLabel, Tclass. */ osm_log( &p_osmt->log, OSM_LOG_INFO, "osmt_run_mcast_flow: " "Checking Create given MGID=0 skip service level (o15.0.1.4)...\n" ); - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: " - " Expecting Errors: ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^\n" - ); osmt_init_mc_query_rec(p_osmt, &mc_req_rec); p_mc_res = ib_sa_mad_get_payload_ptr(&res_sa_mad); /* no MGID */ - cl_memclr(&mc_req_rec.mgid,sizeof(ib_gid_t)); + memset(&mc_req_rec.mgid, 0, sizeof(ib_gid_t)); /* Request Join */ ib_member_set_join_state(&mc_req_rec, IB_MC_REC_STATE_FULL_MEMBER); @@ -1251,24 +1372,24 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { /* IB_MCR_COMPMASK_SL | Intentionally missed */ IB_MCR_COMPMASK_FLOW | IB_MCR_COMPMASK_JOIN_STATE | - IB_MCR_COMPMASK_TCLASS | /* all above are required */ + IB_MCR_COMPMASK_TCLASS | /* all above are required */ IB_MCR_COMPMASK_RATE_SEL | IB_MCR_COMPMASK_RATE; + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmt_run_mcast_flow: " EXPECTING_ERRORS_START "\n" ); status = osmt_send_mcast_request( p_osmt, 1, &mc_req_rec, comp_mask, &res_sa_mad ); osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: " - " Expected Errors: vvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvv\n" - ); + "osmt_run_mcast_flow: " EXPECTING_ERRORS_END "\n" ); if (status != IB_REMOTE_ERROR || (( ib_net16_t ) (res_sa_mad.status & IB_SMP_STATUS_MASK )) != IB_SA_MAD_STATUS_INSUF_COMPS) { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: ERR 02ag: " + "osmt_run_mcast_flow: ERR 02A8: " "Expected REMOTE ERROR IB_SA_MAD_STATUS_INSUF_COMPS got:%s/%s\n", ib_get_err_str( status ), ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) ) @@ -1283,7 +1404,7 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { if (status != IB_SUCCESS) { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: ERR 02aa: " + "osmt_run_mcast_flow: ERR 02AA: " "Could not get all MC Records in subnet, got:%s/%s\n", ib_get_err_str( status ), ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) ) @@ -1312,47 +1433,41 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { "Checking Create given MGID=0 skip Qkey and Pkey (o15.0.1.4)...\n" ); - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: " - " Expecting Errors: ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^\n" - ); - osmt_init_mc_query_rec(p_osmt, &mc_req_rec); p_mc_res = ib_sa_mad_get_payload_ptr(&res_sa_mad); /* no MGID */ - cl_memclr(&mc_req_rec.mgid,sizeof(ib_gid_t)); + memset(&mc_req_rec.mgid, 0, sizeof(ib_gid_t)); /* Request Join */ ib_member_set_join_state(&mc_req_rec, IB_MC_REC_STATE_FULL_MEMBER); comp_mask = IB_MCR_COMPMASK_MGID | IB_MCR_COMPMASK_PORT_GID | - /* IB_MCR_COMPMASK_QKEY | */ + /* IB_MCR_COMPMASK_QKEY | */ /* IB_MCR_COMPMASK_PKEY | Intentionally missed */ IB_MCR_COMPMASK_SL | IB_MCR_COMPMASK_FLOW | IB_MCR_COMPMASK_JOIN_STATE | - IB_MCR_COMPMASK_TCLASS | /* all above are required */ + IB_MCR_COMPMASK_TCLASS | /* all above are required */ IB_MCR_COMPMASK_RATE_SEL | IB_MCR_COMPMASK_RATE; + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmt_run_mcast_flow: " EXPECTING_ERRORS_START "\n" ); status = osmt_send_mcast_request( p_osmt, 1, &mc_req_rec, comp_mask, &res_sa_mad ); - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: " - " Expected Errors: vvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvv\n" - ); + "osmt_run_mcast_flow: " EXPECTING_ERRORS_END "\n" ); if (status != IB_REMOTE_ERROR || (( ib_net16_t ) (res_sa_mad.status & IB_SMP_STATUS_MASK )) != IB_SA_MAD_STATUS_INSUF_COMPS) { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: ERR 02ai: " + "osmt_run_mcast_flow: ERR 02A7: " "Expected REMOTE ERROR IB_SA_MAD_STATUS_INSUF_COMPS got:%s/%s\n", ib_get_err_str( status ), ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) ) @@ -1369,17 +1484,13 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { "osmt_run_mcast_flow: " "Checking Create given MGID=0 skip TClass (o15.0.1.4)...\n" ); - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: " - " Expecting Errors: ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^\n" - ); osmt_init_mc_query_rec(p_osmt, &mc_req_rec); p_mc_res = ib_sa_mad_get_payload_ptr(&res_sa_mad); /* no MGID */ - cl_memclr(&mc_req_rec.mgid,sizeof(ib_gid_t)); + memset(&mc_req_rec.mgid, 0, sizeof(ib_gid_t)); /* Request Join */ ib_member_set_join_state(&mc_req_rec, IB_MC_REC_STATE_FULL_MEMBER); @@ -1391,26 +1502,25 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { IB_MCR_COMPMASK_SL | IB_MCR_COMPMASK_FLOW | IB_MCR_COMPMASK_JOIN_STATE | - /* IB_MCR_COMPMASK_TCLASS | Intentionally missed */ - /* all above are required */ + /* IB_MCR_COMPMASK_TCLASS | Intentionally missed */ + /* all above are required */ IB_MCR_COMPMASK_RATE_SEL | IB_MCR_COMPMASK_RATE; + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmt_run_mcast_flow: " EXPECTING_ERRORS_START "\n" ); status = osmt_send_mcast_request( p_osmt, 1, &mc_req_rec, comp_mask, &res_sa_mad ); - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: " - " Expected Errors: vvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvv\n" - ); + "osmt_run_mcast_flow: " EXPECTING_ERRORS_END "\n" ); if (status != IB_REMOTE_ERROR || (( ib_net16_t ) (res_sa_mad.status & IB_SMP_STATUS_MASK )) != IB_SA_MAD_STATUS_INSUF_COMPS) { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: ERR 02aj: " + "osmt_run_mcast_flow: ERR 02A6: " "Expected REMOTE ERROR IB_SA_MAD_STATUS_INSUF_COMPS got:%s/%s\n", ib_get_err_str( status ), ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) ) @@ -1442,7 +1552,7 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { IB_MCR_COMPMASK_SL | IB_MCR_COMPMASK_FLOW | IB_MCR_COMPMASK_JOIN_STATE | - IB_MCR_COMPMASK_TCLASS | /* all above are required */ + IB_MCR_COMPMASK_TCLASS | /* all above are required */ IB_MCR_COMPMASK_RATE_SEL | IB_MCR_COMPMASK_RATE; @@ -1453,8 +1563,8 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { if (status != IB_SUCCESS) { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: ERR 02ak: " - "Failed to create MCG for MGID=0 with higher than minimum RATE\n", + "osmt_run_mcast_flow: ERR 02A5: " + "Failed to create MCG for MGID=0 with higher than minimum RATE - got %s/%s\n", ib_get_err_str( status ), ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) ) ); @@ -1487,7 +1597,7 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { IB_MCR_COMPMASK_SL | IB_MCR_COMPMASK_FLOW | IB_MCR_COMPMASK_JOIN_STATE | - IB_MCR_COMPMASK_TCLASS | /* all above are required */ + IB_MCR_COMPMASK_TCLASS | /* all above are required */ IB_MCR_COMPMASK_RATE_SEL | IB_MCR_COMPMASK_RATE; @@ -1498,8 +1608,8 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { if (status != IB_SUCCESS) { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: ERR 021: " - "Failed to create MCG for MGID=0 with less than highest RATE\n", + "osmt_run_mcast_flow: ERR 0211: " + "Failed to create MCG for MGID=0 with less than highest RATE - got %s/%s\n", ib_get_err_str( status ), ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) ) ); @@ -1523,7 +1633,6 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { mc_req_rec.mtu = IB_MTU_LEN_4096 | IB_PATH_SELECTOR_LESS_THAN << 6; - comp_mask = IB_MCR_COMPMASK_MGID | IB_MCR_COMPMASK_PORT_GID | @@ -1532,7 +1641,7 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { IB_MCR_COMPMASK_SL | IB_MCR_COMPMASK_FLOW | IB_MCR_COMPMASK_JOIN_STATE | - IB_MCR_COMPMASK_TCLASS | /* all above are required */ + IB_MCR_COMPMASK_TCLASS | /* all above are required */ IB_MCR_COMPMASK_MTU_SEL | IB_MCR_COMPMASK_MTU; @@ -1544,7 +1653,7 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { { osm_log( &p_osmt->log, OSM_LOG_ERROR, "osmt_run_mcast_flow: ERR 0238: " - "Failed to create MCG for MGID=0 with less than highest MTU\n", + "Failed to create MCG for MGID=0 with less than highest MTU - got %s/%s\n", ib_get_err_str( status ), ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) ) ); @@ -1563,7 +1672,7 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { cl_map_insert(&test_created_mlids, cl_ntoh16(p_recvd_rec->mlid), p_recvd_rec ); - /* Good Flow - mgid is 0 while giving all required fields for join : P_Key, Q_Key, SL, FlowLabel, Tclass */ + /* Good Flow - mgid is 0 while giving all required fields for join : P_Key, Q_Key, SL, FlowLabel, Tclass */ mc_req_rec.mtu = IB_MTU_LEN_256 | IB_PATH_SELECTOR_GREATER_THAN << 6; @@ -1575,7 +1684,7 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { IB_MCR_COMPMASK_SL | IB_MCR_COMPMASK_FLOW | IB_MCR_COMPMASK_JOIN_STATE | - IB_MCR_COMPMASK_TCLASS | /* all above are required */ + IB_MCR_COMPMASK_TCLASS | /* all above are required */ IB_MCR_COMPMASK_MTU_SEL | IB_MCR_COMPMASK_MTU; @@ -1587,7 +1696,7 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { { osm_log( &p_osmt->log, OSM_LOG_ERROR, "osmt_run_mcast_flow: ERR 0239: " - "Failed to create MCG for MGID=0 with higher than lowest MTU\n", + "Failed to create MCG for MGID=0 with higher than lowest MTU - got %s/%s\n", ib_get_err_str( status ), ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) ) ); @@ -1603,11 +1712,17 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { cl_ntoh64( p_recvd_rec->mgid.unicast.prefix ), cl_ntoh64( p_recvd_rec->mgid.unicast.interface_id ), cl_ntoh16( p_recvd_rec->mlid )); - cl_map_insert(&test_created_mlids, - cl_ntoh16(p_recvd_rec->mlid), p_recvd_rec ); + cl_map_insert( &test_created_mlids, + cl_ntoh16(p_recvd_rec->mlid), p_recvd_rec ); - /* Good Flow - mgid is 0 while giving all required fields for join : P_Key, Q_Key, SL, FlowLabel, Tclass */ - /* Using Exact feasible MTU & RATE */ + /* Good Flow - mgid is 0 while giving all required fields for join : P_Key, Q_Key, SL, FlowLabel, Tclass */ + /* Using Exact feasible MTU & RATE */ + + osm_log( &p_osmt->log, OSM_LOG_VERBOSE, + "osmt_run_mcast_flow: " + "Using Exact feasible MTU & RATE: " + "MTU = 0x%02X, RATE = 0x%02X\n", + mtu_phys, rate_phys ); mc_req_rec.mtu = mtu_phys; mc_req_rec.rate = rate_phys; @@ -1620,7 +1735,7 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { IB_MCR_COMPMASK_SL | IB_MCR_COMPMASK_FLOW | IB_MCR_COMPMASK_JOIN_STATE | - IB_MCR_COMPMASK_TCLASS | /* all above are required */ + IB_MCR_COMPMASK_TCLASS | /* all above are required */ IB_MCR_COMPMASK_MTU_SEL | IB_MCR_COMPMASK_MTU | IB_MCR_COMPMASK_RATE_SEL | @@ -1635,7 +1750,7 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { { osm_log( &p_osmt->log, OSM_LOG_ERROR, "osmt_run_mcast_flow: ERR 0240: " - "Failed to create MCG for MGID=0 with exact MTU & RATE\n", + "Failed to create MCG for MGID=0 with exact MTU & RATE - got %s/%s\n", ib_get_err_str( status ), ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) ) ); @@ -1654,8 +1769,13 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { cl_map_insert(&test_created_mlids, cl_ntoh16(p_recvd_rec->mlid), p_recvd_rec ); - /* Good Flow - mgid is 0 while giving all required fields for join : P_Key, Q_Key, SL, FlowLabel, Tclass */ - /* Using Exact feasible RATE */ + /* Good Flow - mgid is 0 while giving all required fields for join : P_Key, Q_Key, SL, FlowLabel, Tclass */ + /* Using Exact feasible RATE */ + + osm_log( &p_osmt->log, OSM_LOG_VERBOSE, + "osmt_run_mcast_flow: " + "Using Exact feasible RATE: 0x%02X\n", + rate_phys ); mc_req_rec.rate = rate_phys; @@ -1667,7 +1787,7 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { IB_MCR_COMPMASK_SL | IB_MCR_COMPMASK_FLOW | IB_MCR_COMPMASK_JOIN_STATE | - IB_MCR_COMPMASK_TCLASS | /* all above are required */ + IB_MCR_COMPMASK_TCLASS | /* all above are required */ IB_MCR_COMPMASK_RATE_SEL | IB_MCR_COMPMASK_RATE; @@ -1679,7 +1799,7 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { { osm_log( &p_osmt->log, OSM_LOG_ERROR, "osmt_run_mcast_flow: ERR 0241: " - "Failed to create MCG for MGID=0 with exact RATE\n", + "Failed to create MCG for MGID=0 with exact RATE - got %s/%s\n", ib_get_err_str( status ), ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) ) ); @@ -1695,12 +1815,17 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { cl_ntoh64( p_recvd_rec->mgid.unicast.prefix ), cl_ntoh64( p_recvd_rec->mgid.unicast.interface_id ), cl_ntoh16( p_recvd_rec->mlid )); - cl_map_insert(&test_created_mlids, - cl_ntoh16(p_recvd_rec->mlid), p_recvd_rec ); + cl_map_insert(&test_created_mlids, + cl_ntoh16(p_recvd_rec->mlid), p_recvd_rec ); /* Good Flow - mgid is 0 while giving all required fields for join : P_Key, Q_Key, SL, FlowLabel, Tclass */ /* Using Exact feasible MTU */ + osm_log( &p_osmt->log, OSM_LOG_VERBOSE, + "osmt_run_mcast_flow: " + "Using Exact feasible MTU: 0x%02X\n", + mtu_phys ); + mc_req_rec.mtu = mtu_phys; comp_mask = @@ -1711,7 +1836,7 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { IB_MCR_COMPMASK_SL | IB_MCR_COMPMASK_FLOW | IB_MCR_COMPMASK_JOIN_STATE | - IB_MCR_COMPMASK_TCLASS | /* all above are required */ + IB_MCR_COMPMASK_TCLASS | /* all above are required */ IB_MCR_COMPMASK_MTU_SEL | IB_MCR_COMPMASK_MTU; @@ -1723,7 +1848,7 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { { osm_log( &p_osmt->log, OSM_LOG_ERROR, "osmt_run_mcast_flow: ERR 0242: " - "Failed to create MCG for MGID=0 with exact MTU\n", + "Failed to create MCG for MGID=0 with exact MTU - got %s/%s\n", ib_get_err_str( status ), ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) ) ); @@ -1742,8 +1867,8 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { cl_map_insert(&test_created_mlids, cl_ntoh16(p_recvd_rec->mlid), p_recvd_rec ); - /* o15.0.1.5: */ - /* - Check the returned MGID is valid. (p 804) */ + /* o15.0.1.5: */ + /* - Check the returned MGID is valid. (p 804) */ osm_log( &p_osmt->log, OSM_LOG_INFO, "osmt_run_mcast_flow: " "Validating resulting MGID (o15.0.1.5)...\n" @@ -1758,26 +1883,29 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { { osm_log( &p_osmt->log, OSM_LOG_ERROR, "osmt_run_mcast_flow: ERR 0209: " - "Validating MGID failed. MGID:0x%016" PRIx64 "\n", - p_mc_res->mgid + "Validating MGID failed. MGID:0x%016" PRIx64 ":%016" PRIx64 "\n", + cl_ntoh64( p_mc_res->mgid.unicast.prefix ), + cl_ntoh64( p_mc_res->mgid.unicast.interface_id ) ); status = IB_ERROR; goto Exit; } - /* Lets try another multicast request */ + /* Good Flow - mgid is 0 while giving all required fields for join : P_Key, Q_Key, SL, FlowLabel, Tclass */ + /* Using feasible GREATER_THAN 0 packet lifitime */ osm_log( &p_osmt->log, OSM_LOG_INFO, "osmt_run_mcast_flow: " "Checking Create given MGID=0 (o15.0.1.4)...\n" ); - status = osmt_query_mcast( p_osmt); + + status = osmt_query_mcast(p_osmt); osmt_init_mc_query_rec(p_osmt, &mc_req_rec); p_mc_res = ib_sa_mad_get_payload_ptr(&res_sa_mad); /* no MGID */ - cl_memclr(&mc_req_rec.mgid,sizeof(ib_gid_t)); + memset(&mc_req_rec.mgid, 0, sizeof(ib_gid_t)); /* Request Join */ ib_member_set_join_state(&mc_req_rec, IB_MC_REC_STATE_FULL_MEMBER); @@ -1791,7 +1919,7 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { IB_MCR_COMPMASK_SL | IB_MCR_COMPMASK_FLOW | IB_MCR_COMPMASK_JOIN_STATE | - IB_MCR_COMPMASK_TCLASS | /* all above are required */ + IB_MCR_COMPMASK_TCLASS | /* all above are required */ IB_MCR_COMPMASK_LIFE | IB_MCR_COMPMASK_LIFE_SEL; @@ -1804,7 +1932,7 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { { osm_log( &p_osmt->log, OSM_LOG_ERROR, "osmt_run_mcast_flow: ERR 0210: " - "Failed to create MCG for MGID=0\n", + "Failed to create MCG for MGID=0 - got %s/%s\n", ib_get_err_str( status ), ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) ) ); @@ -1823,16 +1951,56 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { cl_map_insert(&test_created_mlids, cl_ntoh16(p_recvd_rec->mlid), p_recvd_rec ); - /* o15.0.1.6: */ - /* - Create a new MCG with valid requested MGID. */ + /* o15.0.1.6: */ + /* - Create a new MCG with valid requested MGID. */ + osmt_init_mc_query_rec(p_osmt, &mc_req_rec); + mc_req_rec.mgid = good_mgid; osm_log( &p_osmt->log, OSM_LOG_INFO, "osmt_run_mcast_flow: " - "Checking Create given MGID=0x%016" PRIx64 " : " + "Checking Create given valid MGID=0x%016" PRIx64 " : " + "0x%016" PRIx64 " (o15.0.1.6)...\n", + cl_ntoh64(mc_req_rec.mgid.unicast.prefix), + cl_ntoh64(mc_req_rec.mgid.unicast.interface_id)); + + /* Before creation, need to check that this group doesn't exist */ + osm_log( &p_osmt->log, OSM_LOG_INFO, + "osmt_run_mcast_flow: " + "Verifying that MCGroup with this MGID doesn't exist by trying to Join it (o15.0.1.13)...\n" ); + + ib_member_set_join_state(&mc_req_rec, IB_MC_REC_STATE_NON_MEMBER); + + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmt_run_mcast_flow: " EXPECTING_ERRORS_START "\n" ); + status = osmt_send_mcast_request( p_osmt, 1, /* join */ + &mc_req_rec, + comp_mask, + &res_sa_mad ); + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmt_run_mcast_flow: " EXPECTING_ERRORS_END "\n" ); + + if ((status != IB_REMOTE_ERROR) || + (res_sa_mad.status != IB_SA_MAD_STATUS_REQ_INVALID)) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmt_run_mcast_flow: ERR 0301: " + "Tried joining group that shouldn't have existed - got %s/%s\n", + ib_get_err_str( status ), + ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) ) + ); + status = IB_ERROR; + goto Exit; + } + + /* Set State to full member to allow group creation */ + ib_member_set_join_state(&mc_req_rec, IB_MC_REC_STATE_FULL_MEMBER); + + osm_log( &p_osmt->log, OSM_LOG_INFO, + "osmt_run_mcast_flow: " + "Now creating group with given valid MGID=0x%016" PRIx64 " : " "0x%016" PRIx64 " (o15.0.1.6)...\n", cl_ntoh64(mc_req_rec.mgid.unicast.prefix), cl_ntoh64(mc_req_rec.mgid.unicast.interface_id)); - mc_req_rec.mgid = good_mgid; status = osmt_send_mcast_request( p_osmt, 1, &mc_req_rec, @@ -1843,11 +2011,11 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { osm_log( &p_osmt->log, OSM_LOG_ERROR, "osmt_run_mcast_flow: ERR 0211: " "Failed to create MCG for MGID=0x%016" PRIx64 " : " - "0x%016" PRIx64 " (o15.0.1.6)...\n", - ib_get_err_str( status ), - ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad)), + "0x%016" PRIx64 " (o15.0.1.6) - got %s/%s\n", cl_ntoh64(good_mgid.unicast.prefix), - cl_ntoh64(good_mgid.unicast.interface_id)); + cl_ntoh64(good_mgid.unicast.interface_id), + ib_get_err_str( status ), + ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad)) ); goto Exit; } @@ -1869,44 +2037,42 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { ); /* prefix 0xFF1 Scope 0xA01B */ if ( (p_mc_res->mgid.multicast.header[0] != 0xFF) || - (p_mc_res->mgid.multicast.header[1] != 0x12) || /* HACK hardcoded scope = 0x02 */ + (p_mc_res->mgid.multicast.header[1] != 0x12) || /* HACK hardcoded scope = 0x02 */ (p_mc_res->mgid.multicast.raw_group_id[0] != 0xA0) || (p_mc_res->mgid.multicast.raw_group_id[1] != 0x1C) ) { osm_log( &p_osmt->log, OSM_LOG_ERROR, "osmt_run_mcast_flow: ERR 0212: " - "Validating MGID failed. MGID:0x%016" PRIx64 "\n", - p_mc_res->mgid + "Validating MGID failed. MGID:0x%016" PRIx64 ":%016" PRIx64 "\n", + cl_ntoh64( p_mc_res->mgid.unicast.prefix ), + cl_ntoh64( p_mc_res->mgid.unicast.interface_id ) ); status = IB_ERROR; goto Exit; } - /* - Try to create a new MCG with invalid MGID : get back ERR_REQ_INVALID */ + /* - Try to create a new MCG with invalid MGID : get back ERR_REQ_INVALID */ osm_log( &p_osmt->log, OSM_LOG_INFO, "osmt_run_mcast_flow: " "Checking BAD MGID=0xFA..... (o15.0.1.6)...\n" ); osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: " - " Expecting Errors: ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^\n" - ); + "osmt_run_mcast_flow: " EXPECTING_ERRORS_START "\n" ); + mc_req_rec.mgid.raw[0] = 0xFA; status = osmt_send_mcast_request( p_osmt, 1, &mc_req_rec, comp_mask, &res_sa_mad ); osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: " - " Expected Errors: vvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvv\n" - ); + "osmt_run_mcast_flow: " EXPECTING_ERRORS_END "\n" ); if ((status != IB_REMOTE_ERROR) || (res_sa_mad.status != IB_SA_MAD_STATUS_REQ_INVALID)) { osm_log( &p_osmt->log, OSM_LOG_ERROR, "osmt_run_mcast_flow: ERR 0213: " - "Failed to recognize MGID error for MGID=0xFA......\n", + "Failed to recognize MGID error for MGID=0xFA - got %s/%s\n", ib_get_err_str( status ), ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) ) ); @@ -1914,29 +2080,25 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { goto Exit; } - /* - Try again with MGID prefix = 0xA01B (maybe 0x1BA0 little or big ?) */ + /* - Try again with MGID prefix = 0xA01B (maybe 0x1BA0 little or big ?) */ osm_log( &p_osmt->log, OSM_LOG_INFO, "osmt_run_mcast_flow: " "Checking BAD MGID=0xFF12A01B..... with link-local scope (o15.0.1.6)...\n" ); - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: " - " Expecting Errors: ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^\n" - ); mc_req_rec.mgid.raw[0] = 0xFF; mc_req_rec.mgid.raw[3] = 0x1B; comp_mask = comp_mask | IB_MCR_COMPMASK_SCOPE; - mc_req_rec.scope_state = mc_req_rec.scope_state & 0x2F; /* local scope */ - + mc_req_rec.scope_state = mc_req_rec.scope_state & 0x2F; /* local scope */ + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmt_run_mcast_flow: " EXPECTING_ERRORS_START "\n" ); status = osmt_send_mcast_request( p_osmt, 1, &mc_req_rec, comp_mask, &res_sa_mad ); osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: " - " Expected Errors: vvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvv\n" - ); + "osmt_run_mcast_flow: " EXPECTING_ERRORS_END "\n" ); + if ((status != IB_REMOTE_ERROR) || (res_sa_mad.status != IB_SA_MAD_STATUS_REQ_INVALID)) { osm_log( &p_osmt->log, OSM_LOG_ERROR, @@ -1956,29 +2118,24 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { "Checking BAD MGID PREFIX=0xEF... (o15.0.1.6)...\n" ); - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: " - " Expecting Errors: ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^\n" - ); - - mc_req_rec.mgid = good_mgid; mc_req_rec.mgid.raw[0] = 0xEF; + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmt_run_mcast_flow: " EXPECTING_ERRORS_START "\n" ); status = osmt_send_mcast_request( p_osmt, 1, &mc_req_rec, comp_mask, &res_sa_mad ); osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: " - " Expected Errors: vvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvv\n" - ); + "osmt_run_mcast_flow: " EXPECTING_ERRORS_END "\n" ); + if ((status != IB_REMOTE_ERROR) || (res_sa_mad.status != IB_SA_MAD_STATUS_REQ_INVALID)) { osm_log( &p_osmt->log, OSM_LOG_ERROR, "osmt_run_mcast_flow: ERR 0215: " - "Failed to recognize MGID PREFIX error for MGID=0xEF....\n", + "Failed to recognize MGID PREFIX error for MGID=0xEF - got %s/%s\n", ib_get_err_str( status ), ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) ) ); @@ -2008,11 +2165,11 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { osm_log( &p_osmt->log, OSM_LOG_ERROR, "osmt_run_mcast_flow: ERR 0216: " "Failed to create MCG for MGID=0x%016" PRIx64 " : " - "0x%016" PRIx64 "\n", - ib_get_err_str( status ), - ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) ), + "0x%016" PRIx64 " - got %s/%s\n", cl_ntoh64(good_mgid.unicast.prefix), - cl_ntoh64(good_mgid.unicast.interface_id)); + cl_ntoh64(good_mgid.unicast.interface_id), + ib_get_err_str( status ), + ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) ) ); goto Exit; } @@ -2025,8 +2182,8 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { cl_ntoh64( p_recvd_rec->mgid.unicast.prefix ), cl_ntoh64( p_recvd_rec->mgid.unicast.interface_id ), cl_ntoh16( p_recvd_rec->mlid )); - cl_map_insert(&test_created_mlids, - cl_ntoh16(p_recvd_rec->mlid), p_recvd_rec ); + cl_map_insert(&test_created_mlids, + cl_ntoh16(p_recvd_rec->mlid), p_recvd_rec ); /* Change the flags to invalid value 0x2 - get back INVALID REQ */ @@ -2036,9 +2193,7 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { ); osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: " - " Expecting Errors: ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^\n" - ); + "osmt_run_mcast_flow: " EXPECTING_ERRORS_START "\n" ); mc_req_rec.mgid = good_mgid; @@ -2050,15 +2205,13 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { &res_sa_mad ); osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: " - " Expected Errors: vvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvv\n" - ); + "osmt_run_mcast_flow: " EXPECTING_ERRORS_END "\n" ); if ((status != IB_REMOTE_ERROR) || (res_sa_mad.status != IB_SA_MAD_STATUS_REQ_INVALID)) { osm_log( &p_osmt->log, OSM_LOG_ERROR, "osmt_run_mcast_flow: ERR 0217: " - "Failed to recognize create with invalid flags value 0x2\n", + "Failed to recognize create with invalid flags value 0x2 - got %s/%s\n", ib_get_err_str( status ), ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) ) ); @@ -2083,7 +2236,7 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { { osm_log( &p_osmt->log, OSM_LOG_ERROR, "osmt_run_mcast_flow: ERR 0218: " - "Failed to create MCG for MGID=0xFF02:0:0:0:0:0:0:1\n", + "Failed to create MCG for MGID=0xFF02:0:0:0:0:0:0:1 - got %s/%s\n", ib_get_err_str( status ), ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) ) ); @@ -2099,14 +2252,14 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { cl_ntoh64( p_recvd_rec->mgid.unicast.prefix ), cl_ntoh64( p_recvd_rec->mgid.unicast.interface_id ), cl_ntoh16( p_recvd_rec->mlid )); - cl_map_insert(&test_created_mlids, - cl_ntoh16(p_recvd_rec->mlid), p_recvd_rec ); + cl_map_insert(&test_created_mlids, + cl_ntoh16(p_recvd_rec->mlid), p_recvd_rec ); - /* o15.0.1.7 - implicitlly checked during the prev steps. */ - /* o15.0.1.8 - implicitlly checked during the prev steps. */ + /* o15.0.1.7 - implicitlly checked during the prev steps. */ + /* o15.0.1.8 - implicitlly checked during the prev steps. */ - /* o15.0.1.9 */ - /* - Create MCG with Invalid JoinState.FullMember != 1 : get ERR_REQ_INVALID */ + /* o15.0.1.9 */ + /* - Create MCG with Invalid JoinState.FullMember != 1 : get ERR_REQ_INVALID */ osm_log( &p_osmt->log, OSM_LOG_INFO, "osmt_run_mcast_flow: " @@ -2114,26 +2267,24 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { ); osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: " - " Expecting Errors: ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^\n" - ); + "osmt_run_mcast_flow: " EXPECTING_ERRORS_START "\n" ); + mc_req_rec.mgid = good_mgid; mc_req_rec.mgid.raw[12] = 0xFF; - mc_req_rec.scope_state = 0x22; /* link-local scope */ + mc_req_rec.scope_state = 0x22; /* link-local scope, non-member state */ status = osmt_send_mcast_request( p_osmt, 1, &mc_req_rec, comp_mask, &res_sa_mad ); osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: " - " Expected Errors: vvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvv\n" - ); + "osmt_run_mcast_flow: " EXPECTING_ERRORS_END "\n" ); + if ((status != IB_REMOTE_ERROR) || (res_sa_mad.status != IB_SA_MAD_STATUS_REQ_INVALID)) { osm_log( &p_osmt->log, OSM_LOG_ERROR, "osmt_run_mcast_flow: ERR 0219: " - "Failed to recognize create with JoinState != FullMember\n", + "Failed to recognize create with JoinState != FullMember - got %s/%s\n", ib_get_err_str( status ), ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) ) ); @@ -2148,7 +2299,7 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { ); mc_req_rec.mgid = good_mgid; - mc_req_rec.scope_state = 0x23; /* link-local scope, non member and full member */ + mc_req_rec.scope_state = 0x23; /* link-local scope, non member and full member */ status = osmt_send_mcast_request( p_osmt, 1, &mc_req_rec, @@ -2159,13 +2310,25 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { { osm_log( &p_osmt->log, OSM_LOG_ERROR, "osmt_run_mcast_flow: ERR 0220: " - "Failed to create MCG with valid join state 0x3\n", + "Failed to create MCG with valid join state 0x3 - got %s/%s\n", ib_get_err_str( status ), ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) ) ); goto Exit; } + /* Save the mlid created in test_created_mlids map */ + p_recvd_rec = (ib_member_rec_t*)ib_sa_mad_get_payload_ptr( &res_sa_mad ); + osm_log( &p_osmt->log, OSM_LOG_VERBOSE, + "osmt_run_mcast_flow: " + "Created MGID:0x%016" PRIx64 " : " + "0x%016" PRIx64 " MLID:0x%04X\n", + cl_ntoh64( p_recvd_rec->mgid.unicast.prefix ), + cl_ntoh64( p_recvd_rec->mgid.unicast.interface_id ), + cl_ntoh16( p_recvd_rec->mlid ) ); + cl_map_insert( &test_created_mlids, + cl_ntoh16(p_recvd_rec->mlid), p_recvd_rec ); + /* Lets try another invalid join scope state */ osm_log( &p_osmt->log, OSM_LOG_INFO, "osmt_run_mcast_flow: " @@ -2173,28 +2336,26 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { ); osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: " - " Expecting Errors: ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^\n" - ); + "osmt_run_mcast_flow: " EXPECTING_ERRORS_START "\n" ); + /* We have created a new MCG so now we need different mgid when cresting group otherwise it will be counted as join request .*/ mc_req_rec.mgid = good_mgid; mc_req_rec.mgid.raw[12] = 0xFC; - mc_req_rec.scope_state = 0x24; /* link-local scope, send only member */ + mc_req_rec.scope_state = 0x24; /* link-local scope, send only member */ status = osmt_send_mcast_request( p_osmt, 1, &mc_req_rec, comp_mask, &res_sa_mad ); osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: " - " Expected Errors: vvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvv\n" - ); + "osmt_run_mcast_flow: " EXPECTING_ERRORS_END "\n" ); + if ((status != IB_REMOTE_ERROR) || (res_sa_mad.status != IB_SA_MAD_STATUS_REQ_INVALID)) { osm_log( &p_osmt->log, OSM_LOG_ERROR, "osmt_run_mcast_flow: ERR 0221: " - "Failed to recognize create with JoinState != FullMember\n", + "Failed to recognize create with JoinState != FullMember - got %s/%s\n", ib_get_err_str( status ), ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) ) ); @@ -2205,13 +2366,13 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { /* Lets try another valid join scope state */ osm_log( &p_osmt->log, OSM_LOG_INFO, "osmt_run_mcast_flow: " - "Checking new MGID with valid join state (o15.0.1.9)...\n" + "Checking new MGID creation with valid join state (o15.0.1.9)...\n" ); mc_req_rec.mgid = good_mgid; mc_req_rec.mgid.raw[12] = 0xFB; - cl_memcpy(&special_mgid, &mc_req_rec.mgid, sizeof(ib_gid_t)); - mc_req_rec.scope_state = 0x2F; /* link-local scope, Full member with all other bits turned on */ + memcpy(&special_mgid, &mc_req_rec.mgid, sizeof(ib_gid_t)); + mc_req_rec.scope_state = 0x2F; /* link-local scope, Full member with all other bits turned on */ status = osmt_send_mcast_request( p_osmt, 1, &mc_req_rec, @@ -2222,7 +2383,7 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { { osm_log( &p_osmt->log, OSM_LOG_ERROR, "osmt_run_mcast_flow: ERR 0222: " - "Failed to create MCG with valid join state 0xF\n", + "Failed to create MCG with valid join state 0xF - got %s/%s\n", ib_get_err_str( status ), ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) ) ); @@ -2238,18 +2399,18 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { cl_ntoh64( p_recvd_rec->mgid.unicast.prefix ), cl_ntoh64( p_recvd_rec->mgid.unicast.interface_id ), cl_ntoh16( p_recvd_rec->mlid )); - cl_map_insert(&test_created_mlids, - cl_ntoh16(p_recvd_rec->mlid), p_recvd_rec ); + cl_map_insert(&test_created_mlids, + cl_ntoh16(p_recvd_rec->mlid), p_recvd_rec ); - /* o15.0.1.10 - can't check on a single client .-- obsolete - - checked by SilverStorm bug o15-0.2.4, never the less recheck */ + /* o15.0.1.10 - can't check on a single client .-- obsolete - + checked by SilverStorm bug o15-0.2.4, never the less recheck */ /* o15-0.2.4 - Check a join request to already created MCG */ p_mc_res = ib_sa_mad_get_payload_ptr(&res_sa_mad); osm_log( &p_osmt->log, OSM_LOG_INFO, "osmt_run_mcast_flow: " - "Check o15-0.2.4 statement...\n"); + "Check o15-0.2.4 statement...\n" ); /* Try to join */ - cl_memcpy(&mc_req_rec.mgid,&p_mc_res->mgid,sizeof(ib_gid_t)); + memcpy(&mc_req_rec.mgid,&p_mc_res->mgid,sizeof(ib_gid_t)); /* Request Join */ ib_member_set_join_state(&mc_req_rec, IB_MC_REC_STATE_NON_MEMBER); comp_mask = @@ -2257,29 +2418,29 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { IB_MCR_COMPMASK_PORT_GID | IB_MCR_COMPMASK_JOIN_STATE; - status = osmt_send_mcast_request( p_osmt, 0x1, /* User Defined query */ + status = osmt_send_mcast_request( p_osmt, 0x1, /* User Defined query */ &mc_req_rec, comp_mask, &res_sa_mad ); if (status != IB_SUCCESS) { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: ERR 02cc: " + "osmt_run_mcast_flow: ERR 02CC: " "Failed to join MCG with valid req, returned status = %s\n", ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) )); goto Exit; } - /* o15.0.1.11: */ - /* - Try to join into a MGID that exists with JoinState=SendOnlyMember - */ - /* see that it updates JoinState. What is the routing change? */ + /* o15.0.1.11: */ + /* - Try to join into a MGID that exists with JoinState=SendOnlyMember - */ + /* see that it updates JoinState. What is the routing change? */ osm_log( &p_osmt->log, OSM_LOG_INFO, "osmt_run_mcast_flow: " "Checking Retry of existing MGID - See JoinState update (o15.0.1.11)...\n" ); mc_req_rec.mgid = good_mgid; - mc_req_rec.scope_state = 0x22; /* link-local scope, send only member */ + mc_req_rec.scope_state = 0x22; /* link-local scope, send only member */ status = osmt_send_mcast_request( p_osmt, 1, &mc_req_rec, @@ -2288,8 +2449,8 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { if (status != IB_SUCCESS) { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: ERR 02cd: " - "Failed to update existing MGID\n", + "osmt_run_mcast_flow: ERR 02CD: " + "Failed to update existing MGID - got %s/%s\n", ib_get_err_str( status ), ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) ) ); @@ -2301,10 +2462,10 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { "Validating Join State update with NonMember (o15.0.1.11)...\n" ); - if (p_mc_res->scope_state != 0x23) /* scope is LSB */ + if (p_mc_res->scope_state != 0x23) /* scope is LSB */ { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: ERR 02ce: " + "osmt_run_mcast_flow: ERR 02CE: " "Validating JoinState update failed. Expected 0x23 got: 0x%02X\n", p_mc_res->scope_state ); @@ -2322,7 +2483,7 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { IB_LINK_WIDTH_ACTIVE_1X | IB_PATH_SELECTOR_GREATER_THAN << 6; mc_req_rec.mgid = good_mgid; - /* link-local scope, non member (so we should not be able to delete) */ + /* link-local scope, non member (so we should not be able to delete) */ /* but the FullMember bit should be gone */ osm_log( &p_osmt->log, OSM_LOG_INFO, "osmt_run_mcast_flow: " @@ -2336,7 +2497,7 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { if ((status != IB_SUCCESS) || (p_mc_res->scope_state != 0x21)) { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: ERR 02cf: " + "osmt_run_mcast_flow: ERR 02CF: " "Failed to partially update JoinState : %s/%s\n", ib_get_err_str( status ), ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) ) @@ -2345,9 +2506,9 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { goto Exit; } - /* So far delete succeffully state - Now change it*/ + /* So far successfully delete state - Now change it */ mc_req_rec.mgid = good_mgid; - mc_req_rec.scope_state = 0x24; /* link-local scope, send only member */ + mc_req_rec.scope_state = 0x24; /* link-local scope, send only member */ status = osmt_send_mcast_request( p_osmt, 1, &mc_req_rec, @@ -2356,8 +2517,8 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { if (status != IB_SUCCESS) { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: ERR 02cg: " - "Failed to update existing MCG\n", + "osmt_run_mcast_flow: ERR 02C0: " + "Failed to update existing MCG - got %s/%s\n", ib_get_err_str( status ), ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) ) ); @@ -2369,10 +2530,10 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { "Validating Join State update with Send Only Member (o15.0.1.11)...\n" ); - if (p_mc_res->scope_state != 0x25) /* scope is MSB */ + if (p_mc_res->scope_state != 0x25) /* scope is MSB */ { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: ERR 02ch: " + "osmt_run_mcast_flow: ERR 02C1: " "Validating JoinState update failed. Expected 0x25 got: 0x%02X\n", p_mc_res->scope_state ); @@ -2380,7 +2541,7 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { goto Exit; } /* Now try to update value of join state */ - mc_req_rec.scope_state = 0x21; /* link-local scope, full member */ + mc_req_rec.scope_state = 0x21; /* link-local scope, full member */ status = osmt_send_mcast_request( p_osmt, 1, &mc_req_rec, @@ -2389,8 +2550,8 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { if (status != IB_SUCCESS) { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: ERR 02ci: " - "Failed to update existing MGID\n", + "osmt_run_mcast_flow: ERR 02C2: " + "Failed to update existing MGID - got %s/%s\n", ib_get_err_str( status ), ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) ) ); @@ -2400,12 +2561,12 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { osm_log( &p_osmt->log, OSM_LOG_INFO, "osmt_run_mcast_flow: " "Validating Join State update with Full Member\n\t\t" - "to an existing 0x5 state MCG (o15.0.1.11)...\n"); + "to an existing 0x5 state MCG (o15.0.1.11)...\n" ); - if (p_mc_res->scope_state != 0x25) /* scope is LSB */ + if (p_mc_res->scope_state != 0x25) /* scope is LSB */ { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: ERR 02cj: " + "osmt_run_mcast_flow: ERR 02C3: " "Validating JoinState update failed. Expected 0x25 got: 0x%02X\n", p_mc_res->scope_state ); @@ -2414,7 +2575,7 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { } /* Now try to update value of join state */ - mc_req_rec.scope_state = 0x22; /* link-local scope,non member */ + mc_req_rec.scope_state = 0x22; /* link-local scope,non member */ status = osmt_send_mcast_request( p_osmt, 1, &mc_req_rec, @@ -2423,8 +2584,8 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { if (status != IB_SUCCESS) { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: ERR 02ck: " - "Failed to update existing MGID\n", + "osmt_run_mcast_flow: ERR 02C4: " + "Failed to update existing MGID - got %s/%s\n", ib_get_err_str( status ), ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) ) ); @@ -2433,12 +2594,12 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { osm_log( &p_osmt->log, OSM_LOG_INFO, "osmt_run_mcast_flow: " "Validating Join State update with Non Member\n\t\t" - "to an existing 0x5 state MCG (o15.0.1.11)...\n"); + "to an existing 0x5 state MCG (o15.0.1.11)...\n" ); - if (p_mc_res->scope_state != 0x27) /* scope is LSB */ + if (p_mc_res->scope_state != 0x27) /* scope is LSB */ { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: ERR 02cl: " + "osmt_run_mcast_flow: ERR 02C5: " "Validating JoinState update failed. Expected 0x27 got: 0x%02X\n", p_mc_res->scope_state ); @@ -2447,26 +2608,24 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { } osm_log( &p_osmt->log, OSM_LOG_VERBOSE, - "DEBUG - Current scope_state value : 0x%02X...\n", p_mc_res->scope_state); + "DEBUG - Current scope_state value : 0x%02X...\n", p_mc_res->scope_state ); - /* - We can not check simple join since we have only one tester (for now) */ + /* - We can not check simple join since we have only one tester (for now) */ - /* o15.0.1.12: Not Supported*/ - /* - The SendOnlyNonMem join should have a special treatment in the - SA but what is it ? */ + /* o15.0.1.12: Not Supported */ + /* - The SendOnlyNonMem join should have a special treatment in the + SA but what is it ? */ - /* o15.0.1.13: */ - /* - Try joining with rate that does not exist in any MCG - - ERR_REQ_INVALID */ + /* o15.0.1.13: */ + /* - Try joining with rate that does not exist in any MCG - + ERR_REQ_INVALID */ osm_log( &p_osmt->log, OSM_LOG_INFO, "osmt_run_mcast_flow: " "Checking BAD RATE when connecting to existing MGID (o15.0.1.13)...\n" ); osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: " - " Expecting Errors: ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^\\n" - ); + "osmt_run_mcast_flow: " EXPECTING_ERRORS_START "\n" ); mc_req_rec.mgid = good_mgid; mc_req_rec.rate = @@ -2480,7 +2639,7 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { IB_MCR_COMPMASK_SL | IB_MCR_COMPMASK_FLOW | IB_MCR_COMPMASK_JOIN_STATE | - IB_MCR_COMPMASK_TCLASS | /* all above are required */ + IB_MCR_COMPMASK_TCLASS | /* all above are required */ IB_MCR_COMPMASK_RATE_SEL | IB_MCR_COMPMASK_RATE; @@ -2489,13 +2648,12 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { comp_mask, &res_sa_mad ); osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: " - " Expected Errors: vvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvv\n" - ); + "osmt_run_mcast_flow: " EXPECTING_ERRORS_END "\n" ); + if ((status != IB_REMOTE_ERROR) || (res_sa_mad.status != IB_SA_MAD_STATUS_REQ_INVALID)) { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: ERR 02cm: " + "osmt_run_mcast_flow: ERR 02C6: " "Failed to catch BAD RATE joining an exiting MGID: %s/%s\n", ib_get_err_str( status ), ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) ) @@ -2511,9 +2669,7 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { "existing MGID (o15.0.1.13)...\n" ); osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: " - " Expecting Errors: ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^\n" - ); + "osmt_run_mcast_flow: " EXPECTING_ERRORS_START "\n" ); mc_req_rec.mgid = osm_ipoib_mgid; mc_req_rec.mtu = @@ -2527,7 +2683,7 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { IB_MCR_COMPMASK_SL | IB_MCR_COMPMASK_FLOW | IB_MCR_COMPMASK_JOIN_STATE | - IB_MCR_COMPMASK_TCLASS | /* all above are required */ + IB_MCR_COMPMASK_TCLASS | /* all above are required */ IB_MCR_COMPMASK_MTU_SEL | IB_MCR_COMPMASK_MTU; @@ -2536,13 +2692,12 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { comp_mask, &res_sa_mad ); osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: " - " Expected Errors: vvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvv\n" - ); + "osmt_run_mcast_flow: " EXPECTING_ERRORS_END "\n" ); + if ((status != IB_REMOTE_ERROR) || (res_sa_mad.status != IB_SA_MAD_STATUS_REQ_INVALID)) { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: ERR 02cn: " + "osmt_run_mcast_flow: ERR 02C7: " "Failed to catch BAD RATE (higher them max) joining an exiting MGID: %s/%s\n", ib_get_err_str( status ), ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) ) @@ -2558,9 +2713,7 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { "to existing MGID (o15.0.1.13)...\n" ); osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: " - " Expecting Errors: ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^\n" - ); + "osmt_run_mcast_flow: " EXPECTING_ERRORS_START "\n" ); mc_req_rec.mgid = osm_ipoib_mgid; mc_req_rec.mtu = @@ -2574,7 +2727,7 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { IB_MCR_COMPMASK_SL | IB_MCR_COMPMASK_FLOW | IB_MCR_COMPMASK_JOIN_STATE | - IB_MCR_COMPMASK_TCLASS | /* all above are required */ + IB_MCR_COMPMASK_TCLASS | /* all above are required */ IB_MCR_COMPMASK_MTU_SEL | IB_MCR_COMPMASK_MTU; @@ -2583,13 +2736,12 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { comp_mask, &res_sa_mad ); osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: " - " Expected Errors: vvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvv\n" - ); + "osmt_run_mcast_flow: " EXPECTING_ERRORS_END "\n" ); + if ((status != IB_REMOTE_ERROR) || (res_sa_mad.status != IB_SA_MAD_STATUS_REQ_INVALID)) { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: ERR 02co: " + "osmt_run_mcast_flow: ERR 02C8: " "Failed to catch BAD RATE (less them min) joining an exiting MGID: %s/%s\n", ib_get_err_str( status ), ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) ) @@ -2598,8 +2750,8 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { goto Exit; } - /* o15.0.1.14: */ - /* - Try partial delete - actually updating the join state. check it. */ + /* o15.0.1.14: */ + /* - Try partial delete - actually updating the join state. check it. */ osm_log( &p_osmt->log, OSM_LOG_INFO, "osmt_run_mcast_flow: " @@ -2618,11 +2770,11 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { IB_MCR_COMPMASK_SL | IB_MCR_COMPMASK_FLOW | IB_MCR_COMPMASK_JOIN_STATE | - IB_MCR_COMPMASK_TCLASS | /* all above are required */ + IB_MCR_COMPMASK_TCLASS | /* all above are required */ IB_MCR_COMPMASK_RATE_SEL | IB_MCR_COMPMASK_RATE; - /* link-local scope, non member (so we should not be able to delete) */ - /* but the FullMember bit should be gone */ + /* link-local scope, non member (so we should not be able to delete) */ + /* but the FullMember bit should be gone */ mc_req_rec.scope_state = 0x22; status = osmt_send_mcast_request( p_osmt, 0, @@ -2633,7 +2785,7 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { if (status != IB_SUCCESS) { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: ERR 02cp: " + "osmt_run_mcast_flow: ERR 02C9: " "Fail to partially update JoinState during delete: %s/%s\n", ib_get_err_str( status ), ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) ) @@ -2646,10 +2798,10 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { "osmt_run_mcast_flow: " "Validating Join State removal of Non Member bit (o15.0.1.14)...\n" ); - if (p_mc_res->scope_state != 0x25) /* scope is MSB - now only the non member & send only member have left */ + if (p_mc_res->scope_state != 0x25) /* scope is MSB - now only the non member & send only member have left */ { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: ERR 02cq: " + "osmt_run_mcast_flow: ERR 02CA: " "Validating JoinState update failed. Expected 0x25 got: 0x%02X\n", p_mc_res->scope_state ); @@ -2668,7 +2820,7 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { if (status != IB_SUCCESS) { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: ERR 02cr: " + "osmt_run_mcast_flow: ERR 02CB: " "Failed to update JoinState during delete: %s/%s\n", ib_get_err_str( status ), ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) ) @@ -2682,10 +2834,10 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { "Validating Join State update remove (o15.0.1.14)...\n" ); - if (p_mc_res->scope_state != 0x25) /* scope is MSB - now only 0x0 so port is removed from MCG */ + if (p_mc_res->scope_state != 0x25) /* scope is MSB - now only 0x0 so port is removed from MCG */ { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: ERR 02cs: " + "osmt_run_mcast_flow: ERR 02BF: " "Validating JoinState update failed. Expected 0x25 got: 0x%02X\n", p_mc_res->scope_state ); @@ -2693,28 +2845,27 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { goto Exit; } - /* - Try joining (not full mem) again to see the group was deleted. (should fail) */ + /* - Try joining (not full mem) again to see the group was deleted. (should fail) */ osm_log( &p_osmt->log, OSM_LOG_INFO, "osmt_run_mcast_flow: " - "Checking Delete by trying to Join deleted group (o15.0.1.14)...\n" + "Checking Delete by trying to Join deleted group (o15.0.1.13)...\n" ); + + mc_req_rec.scope_state = 0x22; /* use non member - so if no group fail */ + osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: " - " Expecting Errors: ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^\n" - ); - mc_req_rec.scope_state = 0x22; /* use non member - so if no group fail */ - status = osmt_send_mcast_request( p_osmt, 1, /* join */ + "osmt_run_mcast_flow: " EXPECTING_ERRORS_START "\n" ); + status = osmt_send_mcast_request( p_osmt, 1, /* join */ &mc_req_rec, comp_mask, &res_sa_mad ); osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: " - " Expected Errors: vvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvv\n" - ); + "osmt_run_mcast_flow: " EXPECTING_ERRORS_END "\n" ); + if (status != IB_REMOTE_ERROR) { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: ERR 02ct: " + "osmt_run_mcast_flow: ERR 02BC: " "Succeeded Joining Deleted Group: %s/%s\n", ib_get_err_str( status ), ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) ) @@ -2723,34 +2874,31 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { goto Exit; } - /* - Try deletion of the IPoIB MCG and get: ERR_REQ_INVALID */ + /* - Try deletion of the IPoIB MCG and get: ERR_REQ_INVALID */ osm_log( &p_osmt->log, OSM_LOG_INFO, "osmt_run_mcast_flow: " "Checking BAD Delete of Mgid membership (no prev join) (o15.0.1.15)...\n" ); osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: " - " Expecting Errors: ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^\n" - ); + "osmt_run_mcast_flow: " EXPECTING_ERRORS_START "\n" ); mc_req_rec.mgid = osm_ipoib_mgid; mc_req_rec.rate = IB_LINK_WIDTH_ACTIVE_1X | IB_PATH_SELECTOR_GREATER_THAN << 6; - mc_req_rec.scope_state = 0x21; /* delete full member */ + mc_req_rec.scope_state = 0x21; /* delete full member */ - status = osmt_send_mcast_request( p_osmt, 0, /* delete flag */ + status = osmt_send_mcast_request( p_osmt, 0, /* delete flag */ &mc_req_rec, comp_mask, &res_sa_mad ); osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: " - " Expected Errors: vvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvv\n" - ); + "osmt_run_mcast_flow: " EXPECTING_ERRORS_END "\n" ); + if ((status != IB_REMOTE_ERROR) || (res_sa_mad.status != IB_SA_MAD_STATUS_REQ_INVALID)) { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: ERR 02cu: " + "osmt_run_mcast_flow: ERR 02BD: " "Failed to catch BAD delete from IPoIB: %s/%s\n", ib_get_err_str( status ), ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) ) @@ -2765,12 +2913,12 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { "Checking Create given MGID=0x%016" PRIx64 " : " "0x%016" PRIx64 "\n\t\t(o15.0.1.4)...\n", cl_ntoh64(osm_ipoib_mgid.unicast.prefix), - cl_ntoh64(osm_ipoib_mgid.unicast.interface_id)); + cl_ntoh64(osm_ipoib_mgid.unicast.interface_id) ); mc_req_rec.mgid = good_mgid; mc_req_rec.mgid.raw[12] = 0xAA; mc_req_rec.pkt_life = 0 | IB_PATH_SELECTOR_GREATER_THAN << 6; - mc_req_rec.scope_state = 0x21;/* Full memeber */ + mc_req_rec.scope_state = 0x21; /* Full memeber */ comp_mask = IB_MCR_COMPMASK_GID | IB_MCR_COMPMASK_PORT_GID | @@ -2779,7 +2927,7 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { IB_MCR_COMPMASK_SL | IB_MCR_COMPMASK_FLOW | IB_MCR_COMPMASK_JOIN_STATE | - IB_MCR_COMPMASK_TCLASS | /* all above are required */ + IB_MCR_COMPMASK_TCLASS | /* all above are required */ IB_MCR_COMPMASK_LIFE | IB_MCR_COMPMASK_LIFE_SEL; @@ -2790,22 +2938,22 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { if (status != IB_SUCCESS) { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: ERR 02cv: " + "osmt_run_mcast_flow: ERR 02BE: " "Failed to create MCG for 0x%016" PRIx64 " : " - "0x%016" PRIx64 ".\n", - ib_get_err_str( status ), - ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) ), + "0x%016" PRIx64 " - got %s/%s\n", cl_ntoh64(good_mgid.unicast.prefix), - cl_ntoh64(good_mgid.unicast.interface_id)); + cl_ntoh64(good_mgid.unicast.interface_id), + ib_get_err_str( status ), + ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) ) ); goto Exit; } - /* - Try delete with valid join state */ + /* - Try delete with valid join state */ osm_log( &p_osmt->log, OSM_LOG_INFO, "osmt_run_mcast_flow: " "Checking Full Delete of a group (o15.0.1.14)...\n" ); - mc_req_rec.scope_state = 0x21; /* the FullMember is the current JoinState */ + mc_req_rec.scope_state = 0x21; /* the FullMember is the current JoinState */ status = osmt_send_mcast_request( p_osmt, 0, &mc_req_rec, comp_mask, @@ -2816,31 +2964,29 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { goto Exit; } - /* o15.0.1.15: */ - /* - Try deletion of the IPoIB MCG and get: ERR_REQ_INVALID */ + /* o15.0.1.15: */ + /* - Try deletion of the IPoIB MCG and get: ERR_REQ_INVALID */ osm_log( &p_osmt->log, OSM_LOG_INFO, "osmt_run_mcast_flow: " "Checking BAD Delete of IPoIB membership (no prev join) (o15.0.1.15)...\n" ); osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: " - " Expecting Errors: ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^\n" - ); + "osmt_run_mcast_flow: " EXPECTING_ERRORS_START "\n" ); mc_req_rec.mgid = osm_ipoib_mgid; mc_req_rec.rate = IB_LINK_WIDTH_ACTIVE_1X | IB_PATH_SELECTOR_GREATER_THAN << 6; - mc_req_rec.scope_state = 0x21; /* delete full member */ + mc_req_rec.scope_state = 0x21; /* delete full member */ - status = osmt_send_mcast_request( p_osmt, 0, /* delete flag */ + status = osmt_send_mcast_request( p_osmt, 0, /* delete flag */ &mc_req_rec, comp_mask, &res_sa_mad ); + osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: " - " Expected Errors: vvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvv\n" - ); + "osmt_run_mcast_flow: " EXPECTING_ERRORS_END "\n" ); + if ((status != IB_REMOTE_ERROR) || (res_sa_mad.status != IB_SA_MAD_STATUS_REQ_INVALID)) { osm_log( &p_osmt->log, OSM_LOG_ERROR, @@ -2866,7 +3012,7 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { /* First create new mgrp */ ib_member_set_join_state(&mc_req_rec, IB_MC_REC_STATE_FULL_MEMBER); mc_req_rec.mtu = IB_MTU_LEN_1024 | IB_PATH_SELECTOR_EXACTLY << 6; - cl_memclr(&mc_req_rec.mgid,sizeof(ib_gid_t)); + memset(&mc_req_rec.mgid, 0, sizeof(ib_gid_t)); comp_mask = IB_MCR_COMPMASK_MGID | IB_MCR_COMPMASK_PORT_GID | @@ -2875,7 +3021,7 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { IB_MCR_COMPMASK_SL | IB_MCR_COMPMASK_FLOW | IB_MCR_COMPMASK_JOIN_STATE | - IB_MCR_COMPMASK_TCLASS | /* all above are required */ + IB_MCR_COMPMASK_TCLASS | /* all above are required */ IB_MCR_COMPMASK_MTU_SEL | IB_MCR_COMPMASK_MTU; @@ -2887,22 +3033,17 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { if (status != IB_SUCCESS) { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: ERR 02eb: " - "Failed to create new mgrp\n"); + "osmt_run_mcast_flow: ERR 02EB: " + "Failed to create new mgrp\n" ); goto Exit; } - cl_memcpy(&tmp_mgid,&p_mc_res->mgid,sizeof(ib_gid_t)); + memcpy(&tmp_mgid,&p_mc_res->mgid,sizeof(ib_gid_t)); osm_dump_mc_record( &p_osmt->log, p_mc_res, OSM_LOG_INFO ); /* tmp_mtu = p_mc_res->mtu & 0x3F; */ - /* impossible requested mtu always greater than exist in MCG */ - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: " - " Expecting Errors: ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^\n" - ); mc_req_rec.mtu = IB_MTU_LEN_4096 | IB_PATH_SELECTOR_GREATER_THAN << 6; - cl_memcpy(&mc_req_rec.mgid,&tmp_mgid,sizeof(ib_gid_t)); + memcpy(&mc_req_rec.mgid,&tmp_mgid,sizeof(ib_gid_t)); ib_member_set_join_state(&mc_req_rec, IB_MC_REC_STATE_FULL_MEMBER); comp_mask = IB_MCR_COMPMASK_GID | @@ -2911,18 +3052,19 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { IB_MCR_COMPMASK_MTU_SEL | IB_MCR_COMPMASK_MTU; + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmt_run_mcast_flow: " EXPECTING_ERRORS_START "\n" ); status = osmt_send_mcast_request( p_osmt, 1, &mc_req_rec, comp_mask, &res_sa_mad ); osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: " - " Expected Errors: vvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvv\n" - ); + "osmt_run_mcast_flow: " EXPECTING_ERRORS_END "\n" ); + if (status == IB_SUCCESS) { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: ERR 02e4: " + "osmt_run_mcast_flow: ERR 02E4: " "Expected REMOTE ERROR got:%s/%s\n", ib_get_err_str( status ), ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) ) @@ -2931,12 +3073,12 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { goto Exit; } - /* - Try GetTable with PortGUID wildcarded and get back some groups. */ + /* - Try GetTable with PortGUID wildcarded and get back some groups. */ status = osmt_query_mcast( p_osmt); cnt = cl_qmap_count(&p_osmt->exp_subn.mgrp_mlid_tbl); osm_log( &p_osmt->log, OSM_LOG_INFO, "osmt_run_mcast_flow (Before checking Max MCG creation): " - "Number of MC Records found in SA DB is %d\n",cnt); + "Number of MC Records found in SA DB is %d\n", cnt ); /**************************************************************************/ /* Checking join on behalf of remote port gid */ @@ -2945,7 +3087,7 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { "Checking Proxy Join...\n" ); osmt_init_mc_query_rec(p_osmt, &mc_req_rec); - cl_memclr( &context, sizeof( context ) ); + memset( &context, 0, sizeof( context ) ); /* * Do a blocking query for all NodeRecords in the subnet. @@ -2956,7 +3098,7 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { if( status != IB_SUCCESS ) { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: ERR 02e5: " + "osmt_run_mcast_flow: ERR 02E5: " "osmtest_get_all_recs failed on getting all node records(%s)\n", ib_get_err_str( status ) ); goto Exit; @@ -2978,18 +3120,19 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { { osm_log( &p_osmt->log, OSM_LOG_VERBOSE, "osmt_run_mcast_flow: " - "current port_guid = 0x%" PRIx64 "\n", - cl_ntoh64(p_rec->node_info.port_guid)); + "remote port_guid = 0x%" PRIx64 "\n", + cl_ntoh64(p_rec->node_info.port_guid) ); remote_port_guid = p_rec->node_info.port_guid; i = num_recs; + break; } } if (remote_port_guid != 0x0) { ib_member_set_join_state(&mc_req_rec, IB_MC_REC_STATE_FULL_MEMBER); - cl_memclr(&mc_req_rec.mgid,sizeof(ib_gid_t)); + memset(&mc_req_rec.mgid, 0, sizeof(ib_gid_t)); mc_req_rec.port_gid.unicast.interface_id = remote_port_guid; comp_mask = IB_MCR_COMPMASK_MGID | @@ -2999,7 +3142,7 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { IB_MCR_COMPMASK_SL | IB_MCR_COMPMASK_FLOW | IB_MCR_COMPMASK_JOIN_STATE | - IB_MCR_COMPMASK_TCLASS; /* all above are required */ + IB_MCR_COMPMASK_TCLASS; /* all above are required */ status = osmt_send_mcast_request( p_osmt, 1, &mc_req_rec, @@ -3010,42 +3153,60 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { if (status != IB_SUCCESS) { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: ERR 02b4: " + "osmt_run_mcast_flow: ERR 02B4: " "Could not join on behalf of remote port 0x%016" PRIx64 " remote status: %s\n", cl_ntoh64(remote_port_guid), - ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) )); + ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) ) ); status = IB_ERROR; goto Exit; } p_mc_res = ib_sa_mad_get_payload_ptr(&res_sa_mad); - cl_memcpy(&proxy_mgid,&p_mc_res->mgid,sizeof(ib_gid_t)); + memcpy(&proxy_mgid,&p_mc_res->mgid,sizeof(ib_gid_t)); /* First try a bad deletion then good one */ + + osm_log( &p_osmt->log, OSM_LOG_INFO, + "osmt_run_mcast_flow: " + "Trying deletion of remote port with local port guid\n" ); + osmt_init_mc_query_rec(p_osmt, &mc_req_rec); ib_member_set_join_state(&mc_req_rec, IB_MC_REC_STATE_FULL_MEMBER); comp_mask = IB_MCR_COMPMASK_MGID | IB_MCR_COMPMASK_PORT_GID | IB_MCR_COMPMASK_JOIN_STATE; - status = osmt_send_mcast_request( p_osmt, 0, /* delete flag */ + + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmt_run_mcast_flow: " EXPECTING_ERRORS_START "\n" ); + + status = osmt_send_mcast_request( p_osmt, 0, /* delete flag */ &mc_req_rec, comp_mask, &res_sa_mad ); + + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmt_run_mcast_flow: " EXPECTING_ERRORS_END "\n" ); + if (status == IB_SUCCESS) { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: ERR 02a9: " + "osmt_run_mcast_flow: ERR 02A9: " "Successful deletion of remote port guid with local one MGID : " "0x%016" PRIx64 " : 0x%016" PRIx64 ", Got : %s/%s\n", cl_ntoh64(p_mgrp->mcmember_rec.mgid.unicast.prefix), cl_ntoh64(p_mgrp->mcmember_rec.mgid.unicast.interface_id), ib_get_err_str( status ), - ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) )); + ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) ) ); status = IB_ERROR; goto Exit; } + + osm_log( &p_osmt->log, OSM_LOG_INFO, + "osmt_run_mcast_flow: " + "Trying deletion of remote port with the right port guid\n" ); + osmt_init_mc_query_rec(p_osmt, &mc_req_rec); ib_member_set_join_state(&mc_req_rec, IB_MC_REC_STATE_FULL_MEMBER); mc_req_rec.mgid = proxy_mgid; @@ -3054,20 +3215,20 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { IB_MCR_COMPMASK_MGID | IB_MCR_COMPMASK_PORT_GID | IB_MCR_COMPMASK_JOIN_STATE; - status = osmt_send_mcast_request( p_osmt, 0, /* delete flag */ + status = osmt_send_mcast_request( p_osmt, 0, /* delete flag */ &mc_req_rec, comp_mask, &res_sa_mad ); if (status != IB_SUCCESS) { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: ERR 02b0: " + "osmt_run_mcast_flow: ERR 02B0: " "Failed to delete mgid with remote port guid MGID : " "0x%016" PRIx64 " : 0x%016" PRIx64 ", Got : %s/%s\n", cl_ntoh64(p_mgrp->mcmember_rec.mgid.unicast.prefix), cl_ntoh64(p_mgrp->mcmember_rec.mgid.unicast.interface_id), ib_get_err_str( status ), - ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) )); + ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) ) ); goto Exit; } } @@ -3075,17 +3236,17 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { { osm_log( &p_osmt->log, OSM_LOG_INFO, "osmt_run_mcast_flow: " - "Could not check proxy join since could not found remote port, different from local port\n"); + "Could not check proxy join since could not found remote port, different from local port\n" ); } - /* prepare init for next check */ osmt_init_mc_query_rec(p_osmt, &mc_req_rec); + /**************************************************************************/ if (p_osmt->opt.mmode > 2) { /* Check invalid Join with max mlid which is more than the - Mellanox switches support 0xC000+0x1000 = 0xd000 */ + Mellanox switches support 0xC000+0x1000 = 0xd000 */ osm_log( &p_osmt->log, OSM_LOG_INFO, "osmt_run_mcast_flow: " "Checking Creation of Maximum avaliable Groups (MulticastFDBCap)...\n" @@ -3094,6 +3255,7 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { while (tmp_mlid > 0 && !ReachedMlidLimit) { uint16_t cur_mlid = 0; + /* Request Set */ ib_member_set_join_state(&mc_req_rec, IB_MC_REC_STATE_FULL_MEMBER); /* Good Flow - mgid is 0 while giving all required fields for @@ -3103,7 +3265,7 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { IB_LINK_WIDTH_ACTIVE_1X | IB_PATH_SELECTOR_GREATER_THAN << 6; mc_req_rec.mlid = max_mlid; - cl_memclr(&mc_req_rec.mgid,sizeof(ib_gid_t)); + memset(&mc_req_rec.mgid, 0, sizeof(ib_gid_t)); comp_mask = IB_MCR_COMPMASK_MGID | IB_MCR_COMPMASK_PORT_GID | @@ -3112,7 +3274,7 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { IB_MCR_COMPMASK_SL | IB_MCR_COMPMASK_FLOW | IB_MCR_COMPMASK_JOIN_STATE | - IB_MCR_COMPMASK_TCLASS |/* all above are required */ + IB_MCR_COMPMASK_TCLASS | /* all above are required */ IB_MCR_COMPMASK_MLID; status = osmt_send_mcast_request( p_osmt, 1, &mc_req_rec, @@ -3129,7 +3291,7 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { osm_log( &p_osmt->log, OSM_LOG_ERROR, "osmt_run_mcast_flow : ERR 2E1 " "Successful Join with greater mlid than switches support (MulticastFDBCap) 0x%04X\n", - cur_mlid); + cur_mlid ); status = IB_ERROR; osm_dump_mc_record( &p_osmt->log, p_mc_res, OSM_LOG_VERBOSE ); goto Exit; @@ -3151,28 +3313,39 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { cl_ntoh64( p_recvd_rec->mgid.unicast.prefix ), cl_ntoh64( p_recvd_rec->mgid.unicast.interface_id ), cl_ntoh16( p_recvd_rec->mlid )); - cl_map_insert(&test_created_mlids, - cl_ntoh16(p_recvd_rec->mlid), p_recvd_rec ); + cl_map_insert(&test_created_mlids, + cl_ntoh16(p_recvd_rec->mlid), p_recvd_rec ); } tmp_mlid--; } } + /* Prepare the mc_req_rec for the rest of the flow */ osmt_init_mc_query_rec(p_osmt, &mc_req_rec); + /**************************************************************************/ - /* o15.0.1.16: */ - /* - Try GetTable with PortGUID wildcarded and get back some groups. */ + /* o15.0.1.16: */ + /* - Try GetTable with PortGUID wildcarded and get back some groups. */ status = osmt_query_mcast( p_osmt); + if (status != IB_SUCCESS) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmt_run_mcast_flow: ERR 02B1: " + "Failed to query multicast groups: %s\n", + ib_get_err_str(status) ); + goto Exit; + } + cnt = cl_qmap_count(&p_osmt->exp_subn.mgrp_mlid_tbl); osm_log( &p_osmt->log, OSM_LOG_INFO, "osmt_run_mcast_flow (Before Deletion of all MCG): " - "Number of MC Records found in SA DB is %d\n",cnt); + "Number of MC Records found in SA DB is %d\n", cnt ); /* Delete all MCG that are not of IPoIB */ osm_log( &p_osmt->log, OSM_LOG_INFO, "osmt_run_mcast_flow : " - "Cleanup all MCG that are not IPoIB...\n",cnt); + "Cleanup all MCG that are not IPoIB...\n" ); p_mgrp_mlid_tbl = &p_osmt->exp_subn.mgrp_mlid_tbl; p_mgrp = (osmtest_mgrp_t*)cl_qmap_head( p_mgrp_mlid_tbl ); @@ -3180,14 +3353,13 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { while( p_mgrp != (osmtest_mgrp_t*)cl_qmap_end( p_mgrp_mlid_tbl ) ) { /* Only if different from IPoIB Mgid try to delete */ - if (cl_memcmp(&osm_ipoib_good_mgid,&p_mgrp->mcmember_rec.mgid,sizeof(osm_ipoib_good_mgid)) && - cl_memcmp(&osm_ts_ipoib_good_mgid,&p_mgrp->mcmember_rec.mgid,sizeof(osm_ts_ipoib_good_mgid))) + if (!IS_IPOIB_MGID(&p_mgrp->mcmember_rec.mgid)) { osmt_init_mc_query_rec(p_osmt, &mc_req_rec); mc_req_rec.mgid = p_mgrp->mcmember_rec.mgid; /* o15-0.1.4 - need to specify the oppsite state for a valid delete */ - if (!cl_memcmp(&special_mgid,&p_mgrp->mcmember_rec.mgid,sizeof(special_mgid))) + if (!memcmp(&special_mgid, &p_mgrp->mcmember_rec.mgid, sizeof(special_mgid))) { mc_req_rec.scope_state = 0x2F; } @@ -3206,8 +3378,8 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { " : 0x%016" PRIx64 ", scope_state : 0x%02X\n", cl_ntoh64(mc_req_rec.mgid.unicast.prefix), cl_ntoh64(mc_req_rec.mgid.unicast.interface_id), - mc_req_rec.scope_state); - status = osmt_send_mcast_request( p_osmt, 0, /* delete flag */ + mc_req_rec.scope_state ); + status = osmt_send_mcast_request( p_osmt, 0, /* delete flag */ &mc_req_rec, comp_mask, &res_sa_mad ); @@ -3220,10 +3392,14 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { cl_ntoh64(p_mgrp->mcmember_rec.mgid.unicast.prefix), cl_ntoh64(p_mgrp->mcmember_rec.mgid.unicast.interface_id), ib_get_err_str( status ), - ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) )); + ib_get_mad_status_str( (ib_mad_t*)(&res_sa_mad) ) ); fail_to_delete_mcg++; } } + else + { + end_ipoib_cnt++; + } p_mgrp = (osmtest_mgrp_t*)cl_qmap_next( &p_mgrp->map_item ); } @@ -3232,8 +3408,9 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { if (status != IB_SUCCESS) { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: ERR 2FF " - "GetTable of all records has failed!\n"); + "osmt_run_mcast_flow: ERR 02B2 " + "GetTable of all records has failed - got %s\n", + ib_get_err_str( status ) ); goto Exit; } @@ -3243,17 +3420,34 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { if (p_osmt->opt.mmode == 1 || p_osmt->opt.mmode == 3) { end_cnt = cl_qmap_count(&p_osmt->exp_subn.mgrp_mlid_tbl); + osm_log( &p_osmt->log, OSM_LOG_INFO, - "osmt_run_mcast_flow (After Deletion of all MCG): " - "Number of MC Records found in SA DB is %d\n",end_cnt); - /* when we comapre num of MCG we should consider an outside source which create other MCGs */ - if ((end_cnt-fail_to_delete_mcg) != (start_cnt - mcg_outside_test_cnt)) + "osmt_run_mcast_flow: " + "Status of MC Records in SA DB during the test flow:\n" + " Beginning of test\n" + " Unrelated to the test: %d\n" + " IPoIB MC Records : %d\n" + " Total : %d\n" + " End of test\n" + " Failed to delete : %d\n" + " IPoIB MC Records : %d\n" + " Total : %d\n", + mcg_outside_test_cnt, /* Non-IPoIB that existed at the beginning */ + start_ipoib_cnt, /* IPoIB records */ + start_cnt, /* Total: IPoIB and MC Records unrelated to the test */ + fail_to_delete_mcg, /* Failed to delete at the end */ + end_ipoib_cnt, /* IPoIB records */ + end_cnt); /* Total MC Records at the end */ + + /* when we compare num of MCG we should consider an outside source which create other MCGs */ + if ((end_cnt - fail_to_delete_mcg-end_ipoib_cnt) != (start_cnt - mcg_outside_test_cnt - start_ipoib_cnt)) { osm_log( &p_osmt->log, OSM_LOG_INFO, "osmt_run_mcast_flow: " - "Got different number of records stored in SA DB\n\t\t" + "Got different number of non-IPoIB records stored in SA DB\n\t\t" "at Start got %d, at End got %d (IPoIB groups only)\n", - (start_cnt-mcg_outside_test_cnt),(end_cnt-fail_to_delete_mcg)); + (start_cnt - mcg_outside_test_cnt - start_ipoib_cnt), + (end_cnt - fail_to_delete_mcg-end_ipoib_cnt) ); } p_mgrp_mlid_tbl = &p_osmt->exp_subn.mgrp_mlid_tbl; @@ -3261,39 +3455,46 @@ osmt_run_mcast_flow( IN osmtest_t * const p_osmt ) { while( p_mgrp != (osmtest_mgrp_t*)cl_qmap_end( p_mgrp_mlid_tbl ) ) { uint16_t mlid = (uint16_t)cl_qmap_key((cl_map_item_t*)p_mgrp); + osm_log( &p_osmt->log, OSM_LOG_INFO, "osmt_run_mcast_flow: " "Found MLID:0x%04X\n", - mlid); + mlid ); /* Check if the mlid is in the test_created_mlids. If TRUE, then we didn't delete a MCgroup that was created in this flow. */ if ( cl_map_get (&test_created_mlids, mlid) != NULL ) { /* This means that we still have an mgrp that we created!! */ osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_run_mcast_flow: ERR 02FG: " + "osmt_run_mcast_flow: ERR 02FE: " "Wasn't able to erase mgrp with MGID:0x%016" PRIx64 " : 0x%016" PRIx64 " MLID:0x%04X\n", cl_ntoh64(p_mgrp->mcmember_rec.mgid.unicast.prefix), cl_ntoh64(p_mgrp->mcmember_rec.mgid.unicast.interface_id), mlid ); - status=IB_ERROR; - goto Exit; - } + got_error = TRUE; + } else { - osm_log( &p_osmt->log, OSM_LOG_INFO, - "osmt_run_mcast_flow: " - "Still exists MGID:0x%016" PRIx64 " : 0x%016" - PRIx64 "\n", - cl_ntoh64(p_mgrp->mcmember_rec.mgid.unicast.prefix), - cl_ntoh64(p_mgrp->mcmember_rec.mgid.unicast.interface_id) ); + osm_log( &p_osmt->log, OSM_LOG_INFO, + "osmt_run_mcast_flow: " + "Still exists %s MGID:0x%016" PRIx64 " : 0x%016" PRIx64 "\n", + (IS_IPOIB_MGID(&p_mgrp->mcmember_rec.mgid)) ? "IPoIB" : "non-IPoIB", + cl_ntoh64(p_mgrp->mcmember_rec.mgid.unicast.prefix), + cl_ntoh64(p_mgrp->mcmember_rec.mgid.unicast.interface_id) ); } p_mgrp = (osmtest_mgrp_t*)cl_qmap_next( &p_mgrp->map_item ); } + + if (got_error) + { + __osmt_print_all_multicast_records(p_osmt); + status = IB_ERROR; + } } Exit: OSM_LOG_EXIT( &p_osmt->log ); return status; } + diff --git a/trunk/ulp/opensm/user/osmtest/osmt_service.c b/trunk/ulp/opensm/user/osmtest/osmt_service.c index ec075d52..4325ed5d 100644 --- a/trunk/ulp/opensm/user/osmtest/osmt_service.c +++ b/trunk/ulp/opensm/user/osmtest/osmt_service.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -31,6 +31,7 @@ * $Id$ */ + /* * Abstract: * Implementation of service records testing flow.. @@ -46,8 +47,6 @@ * $Revision: 1.1 $ */ -/* next error code: 16A */ - #ifndef __WIN__ #include #else @@ -57,9 +56,11 @@ #include #include #include -#include #include "osmtest.h" +/********************************************************************** + **********************************************************************/ + ib_api_status_t osmt_register_service( IN osmtest_t * const p_osmt, IN ib_net64_t service_id, @@ -81,10 +82,10 @@ osmt_register_service( IN osmtest_t * const p_osmt, "Registering service: name: %s id: 0x%" PRIx64 "\n", service_name, cl_ntoh64(service_id)); - cl_memclr( &req, sizeof( req ) ); - cl_memclr( &context, sizeof( context ) ); - cl_memclr( &user, sizeof( user ) ); - cl_memclr( &svc_rec, sizeof( svc_rec ) ); + memset( &req, 0, sizeof( req ) ); + memset( &context, 0, sizeof( context ) ); + memset( &user, 0, sizeof( user ) ); + memset( &svc_rec, 0, sizeof( svc_rec ) ); /* set the new service record fields */ svc_rec.service_id = service_id; @@ -92,10 +93,10 @@ osmt_register_service( IN osmtest_t * const p_osmt, svc_rec.service_gid.unicast.prefix = 0; svc_rec.service_gid.unicast.interface_id = p_osmt->local_port.port_guid; svc_rec.service_lease = service_lease; - cl_memclr(&svc_rec.service_key,16*sizeof(uint8_t)); + memset(&svc_rec.service_key, 0, 16*sizeof(uint8_t)); svc_rec.service_key[0] = service_key_lsb; - cl_memclr(svc_rec.service_name, sizeof(svc_rec.service_name)); - cl_memcpy(svc_rec.service_name, service_name, + memset(svc_rec.service_name, 0, sizeof(svc_rec.service_name)); + memcpy(svc_rec.service_name, service_name, (strlen(service_name)+1)*sizeof(char)); /* prepare the data used for this query */ @@ -174,6 +175,9 @@ osmt_register_service( IN osmtest_t * const p_osmt, return status; } +/********************************************************************** + **********************************************************************/ + ib_api_status_t osmt_register_service_with_full_key ( IN osmtest_t * const p_osmt, IN ib_net64_t service_id, @@ -196,10 +200,10 @@ osmt_register_service_with_full_key ( IN osmtest_t * const p_osmt, "Registering service: name: %s id: 0x%" PRIx64 "\n", service_name, cl_ntoh64(service_id)); - cl_memclr( &req, sizeof( req ) ); - cl_memclr( &context, sizeof( context ) ); - cl_memclr( &user, sizeof( user ) ); - cl_memclr( &svc_rec, sizeof( svc_rec ) ); + memset( &req, 0, sizeof( req ) ); + memset( &context, 0, sizeof( context ) ); + memset( &user, 0, sizeof( user ) ); + memset( &svc_rec, 0, sizeof( svc_rec ) ); /* set the new service record fields */ svc_rec.service_id = service_id; @@ -207,12 +211,12 @@ osmt_register_service_with_full_key ( IN osmtest_t * const p_osmt, svc_rec.service_gid.unicast.prefix = 0; svc_rec.service_gid.unicast.interface_id = p_osmt->local_port.port_guid; svc_rec.service_lease = service_lease; - cl_memclr(&svc_rec.service_key,16*sizeof(uint8_t)); - cl_memcpy(svc_rec.service_key,service_key,16*sizeof(uint8_t)); - cl_memclr(svc_rec.service_name, sizeof(svc_rec.service_name)); - cl_memclr(skey, 16*sizeof(uint8_t)); - cl_memcpy(svc_rec.service_name, service_name, - (strlen(service_name)+1)*sizeof(char)); + memset(&svc_rec.service_key, 0, 16*sizeof(uint8_t)); + memcpy(svc_rec.service_key,service_key, 16*sizeof(uint8_t)); + memset(svc_rec.service_name, 0, sizeof(svc_rec.service_name)); + memset(skey, 0, 16*sizeof(uint8_t)); + memcpy(svc_rec.service_name, service_name, + (strlen(service_name)+1)*sizeof(char)); /* prepare the data used for this query */ /* sa_mad_data.method = IB_MAD_METHOD_SET; */ @@ -260,6 +264,23 @@ osmt_register_service_with_full_key ( IN osmtest_t * const p_osmt, } status = context.result.status; + if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmt_register_service_with_full_key: ERR 4A04: " + "ib_query failed (%s)\n", ib_get_err_str( status ) ); + + if( status == IB_REMOTE_ERROR ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmt_register_service_with_full_key: " + "Remote error = %s\n", + ib_get_mad_status_str( osm_madw_get_mad_ptr + ( context.result. + p_result_madw ) ) ); + } + goto Exit; + } /* Check service key on context to see if match */ p_rec = osmv_get_query_svc_rec( context.result.p_result_madw, 0 ); @@ -273,34 +294,16 @@ osmt_register_service_with_full_key ( IN osmtest_t * const p_osmt, i,service_key[i],i,p_rec->service_key[i]); } /* since c15-0.1.14 not supported all key association queries should bring in return zero in service key */ - if (cl_memcmp(skey,p_rec->service_key,16*sizeof(uint8_t)) != 0) + if (memcmp(skey,p_rec->service_key, 16*sizeof(uint8_t)) != 0) { status = IB_REMOTE_ERROR; osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_register_service_with_full_key:" + "osmt_register_service_with_full_key: ERR 4A33: " "Data mismatch in service_key\n" ); goto Exit; } - if( status != IB_SUCCESS ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_register_service_with_full_key: ERR 4A04: " - "ib_query failed (%s)\n", ib_get_err_str( status ) ); - - if( status == IB_REMOTE_ERROR ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_register_service_with_full_key: " - "Remote error = %s\n", - ib_get_mad_status_str( osm_madw_get_mad_ptr - ( context.result. - p_result_madw ) ) ); - } - goto Exit; - } - Exit: if( context.result.p_result_madw != NULL ) { @@ -312,6 +315,9 @@ osmt_register_service_with_full_key ( IN osmtest_t * const p_osmt, return status; } +/********************************************************************** + **********************************************************************/ + ib_api_status_t osmt_register_service_with_data( IN osmtest_t * const p_osmt, IN ib_net64_t service_id, @@ -338,10 +344,10 @@ osmt_register_service_with_data( IN osmtest_t * const p_osmt, "Registering service: name: %s id: 0x%" PRIx64 "\n", service_name, cl_ntoh64(service_id)); - cl_memclr( &req, sizeof( req ) ); - cl_memclr( &context, sizeof( context ) ); - cl_memclr( &user, sizeof( user ) ); - cl_memclr( &svc_rec, sizeof( svc_rec ) ); + memset( &req, 0, sizeof( req ) ); + memset( &context, 0, sizeof( context ) ); + memset( &user, 0, sizeof( user ) ); + memset( &svc_rec, 0, sizeof( svc_rec ) ); /* set the new service record fields */ svc_rec.service_id = service_id; @@ -349,18 +355,18 @@ osmt_register_service_with_data( IN osmtest_t * const p_osmt, svc_rec.service_gid.unicast.prefix = 0; svc_rec.service_gid.unicast.interface_id = p_osmt->local_port.port_guid; svc_rec.service_lease = service_lease; - cl_memclr(&svc_rec.service_key,16*sizeof(uint8_t)); + memset(&svc_rec.service_key, 0, 16*sizeof(uint8_t)); svc_rec.service_key[0] = service_key_lsb; /* Copy data to service_data arrays */ - cl_memcpy(svc_rec.service_data8,service_data8,16*sizeof(uint8_t)); - cl_memcpy(svc_rec.service_data16,service_data16,8*sizeof(ib_net16_t)); - cl_memcpy(svc_rec.service_data32,service_data32,4*sizeof(ib_net32_t)); - cl_memcpy(svc_rec.service_data64,service_data64,2*sizeof(ib_net64_t)); + memcpy(svc_rec.service_data8, service_data8, 16*sizeof(uint8_t)); + memcpy(svc_rec.service_data16, service_data16, 8*sizeof(ib_net16_t)); + memcpy(svc_rec.service_data32, service_data32, 4*sizeof(ib_net32_t)); + memcpy(svc_rec.service_data64, service_data64, 2*sizeof(ib_net64_t)); - cl_memclr(svc_rec.service_name, sizeof(svc_rec.service_name)); - cl_memcpy(svc_rec.service_name, service_name, - (strlen(service_name)+1)*sizeof(char)); + memset(svc_rec.service_name, 0, sizeof(svc_rec.service_name)); + memcpy(svc_rec.service_name, service_name, + (strlen(service_name)+1)*sizeof(char)); /* prepare the data used for this query */ /* sa_mad_data.method = IB_MAD_METHOD_SET; */ @@ -453,10 +459,10 @@ osmt_register_service_with_data( IN osmtest_t * const p_osmt, p_rec = osmv_get_query_svc_rec( context.result.p_result_madw, 0 ); osm_log( &p_osmt->log, OSM_LOG_VERBOSE, "Comparing service data...\n"); - if (cl_memcmp(service_data8,p_rec->service_data8,16*sizeof(uint8_t)) != 0 || - cl_memcmp(service_data16,p_rec->service_data16,8*sizeof(uint16_t)) != 0 || - cl_memcmp(service_data32,p_rec->service_data32,4*sizeof(uint32_t)) != 0 || - cl_memcmp(service_data64,p_rec->service_data64,2*sizeof(uint64_t)) != 0 + if (memcmp(service_data8, p_rec->service_data8,16*sizeof(uint8_t)) != 0 || + memcmp(service_data16, p_rec->service_data16,8*sizeof(uint16_t)) != 0 || + memcmp(service_data32, p_rec->service_data32,4*sizeof(uint32_t)) != 0 || + memcmp(service_data64, p_rec->service_data64,2*sizeof(uint64_t)) != 0 ) { status = IB_REMOTE_ERROR; @@ -478,6 +484,9 @@ osmt_register_service_with_data( IN osmtest_t * const p_osmt, return status; } +/********************************************************************** + **********************************************************************/ + ib_api_status_t osmt_get_service_by_id_and_name ( IN osmtest_t * const p_osmt, IN uint32_t rec_num, @@ -507,8 +516,8 @@ osmt_get_service_by_id_and_name ( IN osmtest_t * const p_osmt, * * The query structures are locals. */ - cl_memclr( &req, sizeof( req ) ); - cl_memclr( &context, sizeof( context ) ); + memset( &req, 0, sizeof( req ) ); + memset( &context, 0, sizeof( context ) ); context.p_osmt = p_osmt; @@ -521,12 +530,12 @@ osmt_get_service_by_id_and_name ( IN osmtest_t * const p_osmt, req.pfn_query_cb = osmtest_query_res_cb; req.sm_key = 0; - cl_memclr( &svc_rec, sizeof( svc_rec ) ); - cl_memclr( &user, sizeof( user ) ); + memset( &svc_rec, 0, sizeof( svc_rec ) ); + memset( &user, 0, sizeof( user ) ); /* set the new service record fields */ - cl_memclr(svc_rec.service_name, sizeof(svc_rec.service_name)); - cl_memcpy(svc_rec.service_name, sr_name, - (strlen(sr_name)+1)*sizeof(char)); + memset(svc_rec.service_name, 0, sizeof(svc_rec.service_name)); + memcpy(svc_rec.service_name, sr_name, + (strlen(sr_name)+1)*sizeof(char)); svc_rec.service_id = sid; req.p_query_input = &user; @@ -618,6 +627,9 @@ osmt_get_service_by_id_and_name ( IN osmtest_t * const p_osmt, return status; } +/********************************************************************** + **********************************************************************/ + ib_api_status_t osmt_get_service_by_id ( IN osmtest_t * const p_osmt, IN uint32_t rec_num, @@ -646,8 +658,8 @@ osmt_get_service_by_id ( IN osmtest_t * const p_osmt, * * The query structures are locals. */ - cl_memclr( &req, sizeof( req ) ); - cl_memclr( &context, sizeof( context ) ); + memset( &req, 0, sizeof( req ) ); + memset( &context, 0, sizeof( context ) ); context.p_osmt = p_osmt; @@ -660,8 +672,8 @@ osmt_get_service_by_id ( IN osmtest_t * const p_osmt, req.pfn_query_cb = osmtest_query_res_cb; req.sm_key = 0; - cl_memclr( &svc_rec, sizeof( svc_rec ) ); - cl_memclr( &user, sizeof( user ) ); + memset( &svc_rec, 0, sizeof( svc_rec ) ); + memset( &user, 0, sizeof( user ) ); /* set the new service record fields */ svc_rec.service_id = sid; req.p_query_input = &user; @@ -755,6 +767,9 @@ osmt_get_service_by_id ( IN osmtest_t * const p_osmt, return status; } +/********************************************************************** + **********************************************************************/ + ib_api_status_t osmt_get_service_by_name_and_key ( IN osmtest_t * const p_osmt, IN char * sr_name, @@ -794,8 +809,8 @@ osmt_get_service_by_name_and_key ( IN osmtest_t * const p_osmt, * * The query structures are locals. */ - cl_memclr( &req, sizeof( req ) ); - cl_memclr( &context, sizeof( context ) ); + memset( &req, 0, sizeof( req ) ); + memset( &context, 0, sizeof( context ) ); context.p_osmt = p_osmt; @@ -808,12 +823,12 @@ osmt_get_service_by_name_and_key ( IN osmtest_t * const p_osmt, req.pfn_query_cb = osmtest_query_res_cb; req.sm_key = 0; - cl_memclr( &svc_rec, sizeof( svc_rec ) ); - cl_memclr( &user, sizeof( user ) ); + memset( &svc_rec, 0, sizeof( svc_rec ) ); + memset( &user, 0, sizeof( user ) ); /* set the new service record fields */ - cl_memclr(svc_rec.service_name, sizeof(svc_rec.service_name)); - cl_memcpy(svc_rec.service_name, sr_name, - (strlen(sr_name)+1)*sizeof(char)); + memset(svc_rec.service_name, 0, sizeof(svc_rec.service_name)); + memcpy(svc_rec.service_name, sr_name, + (strlen(sr_name)+1)*sizeof(char)); for (i = 0; i <= 15; i++) svc_rec.service_key[i] = skey[i]; @@ -907,6 +922,9 @@ osmt_get_service_by_name_and_key ( IN osmtest_t * const p_osmt, return status; } +/********************************************************************** + **********************************************************************/ + ib_api_status_t osmt_get_service_by_name( IN osmtest_t * const p_osmt, IN char * sr_name, @@ -935,8 +953,8 @@ osmt_get_service_by_name( IN osmtest_t * const p_osmt, * * The query structures are locals. */ - cl_memclr( &req, sizeof( req ) ); - cl_memclr( &context, sizeof( context ) ); + memset( &req, 0, sizeof( req ) ); + memset( &context, 0, sizeof( context ) ); context.p_osmt = p_osmt; @@ -949,8 +967,8 @@ osmt_get_service_by_name( IN osmtest_t * const p_osmt, req.pfn_query_cb = osmtest_query_res_cb; req.sm_key = 0; - cl_memclr(service_name, sizeof(service_name)); - cl_memcpy(service_name, sr_name, (strlen(sr_name)+1)*sizeof(char)); + memset(service_name, 0, sizeof(service_name)); + memcpy(service_name, sr_name, (strlen(sr_name)+1)*sizeof(char)); req.p_query_input = service_name; status = osmv_query_sa( p_osmt->h_bind, &req ); @@ -1036,6 +1054,9 @@ osmt_get_service_by_name( IN osmtest_t * const p_osmt, return status; } +/********************************************************************** + **********************************************************************/ + #ifdef VENDOR_RMPP_SUPPORT ib_api_status_t osmt_get_all_services_and_check_names( IN osmtest_t * const p_osmt, @@ -1052,7 +1073,7 @@ osmt_get_all_services_and_check_names( IN osmtest_t * const p_osmt, OSM_LOG_ENTER(&p_osmt->log, osmt_get_all_services_and_check_names ); /* Prepare tracker for the checked names */ - p_checked_names = (uint8_t*)cl_malloc(sizeof(uint8_t)*num_of_valid_names); + p_checked_names = (uint8_t*)malloc(sizeof(uint8_t)*num_of_valid_names); for (j = 0 ; j < num_of_valid_names ; j++) { p_checked_names[j] = 0; @@ -1071,8 +1092,8 @@ osmt_get_all_services_and_check_names( IN osmtest_t * const p_osmt, * * The query structures are locals. */ - cl_memclr( &req, sizeof( req ) ); - cl_memclr( &context, sizeof( context ) ); + memset( &req, 0, sizeof( req ) ); + memset( &context, 0, sizeof( context ) ); context.p_osmt = p_osmt; @@ -1134,9 +1155,9 @@ osmt_get_all_services_and_check_names( IN osmtest_t * const p_osmt, osm_log( &p_osmt->log, OSM_LOG_VERBOSE, "osmt_get_all_services_and_check_names: " "-I- Comparing source name : >%s<, with record name : >%s<, idx : %d\n", - p_valid_service_names_arr[j],p_rec->service_name, p_checked_names[j]); - if ( strcmp(p_valid_service_names_arr[j], - p_rec->service_name) == 0 ) + p_valid_service_names_arr[j], p_rec->service_name, p_checked_names[j]); + if ( strcmp((char *)p_valid_service_names_arr[j], + (char *)p_rec->service_name) == 0 ) { osm_log( &p_osmt->log, OSM_LOG_VERBOSE, "osmt_get_all_services_and_check_names: " @@ -1170,6 +1191,9 @@ osmt_get_all_services_and_check_names( IN osmtest_t * const p_osmt, } #endif +/********************************************************************** + **********************************************************************/ + ib_api_status_t osmt_delete_service_by_name(IN osmtest_t * const p_osmt, IN uint8_t IsServiceExist, @@ -1187,7 +1211,7 @@ osmt_delete_service_by_name(IN osmtest_t * const p_osmt, "Trying to Delete service name: %s\n", sr_name); - cl_memclr( &svc_rec, sizeof( svc_rec ) ); + memset( &svc_rec, 0, sizeof( svc_rec ) ); status = osmt_get_service_by_name(p_osmt, sr_name,rec_num, &svc_rec); if (status != IB_SUCCESS) @@ -1199,14 +1223,14 @@ osmt_delete_service_by_name(IN osmtest_t * const p_osmt, goto ExitNoDel; } - cl_memclr( &req, sizeof( req ) ); - cl_memclr( &context, sizeof( context ) ); - cl_memclr( &user, sizeof( user ) ); + memset( &req, 0, sizeof( req ) ); + memset( &context, 0, sizeof( context ) ); + memset( &user, 0, sizeof( user ) ); /* set the new service record fields */ - cl_memclr(svc_rec.service_name, sizeof(svc_rec.service_name)); - cl_memcpy(svc_rec.service_name, sr_name, - (strlen(sr_name)+1)*sizeof(char)); + memset(svc_rec.service_name, 0, sizeof(svc_rec.service_name)); + memcpy(svc_rec.service_name, sr_name, + (strlen(sr_name)+1)*sizeof(char)); /* prepare the data used for this query */ context.p_osmt = p_osmt; @@ -1293,6 +1317,9 @@ osmt_delete_service_by_name(IN osmtest_t * const p_osmt, return status; } +/********************************************************************** + **********************************************************************/ + /* * Run a complete service records flow: * - register a service @@ -1382,14 +1409,14 @@ osmt_run_service_records_flow( IN osmtest_t * const p_osmt ) { /* Generate 2 instances of service record with consecutive data */ for (instance = 0 ; instance < 2 ; instance++) { /* First, clear all arrays */ - cl_memclr (service_data8,16*sizeof(uint8_t)); - cl_memclr (service_data16,8*sizeof(uint16_t)); - cl_memclr (service_data32,4*sizeof(uint32_t)); - cl_memclr (service_data64,2*sizeof(uint64_t)); - service_data8[instance]=instance+1; - service_data16[instance]=cl_hton16(instance+2); - service_data32[instance]=cl_hton32(instance+3); - service_data64[instance]=cl_hton64(instance+4); + memset (service_data8, 0, 16*sizeof(uint8_t)); + memset (service_data16, 0, 8*sizeof(uint16_t)); + memset (service_data32, 0, 4*sizeof(uint32_t)); + memset (service_data64, 0, 2*sizeof(uint64_t)); + service_data8[instance] = instance+1; + service_data16[instance] = cl_hton16(instance+2); + service_data32[instance] = cl_hton32(instance+3); + service_data64[instance] = cl_hton64(instance+4); status = osmt_register_service_with_data( p_osmt, cl_ntoh64(id[3]), /* IN ib_net64_t service_id, */ @@ -1408,7 +1435,7 @@ osmt_run_service_records_flow( IN osmtest_t * const p_osmt ) { } /* Trying to create service with zero key */ - cl_memclr (service_key,16*sizeof(uint8_t)); + memset (service_key, 0, 16*sizeof(uint8_t)); status = osmt_register_service_with_full_key( p_osmt, cl_ntoh64(id[5]), /* IN ib_net64_t service_id, */ @@ -1530,7 +1557,7 @@ osmt_run_service_records_flow( IN osmtest_t * const p_osmt ) { { osm_log( &p_osmt->log, OSM_LOG_ERROR, "osmt_run_service_records_flow: ERR 4A20: " - "Found service: id: 0x%016 " PRIx64 + "Found service: id: 0x%016" PRIx64 " " "that is invalid\n", id[7] ); status = IB_ERROR; @@ -1544,7 +1571,7 @@ osmt_run_service_records_flow( IN osmtest_t * const p_osmt ) { { osm_log( &p_osmt->log, OSM_LOG_ERROR, "osmt_run_service_records_flow: ERR 4A21: " - "Fail to find service: id: 0x%016 " PRIx64 + "Fail to find service: id: 0x%016" PRIx64 " " "name: %s\n", id[0], (char*)service_name[0] ); @@ -1559,7 +1586,7 @@ osmt_run_service_records_flow( IN osmtest_t * const p_osmt ) { { osm_log( &p_osmt->log, OSM_LOG_ERROR, "osmt_run_service_records_flow: ERR 4A22: " - "Fail to find service: id: 0x%016 " PRIx64 + "Fail to find service: id: 0x%016" PRIx64 " " "name: %s\n", id[5], (char*)service_name[6] ); @@ -1640,7 +1667,7 @@ osmt_run_service_records_flow( IN osmtest_t * const p_osmt ) { } /* Test Service Key */ - cl_memclr(service_key,16*sizeof(uint8_t)); + memset(service_key, 0, 16*sizeof(uint8_t)); /* Check for service_name[5] with service_key=0 - the service shouldn't exist with this name. */ @@ -1693,9 +1720,9 @@ osmt_run_service_records_flow( IN osmtest_t * const p_osmt ) { #ifdef VENDOR_RMPP_SUPPORT /* These ar the only service_names which are valid */ - cl_memcpy(&service_valid_names[0],&service_name[0],sizeof(uint8_t)*64); - cl_memcpy(&service_valid_names[1],&service_name[2],sizeof(uint8_t)*64); - cl_memcpy(&service_valid_names[2],&service_name[6],sizeof(uint8_t)*64); + memcpy(&service_valid_names[0], &service_name[0], sizeof(uint8_t)*64); + memcpy(&service_valid_names[1], &service_name[2], sizeof(uint8_t)*64); + memcpy(&service_valid_names[2], &service_name[6], sizeof(uint8_t)*64); status = osmt_get_all_services_and_check_names(p_osmt,service_valid_names, 3, &num_recs); if (status != IB_SUCCESS) @@ -1803,3 +1830,4 @@ osmt_run_service_records_flow( IN osmtest_t * const p_osmt ) { return status; } + diff --git a/trunk/ulp/opensm/user/osmtest/osmt_slvl_vl_arb.c b/trunk/ulp/opensm/user/osmtest/osmt_slvl_vl_arb.c index 3d58f144..45fe4916 100644 --- a/trunk/ulp/opensm/user/osmtest/osmt_slvl_vl_arb.c +++ b/trunk/ulp/opensm/user/osmtest/osmt_slvl_vl_arb.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -31,10 +31,13 @@ * $Id$ */ + /* * Abstract: * Implementation of SLtoVL and VL Arbitration testing flow.. - * Top level is osmt_run_slvl_vlarbs_records_flow: + * Top level is osmt_run_slvl_and_vlarb_records_flow: + * osmt_query_all_ports_vl_arb + * osmt_query_all_ports_slvl_map * * Environment: * Linux User Mode @@ -42,8 +45,6 @@ * $Revision: 1.2 $ */ -/* next error code: 16A */ - #ifndef __WIN__ #include #endif @@ -51,7 +52,6 @@ #include #include #include -#include #include "osmtest.h" /********************************************************************** @@ -64,7 +64,7 @@ osmtest_write_vl_arb_table( IN osmtest_t * const p_osmt, int result,i; cl_status_t status = IB_SUCCESS; - OSM_LOG_ENTER( &p_osmt->log, osmtest_write_port_info ); + OSM_LOG_ENTER( &p_osmt->log, osmtest_write_vl_arb_table ); result = fprintf( fh, "VL_ARBITRATION_TABLE\n" @@ -76,13 +76,16 @@ osmtest_write_vl_arb_table( IN osmtest_t * const p_osmt, p_rec->block_num ); fprintf( fh, " "); - for (i = 0; i<32; i++) fprintf( fh,"| %-2u ", i); + for (i = 0; i < 32; i++) + fprintf( fh,"| %-2u ", i); fprintf( fh, "|\nVL: "); - for (i = 0; i<32; i++) fprintf( fh,"|0x%02X",p_rec->vl_arb_tbl.vl_entry[i].vl); + for (i = 0; i < 32; i++) + fprintf( fh,"|0x%02X",p_rec->vl_arb_tbl.vl_entry[i].vl); fprintf( fh, "|\nWEIGHT:"); - for (i = 0; i<32; i++) fprintf( fh,"|0x%02X",p_rec->vl_arb_tbl.vl_entry[i].weight); + for (i = 0; i < 32; i++) + fprintf( fh,"|0x%02X",p_rec->vl_arb_tbl.vl_entry[i].weight); fprintf( fh,"|\nEND\n\n"); /* Exit: */ @@ -107,16 +110,16 @@ osmt_query_vl_arb( osmv_query_req_t req; ib_vl_arb_table_record_t record, *p_rec; - OSM_LOG_ENTER( &p_osmt->log, osmtest_get_port_rec ); + OSM_LOG_ENTER( &p_osmt->log, osmt_query_vl_arb ); if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmt_query_vl_arb: " - "Getting VL_Arbitration Table for port with LID 0x%X Num:0x%X.\n", - cl_ntoh16( lid ), - port_num); - } + { + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmt_query_vl_arb: " + "Getting VL_Arbitration Table for port with LID 0x%X Num:0x%X\n", + cl_ntoh16( lid ), + port_num ); + } /* * Do a blocking query for this record in the subnet. @@ -125,9 +128,9 @@ osmt_query_vl_arb( * * The query structures are locals. */ - cl_memclr( &req, sizeof( req ) ); - cl_memclr( &user, sizeof( user ) ); - cl_memclr( &context, sizeof( context ) ); + memset( &req, 0, sizeof( req ) ); + memset( &user, 0, sizeof( user ) ); + memset( &context, 0, sizeof( context ) ); context.p_osmt = p_osmt; @@ -148,54 +151,53 @@ osmt_query_vl_arb( status = osmv_query_sa( p_osmt->h_bind, &req ); if ( status != IB_SUCCESS ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_query_vl_arb: ERR 0405: " - "ib_query failed (%s).\n", ib_get_err_str( status ) ); - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmt_query_vl_arb: ERR 0405: " + "ib_query failed (%s)\n", ib_get_err_str( status ) ); + goto Exit; + } status = context.result.status; if( status != IB_SUCCESS ) - { - if (status != IB_INVALID_PARAMETER) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_query_vl_arb: ERR 0466: " - "ib_query failed (%s).\n", ib_get_err_str( status ) ); - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmt_query_vl_arb: ERR 0466: " + "ib_query failed (%s)\n", ib_get_err_str( status ) ); - if( status == IB_REMOTE_ERROR ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_query_vl_arb: " - "Remote error = %s.\n", - ib_get_mad_status_str( osm_madw_get_mad_ptr - ( context.result.p_result_madw ) ) ); - } - goto Exit; + if( status == IB_REMOTE_ERROR ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmt_query_vl_arb: " + "Remote error = %s\n", + ib_get_mad_status_str( osm_madw_get_mad_ptr + ( context.result.p_result_madw ) ) ); } + goto Exit; + } /* ok it worked */ p_rec = osmv_get_query_result( context.result.p_result_madw, 0); - osmtest_write_vl_arb_table( p_osmt, fh, p_rec ); + if ( fh ) + { + osmtest_write_vl_arb_table( p_osmt, fh, p_rec ); + } Exit: /* * Return the IB query MAD to the pool as necessary. */ if( context.result.p_result_madw != NULL ) - { - osm_mad_pool_put( &p_osmt->mad_pool, context.result.p_result_madw ); - context.result.p_result_madw = NULL; - } + { + osm_mad_pool_put( &p_osmt->mad_pool, context.result.p_result_madw ); + context.result.p_result_madw = NULL; + } OSM_LOG_EXIT( &p_osmt->log ); return ( status ); } - static ib_api_status_t osmt_query_all_ports_vl_arb( IN osmtest_t * const p_osmt, IN FILE * fh ) @@ -205,68 +207,71 @@ osmt_query_all_ports_vl_arb( IN osmtest_t * const p_osmt, port_t *p_src_port; uint8_t block, anyErr = 0; - OSM_LOG_ENTER( &p_osmt->log, osmtest_write_all_path_recs ); + OSM_LOG_ENTER( &p_osmt->log, osmt_query_all_ports_vl_arb ); osm_log( &p_osmt->log, OSM_LOG_VERBOSE, "osmt_query_all_ports_vl_arb: " - "Obtaining ALL Ports VL Arbitration Tables.\n"); + "Obtaining ALL Ports VL Arbitration Tables\n"); /* * Go over all ports that exist in the subnet - * for each pair that are not switch ports get the path record + * get the relevant VLarbs */ p_tbl = &p_osmt->exp_subn.port_key_tbl; p_src_port = ( port_t * ) cl_qmap_head( p_tbl ); - while( p_src_port != ( port_t * ) cl_qmap_end( p_tbl ) ) { + while( p_src_port != ( port_t * ) cl_qmap_end( p_tbl ) ) + { /* HACK we use capability_mask to know diff a CA port from switch port */ - if(p_src_port->rec.port_info.capability_mask ) + if( p_src_port->rec.port_info.capability_mask ) + { + /* this is an hca port */ + for (block = 1; block <= 4; block++) { - /* this is an hca port */ - for (block = 1; block <= 4; block++) { - /* NOTE to comply we must set port numbr to 0 and the SA should figure it out */ - /* since it is a CA port */ - status = osmt_query_vl_arb(p_osmt, p_src_port->rec.lid, 0, block, fh); - if (status != IB_SUCCESS) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_query_all_ports_vl_arb: ERR 0467: " - "Fail to get Lid:0x%X Port:0x%X (%s).\n", - cl_ntoh16(p_src_port->rec.lid), 0, - ib_get_err_str( status ) ); - anyErr = 1; - } + /* NOTE to comply we must set port number to 0 and the SA should figure it out */ + /* since it is a CA port */ + status = osmt_query_vl_arb(p_osmt, p_src_port->rec.lid, 0, block, fh); + if (status != IB_SUCCESS) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmt_query_all_ports_vl_arb: ERR 0467: " + "Failed to get Lid:0x%X Port:0x%X (%s)\n", + cl_ntoh16(p_src_port->rec.lid), 0, + ib_get_err_str( status ) ); + anyErr = 1; } } + } else + { + /* this is a switch port */ + for (block = 1; block <= 4; block++) { - /* this is a switch port */ - for (block = 1; block <= 4; block++) { - status = osmt_query_vl_arb(p_osmt, p_src_port->rec.lid, - p_src_port->rec.port_num, block, fh); - if (status != IB_SUCCESS) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_query_all_ports_vl_arb: ERR 0468: " - "Fail to get Lid:0x%X Port:0x%X (%s).\n", - cl_ntoh16(p_src_port->rec.lid), p_src_port->rec.port_num, - ib_get_err_str( status ) ); - anyErr = 1; - } + status = osmt_query_vl_arb(p_osmt, p_src_port->rec.lid, + p_src_port->rec.port_num, block, fh); + if (status != IB_SUCCESS) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmt_query_all_ports_vl_arb: ERR 0468: " + "Failed to get Lid:0x%X Port:0x%X (%s)\n", + cl_ntoh16(p_src_port->rec.lid), p_src_port->rec.port_num, + ib_get_err_str( status ) ); + anyErr = 1; } } + } p_src_port = ( port_t * ) cl_qmap_next( &p_src_port->map_item ); } OSM_LOG_EXIT( &p_osmt->log ); if (anyErr) - { - status = IB_ERROR; - } + { + status = IB_ERROR; + } return ( status ); } @@ -281,7 +286,7 @@ osmtest_write_slvl_map_table( IN osmtest_t * const p_osmt, int result, i; cl_status_t status = IB_SUCCESS; - OSM_LOG_ENTER( &p_osmt->log, osmtest_write_port_info ); + OSM_LOG_ENTER( &p_osmt->log, osmtest_write_slvl_map_table ); result = fprintf( fh, "SLtoVL_MAP_TABLE\n" @@ -298,7 +303,7 @@ osmtest_write_slvl_map_table( IN osmtest_t * const p_osmt, fprintf( fh, "|\nVL:"); for (i = 0; i < 16; i++) - fprintf( fh,"| 0x%01X ",ib_slvl_table_get( &p_rec->slvl_tbl, (uint8_t)i)); + fprintf( fh,"| 0x%01X ", ib_slvl_table_get( &p_rec->slvl_tbl, (uint8_t)i)); fprintf( fh,"|\nEND\n\n"); /* Exit: */ @@ -323,16 +328,16 @@ osmt_query_slvl_map( osmv_query_req_t req; ib_slvl_table_record_t record, *p_rec; - OSM_LOG_ENTER( &p_osmt->log, osmtest_get_port_rec ); + OSM_LOG_ENTER( &p_osmt->log, osmt_query_slvl_map ); if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmt_query_slvl_map: " - "Getting SLtoVL Map Table for out-port with LID 0x%X Num:0x%X from In-Port:0x%X.\n", - cl_ntoh16( lid ), - out_port_num, in_port_num); - } + { + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmt_query_slvl_map: " + "Getting SLtoVL Map Table for out-port with LID 0x%X Num:0x%X from In-Port:0x%X\n", + cl_ntoh16( lid ), + out_port_num, in_port_num ); + } /* * Do a blocking query for this record in the subnet. @@ -341,10 +346,9 @@ osmt_query_slvl_map( * * The query structures are locals. */ - cl_memclr( &req, sizeof( req ) ); - cl_memclr( &user, sizeof( user ) ); - cl_memclr( &context, sizeof( context ) ); - + memset( &req, 0, sizeof( req ) ); + memset( &user, 0, sizeof( user ) ); + memset( &context, 0, sizeof( context ) ); context.p_osmt = p_osmt; @@ -365,48 +369,48 @@ osmt_query_slvl_map( status = osmv_query_sa( p_osmt->h_bind, &req ); if ( status != IB_SUCCESS ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_query_slvl_map: ERR 0469: " - "ib_query failed (%s).\n", ib_get_err_str( status ) ); - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmt_query_slvl_map: ERR 0469: " + "ib_query failed (%s)\n", ib_get_err_str( status ) ); + goto Exit; + } status = context.result.status; if( status != IB_SUCCESS ) - { - if (status != IB_INVALID_PARAMETER) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_query_slvl_map: ERR 0470: " - "ib_query failed (%s).\n", ib_get_err_str( status ) ); - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmt_query_slvl_map: ERR 0470: " + "ib_query failed (%s)\n", ib_get_err_str( status ) ); - if( status == IB_REMOTE_ERROR ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_query_slvl_map: " - "Remote error = %s.\n", - ib_get_mad_status_str( osm_madw_get_mad_ptr - ( context.result.p_result_madw ) ) ); - } - goto Exit; + if( status == IB_REMOTE_ERROR ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmt_query_slvl_map: " + "Remote error = %s\n", + ib_get_mad_status_str( osm_madw_get_mad_ptr + ( context.result.p_result_madw ) ) ); } + goto Exit; + } /* ok it worked */ p_rec = osmv_get_query_result( context.result.p_result_madw, 0); - osmtest_write_slvl_map_table( p_osmt, fh, p_rec ); + if ( fh ) + { + osmtest_write_slvl_map_table( p_osmt, fh, p_rec ); + } Exit: /* * Return the IB query MAD to the pool as necessary. */ if( context.result.p_result_madw != NULL ) - { - osm_mad_pool_put( &p_osmt->mad_pool, context.result.p_result_madw ); - context.result.p_result_madw = NULL; - } + { + osm_mad_pool_put( &p_osmt->mad_pool, context.result.p_result_madw ); + context.result.p_result_madw = NULL; + } OSM_LOG_EXIT( &p_osmt->log ); return ( status ); @@ -423,71 +427,73 @@ osmt_query_all_ports_slvl_map( IN osmtest_t * const p_osmt, node_t *p_node; const cl_qmap_t *p_node_tbl; - OSM_LOG_ENTER( &p_osmt->log, osmt_query_all_ports_slvl ); + OSM_LOG_ENTER( &p_osmt->log, osmt_query_all_ports_slvl_map ); /* * Go over all ports that exist in the subnet - * for each pair that are not switch ports get the relevant SLtoVLs + * get the relevant SLtoVLs */ osm_log( &p_osmt->log, OSM_LOG_VERBOSE, "osmt_query_all_ports_slvl_map: " - "Obtaining ALL Ports (to other ports) SLtoVL Maps.\n"); + "Obtaining ALL Ports (to other ports) SLtoVL Maps\n"); p_tbl = &p_osmt->exp_subn.port_key_tbl; p_node_tbl = &p_osmt->exp_subn.node_lid_tbl; p_src_port = ( port_t * ) cl_qmap_head( p_tbl ); - while( p_src_port != ( port_t * ) cl_qmap_end( p_tbl ) ) { + while( p_src_port != ( port_t * ) cl_qmap_end( p_tbl ) ) + { /* HACK we use capability_mask to know diff a CA port from switch port */ - if(p_src_port->rec.port_info.capability_mask ) + if( p_src_port->rec.port_info.capability_mask ) + { + /* this is an hca port */ + /* NOTE to comply we must set port number to 0 and the SA should figure it out */ + /* since it is a CA port */ + status = osmt_query_slvl_map(p_osmt, p_src_port->rec.lid, 0, 0, fh); + if (status != IB_SUCCESS) { - /* this is an hca port */ - /* NOTE to comply we must set port numbr to 0 and the SA should figure it out */ - /* since it is a CA port */ - status = osmt_query_slvl_map(p_osmt, p_src_port->rec.lid, 0, 0, fh); - if (status != IB_SUCCESS) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_query_all_ports_slvl_map: ERR 0471: " - "Fail to get Lid:0x%X In-Port:0x%X Out-Port:0x%X(%s).\n", - cl_ntoh16(p_src_port->rec.lid), 0, 0, - ib_get_err_str( status ) ); - anyErr = 1; - } + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmt_query_all_ports_slvl_map: ERR 0471: " + "Failed to get Lid:0x%X In-Port:0x%X Out-Port:0x%X(%s)\n", + cl_ntoh16(p_src_port->rec.lid), 0, 0, + ib_get_err_str( status ) ); + anyErr = 1; } + } else + { + /* this is a switch port */ + /* get the node */ + p_node = ( node_t * ) cl_qmap_get( p_node_tbl, p_src_port->rec.lid ); + if( p_node == ( node_t * ) cl_qmap_end( p_node_tbl ) ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmt_query_all_ports_slvl_map: ERR 0472: " + "Failed to get Node by Lid:0x%X\n", + p_src_port->rec.lid ); + goto Exit; + } + + num_ports = p_node->rec.node_info.num_ports; + + for (in_port = 1; in_port <= num_ports; in_port++) { - /* this is a switch port */ - /* get the node */ - p_node = ( node_t * ) cl_qmap_get( p_node_tbl, p_src_port->rec.lid ); - if( p_node == ( node_t * ) cl_qmap_end( p_node_tbl ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_query_all_ports_slvl_map: ERR 0472: " - "Fail to get Node by Lid:0x%X\n", - p_src_port->rec.lid); - goto Exit; - } - - num_ports = p_node->rec.node_info.num_ports; - - for (in_port = 1; in_port <= num_ports; in_port++) { - status = osmt_query_slvl_map(p_osmt, p_src_port->rec.lid, - p_src_port->rec.port_num, in_port, fh); - if (status != IB_SUCCESS) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmt_query_all_ports_slvl_map: ERR 0473: " - "Fail to get Lid:0x%X In-Port:0x%X Out-Port:0x%X (%s).\n", - cl_ntoh16(p_src_port->rec.lid), p_src_port->rec.port_num, in_port, - ib_get_err_str( status ) ); - anyErr = 1; - } + status = osmt_query_slvl_map(p_osmt, p_src_port->rec.lid, + p_src_port->rec.port_num, in_port, fh ); + if (status != IB_SUCCESS) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmt_query_all_ports_slvl_map: ERR 0473: " + "Failed to get Lid:0x%X In-Port:0x%X Out-Port:0x%X (%s)\n", + cl_ntoh16(p_src_port->rec.lid), p_src_port->rec.port_num, in_port, + ib_get_err_str( status ) ); + anyErr = 1; } } + } p_src_port = ( port_t * ) cl_qmap_next( &p_src_port->map_item ); } @@ -495,9 +501,9 @@ osmt_query_all_ports_slvl_map( IN osmtest_t * const p_osmt, Exit: OSM_LOG_EXIT( &p_osmt->log ); if (anyErr) - { - status = IB_ERROR; - } + { + status = IB_ERROR; + } return ( status ); } @@ -513,26 +519,47 @@ osmt_query_all_ports_slvl_map( IN osmtest_t * const p_osmt, * - Try providing non existing port */ ib_api_status_t -osmt_run_slvl_and_vlarb_records_flow( IN osmtest_t * const p_osmt ) { +osmt_run_slvl_and_vlarb_records_flow( IN osmtest_t * const p_osmt ) +{ ib_api_status_t status; FILE *fh; + ib_net16_t test_lid; + uint8_t lmc; - OSM_LOG_ENTER( &p_osmt->log, osmt_run_vlarb_records_flow ); + OSM_LOG_ENTER( &p_osmt->log, osmt_run_slvl_and_vlarb_records_flow ); - fh = fopen("vl_arbs.txt","w"); - /* go over all ports in the subnet */ + fh = fopen("qos.txt","w"); + /* go over all ports in the subnet */ status = osmt_query_all_ports_vl_arb( p_osmt, fh ); if (status != IB_SUCCESS) - { - goto Exit; - } + { + goto Exit; + } status = osmt_query_all_ports_slvl_map( p_osmt, fh ); if (status != IB_SUCCESS) - { + { + goto Exit; + } + + /* If LMC > 0, test non base LID SA QoS Record requests */ + status = osmtest_get_local_port_lmc( p_osmt, p_osmt->local_port.lid, &lmc ); + if ( status != IB_SUCCESS ) + goto Exit; + + if (lmc != 0) + { + test_lid = cl_ntoh16( p_osmt->local_port.lid + 1); + + status = osmt_query_vl_arb( p_osmt, test_lid, 0, 1, NULL ); + if ( status != IB_SUCCESS ) goto Exit; - } + + status = osmt_query_slvl_map( p_osmt, test_lid, 0, 0, NULL ); + if ( status != IB_SUCCESS ) + goto Exit; + } Exit: fclose(fh); diff --git a/trunk/ulp/opensm/user/osmtest/osmtest.c b/trunk/ulp/opensm/user/osmtest/osmtest.c index 86401696..063f8959 100644 --- a/trunk/ulp/opensm/user/osmtest/osmtest.c +++ b/trunk/ulp/opensm/user/osmtest/osmtest.c @@ -1,6 +1,6 @@ /* - * Copyright (c) 2004, 2005 Voltaire, Inc. All rights reserved. - * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved. + * Copyright (c) 2004-2006 Voltaire, Inc. All rights reserved. + * Copyright (c) 2002-2006 Mellanox Technologies LTD. All rights reserved. * Copyright (c) 1996-2003 Intel Corporation. All rights reserved. * * This software is available to you under the OpenIB.org BSD license @@ -31,13 +31,13 @@ * $Id$ */ + /* TODO : Check why we dont free the cl_qmap_items we store when reading DB */ /* * Abstract: * Implementation of osmtest_t. - * This object represents the opensm super object. - * This object is part of the opensm family of objects. + * This object represents the OSMTest Test object. * * Environment: * Linux User Mode @@ -49,19 +49,16 @@ #pragma warning(disable : 4996) #endif -/* next error code: 16A */ - #include #include -#ifdef __WIN__ #include +#ifdef __WIN__ #include #else #include #include #endif #include -#include #include "osmtest.h" #ifndef __WIN__ @@ -72,7 +69,7 @@ #define GUID_ARRAY_SIZE 64 typedef enum _osmtest_token_val - { +{ OSMTEST_TOKEN_COMMENT = 0, OSMTEST_TOKEN_END, OSMTEST_TOKEN_DEFINE_NODE, @@ -137,18 +134,19 @@ typedef enum _osmtest_token_val OSMTEST_TOKEN_RESP_TIME_VAL, OSMTEST_TOKEN_ERR_THRESHOLD, OSMTEST_TOKEN_MTU, + OSMTEST_TOKEN_FROMLID, + OSMTEST_TOKEN_FROMPORTNUM, + OSMTEST_TOKEN_TOPORTNUM, + OSMTEST_TOKEN_TOLID, OSMTEST_TOKEN_UNKNOWN - } -osmtest_token_val_t; +} osmtest_token_val_t; typedef struct _osmtest_token { osmtest_token_val_t val; size_t str_size; const char *str; - -} -osmtest_token_t; +} osmtest_token_t; const osmtest_token_t token_array[] = { {OSMTEST_TOKEN_COMMENT, 1, "#"}, @@ -215,6 +213,10 @@ const osmtest_token_t token_array[] = { {OSMTEST_TOKEN_RESP_TIME_VAL, 15, "resp_time_value"}, {OSMTEST_TOKEN_ERR_THRESHOLD, 15, "error_threshold"}, {OSMTEST_TOKEN_MTU, 3, "MTU"}, /* must be after the other mtu... tokens. */ + {OSMTEST_TOKEN_FROMLID, 8, "from_lid"}, + {OSMTEST_TOKEN_FROMPORTNUM, 13, "from_port_num"}, + {OSMTEST_TOKEN_TOPORTNUM, 11, "to_port_num"}, + {OSMTEST_TOKEN_TOLID, 6, "to_lid"}, {OSMTEST_TOKEN_UNKNOWN, 0, ""} /* must be last entry */ }; @@ -259,142 +261,142 @@ ib_get_mad_status_str( IN const ib_mad_t * const p_mad ) status = ( ib_net16_t ) ( p_mad->status & IB_SMP_STATUS_MASK ); if( status == 0 ) - { - strcat( &line[offset], "IB_SUCCESS" ); - return ( line ); - } + { + strcat( &line[offset], "IB_SUCCESS" ); + return ( line ); + } if( status & IB_MAD_STATUS_BUSY ) - { - strcat( &line[offset], ib_mad_status_str_busy ); - offset += sizeof( ib_mad_status_str_busy ); - } + { + strcat( &line[offset], ib_mad_status_str_busy ); + offset += sizeof( ib_mad_status_str_busy ); + } if( status & IB_MAD_STATUS_REDIRECT ) + { + if( !first ) { - if( !first ) - { - strcat( &line[offset], generic_or_str ); - offset += sizeof( generic_or_str ) - 1; - } - first = FALSE; - strcat( &line[offset], ib_mad_status_str_redirect ); - offset += sizeof( ib_mad_status_str_redirect ) - 1; + strcat( &line[offset], generic_or_str ); + offset += sizeof( generic_or_str ) - 1; } - if( status & IB_MAD_STATUS_UNSUP_CLASS_VER ) + first = FALSE; + strcat( &line[offset], ib_mad_status_str_redirect ); + offset += sizeof( ib_mad_status_str_redirect ) - 1; + } + if( ( status & IB_MAD_STATUS_INVALID_FIELD ) == IB_MAD_STATUS_UNSUP_CLASS_VER ) + { + if( !first ) { - if( !first ) - { - strcat( &line[offset], generic_or_str ); - offset += sizeof( generic_or_str ) - 1; - } - first = FALSE; - strcat( &line[offset], ib_mad_status_str_unsup_class_ver ); - offset += sizeof( ib_mad_status_str_unsup_class_ver ) - 1; + strcat( &line[offset], generic_or_str ); + offset += sizeof( generic_or_str ) - 1; } - if( status & IB_MAD_STATUS_UNSUP_METHOD ) + first = FALSE; + strcat( &line[offset], ib_mad_status_str_unsup_class_ver ); + offset += sizeof( ib_mad_status_str_unsup_class_ver ) - 1; + } + if( ( status & IB_MAD_STATUS_INVALID_FIELD ) == IB_MAD_STATUS_UNSUP_METHOD ) + { + if( !first ) { - if( !first ) - { - strcat( &line[offset], generic_or_str ); - offset += sizeof( generic_or_str ) - 1; - } - first = FALSE; - strcat( &line[offset], ib_mad_status_str_unsup_method ); - offset += sizeof( ib_mad_status_str_unsup_method ) - 1; + strcat( &line[offset], generic_or_str ); + offset += sizeof( generic_or_str ) - 1; } - if( status & IB_MAD_STATUS_UNSUP_METHOD_ATTR ) + first = FALSE; + strcat( &line[offset], ib_mad_status_str_unsup_method ); + offset += sizeof( ib_mad_status_str_unsup_method ) - 1; + } + if( (status & IB_MAD_STATUS_INVALID_FIELD ) == IB_MAD_STATUS_UNSUP_METHOD_ATTR ) + { + if( !first ) { - if( !first ) - { - strcat( &line[offset], generic_or_str ); - offset += sizeof( generic_or_str ) - 1; - } - first = FALSE; - strcat( &line[offset], ib_mad_status_str_unsup_method_attr ); - offset += sizeof( ib_mad_status_str_unsup_method_attr ) - 1; + strcat( &line[offset], generic_or_str ); + offset += sizeof( generic_or_str ) - 1; } - if( status & IB_MAD_STATUS_INVALID_FIELD ) + first = FALSE; + strcat( &line[offset], ib_mad_status_str_unsup_method_attr ); + offset += sizeof( ib_mad_status_str_unsup_method_attr ) - 1; + } + if( ( status & IB_MAD_STATUS_INVALID_FIELD ) == IB_MAD_STATUS_INVALID_FIELD ) + { + if( !first ) { - if( !first ) - { - strcat( &line[offset], generic_or_str ); - offset += sizeof( generic_or_str ) - 1; - } - first = FALSE; - strcat( &line[offset], ib_mad_status_str_invalid_field ); - offset += sizeof( ib_mad_status_str_invalid_field ) - 1; + strcat( &line[offset], generic_or_str ); + offset += sizeof( generic_or_str ) - 1; } + first = FALSE; + strcat( &line[offset], ib_mad_status_str_invalid_field ); + offset += sizeof( ib_mad_status_str_invalid_field ) - 1; + } if( ( status & IB_MAD_STATUS_CLASS_MASK ) == IB_SA_MAD_STATUS_NO_RESOURCES ) + { + if( !first ) { - if( !first ) - { - strcat( &line[offset], generic_or_str ); - offset += sizeof( generic_or_str ) - 1; - } - first = FALSE; - strcat( &line[offset], ib_mad_status_str_no_resources ); - offset += sizeof( ib_mad_status_str_no_resources ) - 1; + strcat( &line[offset], generic_or_str ); + offset += sizeof( generic_or_str ) - 1; } + first = FALSE; + strcat( &line[offset], ib_mad_status_str_no_resources ); + offset += sizeof( ib_mad_status_str_no_resources ) - 1; + } if( ( status & IB_MAD_STATUS_CLASS_MASK ) == IB_SA_MAD_STATUS_REQ_INVALID ) + { + if( !first ) { - if( !first ) - { - strcat( &line[offset], generic_or_str ); - offset += sizeof( generic_or_str ) - 1; - } - first = FALSE; - strcat( &line[offset], ib_mad_status_str_req_invalid ); - offset += sizeof( ib_mad_status_str_req_invalid ) - 1; + strcat( &line[offset], generic_or_str ); + offset += sizeof( generic_or_str ) - 1; } + first = FALSE; + strcat( &line[offset], ib_mad_status_str_req_invalid ); + offset += sizeof( ib_mad_status_str_req_invalid ) - 1; + } if( ( status & IB_MAD_STATUS_CLASS_MASK ) == IB_SA_MAD_STATUS_NO_RECORDS ) + { + if( !first ) { - if( !first ) - { - strcat( &line[offset], generic_or_str ); - offset += sizeof( generic_or_str ) - 1; - } - first = FALSE; - strcat( &line[offset], ib_mad_status_str_no_records ); - offset += sizeof( ib_mad_status_str_no_records ) - 1; + strcat( &line[offset], generic_or_str ); + offset += sizeof( generic_or_str ) - 1; } + first = FALSE; + strcat( &line[offset], ib_mad_status_str_no_records ); + offset += sizeof( ib_mad_status_str_no_records ) - 1; + } if( ( status & IB_MAD_STATUS_CLASS_MASK ) == IB_SA_MAD_STATUS_TOO_MANY_RECORDS ) + { + if( !first ) { - if( !first ) - { - strcat( &line[offset], generic_or_str ); - offset += sizeof( generic_or_str ) - 1; - } - first = FALSE; - strcat( &line[offset], ib_mad_status_str_too_many_records ); - offset += sizeof( ib_mad_status_str_too_many_records ) - 1; + strcat( &line[offset], generic_or_str ); + offset += sizeof( generic_or_str ) - 1; } + first = FALSE; + strcat( &line[offset], ib_mad_status_str_too_many_records ); + offset += sizeof( ib_mad_status_str_too_many_records ) - 1; + } if( ( status & IB_MAD_STATUS_CLASS_MASK ) == IB_SA_MAD_STATUS_INVALID_GID ) + { + if( !first ) { - if( !first ) - { - strcat( &line[offset], generic_or_str ); - offset += sizeof( generic_or_str ) - 1; - } - first = FALSE; - strcat( &line[offset], ib_mad_status_str_invalid_gid ); - offset += sizeof( ib_mad_status_str_invalid_gid ) - 1; + strcat( &line[offset], generic_or_str ); + offset += sizeof( generic_or_str ) - 1; } + first = FALSE; + strcat( &line[offset], ib_mad_status_str_invalid_gid ); + offset += sizeof( ib_mad_status_str_invalid_gid ) - 1; + } if( ( status & IB_MAD_STATUS_CLASS_MASK ) == IB_SA_MAD_STATUS_INSUF_COMPS ) + { + if( !first ) { - if( !first ) - { - strcat( &line[offset], generic_or_str ); - offset += sizeof( generic_or_str ) - 1; - } - first = FALSE; - strcat( &line[offset], ib_mad_status_str_insuf_comps ); - offset += sizeof( ib_mad_status_str_insuf_comps ) - 1; + strcat( &line[offset], generic_or_str ); + offset += sizeof( generic_or_str ) - 1; } + first = FALSE; + strcat( &line[offset], ib_mad_status_str_insuf_comps ); + offset += sizeof( ib_mad_status_str_insuf_comps ) - 1; + } return ( line ); } @@ -435,7 +437,7 @@ subnet_init( IN subnet_t * const p_subn ) void osmtest_construct( IN osmtest_t * const p_osmt ) { - cl_memclr( p_osmt, sizeof( *p_osmt ) ); + memset( p_osmt, 0, sizeof( *p_osmt ) ); osm_log_construct( &p_osmt->log ); subnet_construct( &p_osmt->exp_subn ); } @@ -447,15 +449,17 @@ osmtest_destroy( IN osmtest_t * const p_osmt ) { cl_map_item_t *p_item,*p_next_item; + + /* Currently there is a problem with IBAL exit flow - memory overrun , so we bypass the vendor deletion Since it's already will be cleaned by the Windows OS . */ + #ifndef __WIN__ if( p_osmt->p_vendor ) - { - osm_vendor_delete( &p_osmt->p_vendor ); - } + { + osm_vendor_delete( &p_osmt->p_vendor ); + } #endif - cl_qpool_destroy( &p_osmt->port_pool ); cl_qpool_destroy( &p_osmt->node_pool ); @@ -465,21 +469,21 @@ osmtest_destroy( IN osmtest_t * const p_osmt ) { p_item = p_next_item; p_next_item = cl_qmap_next( p_item ); - cl_free( p_item ); + free( p_item ); } p_next_item = cl_qmap_head( &p_osmt->exp_subn.mgrp_mlid_tbl ); while( p_next_item != cl_qmap_end( &p_osmt->exp_subn.mgrp_mlid_tbl ) ) { p_item = p_next_item; p_next_item = cl_qmap_next( p_item ); - cl_free( p_item ); + free( p_item ); } p_next_item = cl_qmap_head( &p_osmt->exp_subn.node_guid_tbl ); while( p_next_item != cl_qmap_end( &p_osmt->exp_subn.node_guid_tbl ) ) { p_item = p_next_item; p_next_item = cl_qmap_next( p_item ); - cl_free( p_item ); + free( p_item ); } p_next_item = cl_qmap_head( &p_osmt->exp_subn.node_lid_tbl ); @@ -487,7 +491,7 @@ osmtest_destroy( IN osmtest_t * const p_osmt ) { p_item = p_next_item; p_next_item = cl_qmap_next( p_item ); - cl_free( p_item ); + free( p_item ); } p_next_item = cl_qmap_head( &p_osmt->exp_subn.path_tbl ); @@ -495,14 +499,14 @@ osmtest_destroy( IN osmtest_t * const p_osmt ) { p_item = p_next_item; p_next_item = cl_qmap_next( p_item ); - cl_free( p_item ); + free( p_item ); } p_next_item = cl_qmap_head( &p_osmt->exp_subn.port_key_tbl ); while( p_next_item != cl_qmap_end( &p_osmt->exp_subn.port_key_tbl ) ) { p_item = p_next_item; p_next_item = cl_qmap_next( p_item ); - cl_free( p_item ); + free( p_item ); } osm_log_destroy( &p_osmt->log ); @@ -521,8 +525,8 @@ osmtest_init( IN osmtest_t * const p_osmt, /* Can't use log macros here, since we're initializing the log. */ osmtest_construct( p_osmt ); - status = osm_log_init( &p_osmt->log, p_opt->force_log_flush, - 0x0001, p_opt->log_file, TRUE ); + status = osm_log_init_v2( &p_osmt->log, p_opt->force_log_flush, + 0x0001, p_opt->log_file, 0, TRUE ); if( status != IB_SUCCESS ) return ( status ); @@ -548,17 +552,17 @@ osmtest_init( IN osmtest_t * const p_osmt, p_opt->transaction_timeout ); if( p_osmt->p_vendor == NULL ) - { - status = IB_INSUFFICIENT_RESOURCES; - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_init: ERR 0001: " - "Unable to allocate vendor object" ); - goto Exit; - } + { + status = IB_INSUFFICIENT_RESOURCES; + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_init: ERR 0001: " + "Unable to allocate vendor object" ); + status = IB_ERROR; + goto Exit; + } osm_mad_pool_construct( &p_osmt->mad_pool ); - status = osm_mad_pool_init( - &p_osmt->mad_pool, &p_osmt->log ); + status = osm_mad_pool_init( &p_osmt->mad_pool, &p_osmt->log ); if( status != IB_SUCCESS ) goto Exit; @@ -582,14 +586,11 @@ osmtest_query_res_cb( IN osmv_query_res_t * p_rec ) p_ctxt->result = *p_rec; if( p_rec->status != IB_SUCCESS ) - { - if ( p_rec->status != IB_INVALID_PARAMETER ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_query_res_cb: ERR 0003: " - "Error on query (%s)\n", ib_get_err_str( p_rec->status ) ); - } - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_query_res_cb: ERR 0003: " + "Error on query (%s)\n", ib_get_err_str( p_rec->status ) ); + } OSM_LOG_EXIT( &p_osmt->log ); } @@ -609,11 +610,11 @@ osmtest_get_all_recs( IN osmtest_t * const p_osmt, OSM_LOG_ENTER( &p_osmt->log, osmtest_get_all_recs ); if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_get_all_recs: " - "Getting all %s records\n", ib_get_sa_attr_str( attr_id ) ); - } + { + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_get_all_recs: " + "Getting all %s records\n", ib_get_sa_attr_str( attr_id ) ); + } /* * Do a blocking query for all records in the subnet. @@ -622,8 +623,8 @@ osmtest_get_all_recs( IN osmtest_t * const p_osmt, * * The query structures are locals. */ - cl_memclr( &req, sizeof( req ) ); - cl_memclr( &user, sizeof( user ) ); + memset( &req, 0, sizeof( req ) ); + memset( &user, 0, sizeof( user ) ); p_context->p_osmt = p_osmt; user.attr_id = attr_id; @@ -639,34 +640,32 @@ osmtest_get_all_recs( IN osmtest_t * const p_osmt, req.sm_key = 0; status = osmv_query_sa( p_osmt->h_bind, &req ); - if( status != IB_SUCCESS ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_get_all_recs: ERR 0004: " - "ib_query failed (%s)\n", ib_get_err_str( status ) ); - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_all_recs: ERR 0004: " + "ib_query failed (%s)\n", ib_get_err_str( status ) ); + goto Exit; + } status = p_context->result.status; if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_all_recs: ERR 0064: " + "ib_query failed (%s)\n", ib_get_err_str( status ) ); + + if( status == IB_REMOTE_ERROR ) { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_get_all_recs: ERR 0064: " - "ib_query failed (%s)\n", ib_get_err_str( status ) ); - - if( status == IB_REMOTE_ERROR ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_get_all_recs: " - "Remote error = %s\n", - ib_get_mad_status_str( osm_madw_get_mad_ptr - ( p_context->result. - p_result_madw ) ) ); - } - goto Exit; + "osmtest_get_all_recs: " + "Remote error = %s\n", + ib_get_mad_status_str( osm_madw_get_mad_ptr + ( p_context->result.p_result_madw ) ) ); } + goto Exit; + } Exit: OSM_LOG_EXIT( &p_osmt->log ); @@ -685,14 +684,14 @@ osmtest_validate_sa_class_port_info( IN osmtest_t * const p_osmt) osmtest_req_context_t *p_context = &context; ib_sa_mad_t *p_resp_sa_madp; - OSM_LOG_ENTER( &p_osmt->log, osmtest_get_sa_class_port_info ); + OSM_LOG_ENTER( &p_osmt->log, osmtest_validate_sa_class_port_info ); if( osm_log_is_active( &p_osmt->log, OSM_LOG_VERBOSE ) ) - { - osm_log( &p_osmt->log, OSM_LOG_VERBOSE, - "osmtest_validate_sa_class_port_info: " - "Getting ClassPortInfo\n"); - } + { + osm_log( &p_osmt->log, OSM_LOG_VERBOSE, + "osmtest_validate_sa_class_port_info: " + "Getting ClassPortInfo\n"); + } /* * Do a blocking query for this record in the subnet. @@ -701,7 +700,7 @@ osmtest_validate_sa_class_port_info( IN osmtest_t * const p_osmt) * * The query structures are locals. */ - cl_memclr( &req, sizeof( req ) ); + memset( &req, 0, sizeof( req ) ); p_context->p_osmt = p_osmt; req.query_type = OSMV_QUERY_CLASS_PORT_INFO; @@ -714,36 +713,31 @@ osmtest_validate_sa_class_port_info( IN osmtest_t * const p_osmt) req.sm_key = 0; status = osmv_query_sa( p_osmt->h_bind, &req ); - if( status != IB_SUCCESS ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_sa_class_port_info: ERR 0065: " - "ib_query failed (%s)\n", ib_get_err_str( status ) ); - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_sa_class_port_info: ERR 0065: " + "ib_query failed (%s)\n", ib_get_err_str( status ) ); + goto Exit; + } status = p_context->result.status; if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_sa_class_port_info: ERR 0070: " + "ib_query failed (%s)\n", ib_get_err_str( status ) ); + if( status == IB_REMOTE_ERROR ) { - if (status != IB_INVALID_PARAMETER) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_sa_class_port_info: ERR 0070: " - "ib_query failed (%s)\n", ib_get_err_str( status ) ); - } - if( status == IB_REMOTE_ERROR ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_sa_class_port_info: " - "Remote error = %s\n", - ib_get_mad_status_str( osm_madw_get_mad_ptr - ( p_context->result. - p_result_madw ) ) ); - } - goto Exit; + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_sa_class_port_info: " + "Remote error = %s\n", + ib_get_mad_status_str( osm_madw_get_mad_ptr + ( p_context->result.p_result_madw ) ) ); } + goto Exit; + } /* ok we got it so please print it out */ p_resp_sa_madp = (ib_sa_mad_t*)osm_madw_get_mad_ptr(context.result.p_result_madw); @@ -756,13 +750,13 @@ osmtest_validate_sa_class_port_info( IN osmtest_t * const p_osmt) ); Exit: - /* +#if 0 if( context.result.p_result_madw != NULL ) { osm_mad_pool_put( &p_osmt->mad_pool, context.result.p_result_madw ); context.result.p_result_madw = NULL; } - */ +#endif OSM_LOG_EXIT( &p_osmt->log ); return ( status ); @@ -783,12 +777,12 @@ osmtest_get_node_rec( IN osmtest_t * const p_osmt, OSM_LOG_ENTER( &p_osmt->log, osmtest_get_node_rec ); if( osm_log_is_active( &p_osmt->log, OSM_LOG_VERBOSE ) ) - { - osm_log( &p_osmt->log, OSM_LOG_VERBOSE, - "osmtest_get_node_rec: " - "Getting node record for 0x%016" PRIx64 "\n", - cl_ntoh64( node_guid ) ); - } + { + osm_log( &p_osmt->log, OSM_LOG_VERBOSE, + "osmtest_get_node_rec: " + "Getting node record for 0x%016" PRIx64 "\n", + cl_ntoh64( node_guid ) ); + } /* * Do a blocking query for this record in the subnet. @@ -797,9 +791,9 @@ osmtest_get_node_rec( IN osmtest_t * const p_osmt, * * The query structures are locals. */ - cl_memclr( &req, sizeof( req ) ); - cl_memclr( &user, sizeof( user ) ); - cl_memclr( &record, sizeof( record ) ); + memset( &req, 0, sizeof( req ) ); + memset( &user, 0, sizeof( user ) ); + memset( &record, 0, sizeof( record ) ); record.node_info.node_guid = node_guid; @@ -819,36 +813,31 @@ osmtest_get_node_rec( IN osmtest_t * const p_osmt, req.sm_key = 0; status = osmv_query_sa( p_osmt->h_bind, &req ); - if( status != IB_SUCCESS ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_get_node_rec: ERR 0071: " - "ib_query failed (%s)\n", ib_get_err_str( status ) ); - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_node_rec: ERR 0071: " + "ib_query failed (%s)\n", ib_get_err_str( status ) ); + goto Exit; + } status = p_context->result.status; if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_node_rec: ERR 0072: " + "ib_query failed (%s)\n", ib_get_err_str( status ) ); + if( status == IB_REMOTE_ERROR ) { - if (status != IB_INVALID_PARAMETER) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_get_node_rec: ERR 0072: " - "ib_query failed (%s)\n", ib_get_err_str( status ) ); - } - if( status == IB_REMOTE_ERROR ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_get_node_rec: " - "Remote error = %s\n", - ib_get_mad_status_str( osm_madw_get_mad_ptr - ( p_context->result. - p_result_madw ) ) ); - } - goto Exit; + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_node_rec: " + "Remote error = %s\n", + ib_get_mad_status_str( osm_madw_get_mad_ptr + ( p_context->result.p_result_madw ) ) ); } + goto Exit; + } Exit: OSM_LOG_EXIT( &p_osmt->log ); @@ -872,12 +861,12 @@ osmtest_get_node_rec_by_lid( IN osmtest_t * const p_osmt, OSM_LOG_ENTER( &p_osmt->log, osmtest_get_node_rec_by_lid ); if( osm_log_is_active( &p_osmt->log, OSM_LOG_VERBOSE ) ) - { - osm_log( &p_osmt->log, OSM_LOG_VERBOSE, - "osmtest_get_node_rec_by_lid: " - "Getting node record for LID 0x%02X\n", - cl_ntoh16( lid ) ); - } + { + osm_log( &p_osmt->log, OSM_LOG_VERBOSE, + "osmtest_get_node_rec_by_lid: " + "Getting node record for LID 0x%02X\n", + cl_ntoh16( lid ) ); + } /* * Do a blocking query for this record in the subnet. @@ -886,9 +875,9 @@ osmtest_get_node_rec_by_lid( IN osmtest_t * const p_osmt, * * The query structures are locals. */ - cl_memclr( &req, sizeof( req ) ); - cl_memclr( &user, sizeof( user ) ); - cl_memclr( &record, sizeof( record ) ); + memset( &req, 0, sizeof( req ) ); + memset( &user, 0, sizeof( user ) ); + memset( &record, 0, sizeof( record ) ); record.lid = lid; @@ -908,37 +897,33 @@ osmtest_get_node_rec_by_lid( IN osmtest_t * const p_osmt, req.sm_key = 0; status = osmv_query_sa( p_osmt->h_bind, &req ); - if( status != IB_SUCCESS ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_get_node_rec_by_lid: ERR 0073: " - "ib_query failed (%s)\n", ib_get_err_str( status ) ); - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_node_rec_by_lid: ERR 0073: " + "ib_query failed (%s)\n", ib_get_err_str( status ) ); + goto Exit; + } status = p_context->result.status; if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_node_rec_by_lid: ERR 0074: " + "ib_query failed (%s)\n", ib_get_err_str( status ) ); + if( status == IB_REMOTE_ERROR ) { - if (status != IB_INVALID_PARAMETER) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_get_node_rec_by_lid: ERR 0074: " - "ib_query failed (%s)\n", ib_get_err_str( status ) ); - } - if( status == IB_REMOTE_ERROR ) - { - p_mad = osm_madw_get_mad_ptr( p_context->result.p_result_madw ); - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_get_node_rec_by_lid: " - "Remote error = %s\n", - ib_get_mad_status_str( p_mad )); + p_mad = osm_madw_get_mad_ptr( p_context->result.p_result_madw ); + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_node_rec_by_lid: " + "Remote error = %s\n", + ib_get_mad_status_str( p_mad )); - status = (ib_net16_t) (p_mad->status & IB_SMP_STATUS_MASK ); - } - goto Exit; + status = (ib_net16_t) (p_mad->status & IB_SMP_STATUS_MASK ); } + goto Exit; + } Exit: OSM_LOG_EXIT( &p_osmt->log ); @@ -949,9 +934,9 @@ osmtest_get_node_rec_by_lid( IN osmtest_t * const p_osmt, **********************************************************************/ static ib_api_status_t osmtest_get_path_rec_by_guid_pair( IN osmtest_t * const p_osmt, - IN ib_net64_t sguid, - IN ib_net64_t dguid, - IN osmtest_req_context_t *p_context) + IN ib_net64_t sguid, + IN ib_net64_t dguid, + IN osmtest_req_context_t *p_context) { cl_status_t status = IB_SUCCESS; osmv_query_req_t req; @@ -959,7 +944,8 @@ osmtest_get_path_rec_by_guid_pair( IN osmtest_t * const p_osmt, OSM_LOG_ENTER( &p_osmt->log, osmtest_get_path_rec_by_guid_pair); - cl_memclr( p_context, sizeof( *p_context ) ); + memset( &req, 0, sizeof( req ) ); + memset( p_context, 0, sizeof( *p_context ) ); p_context->p_osmt = p_osmt; req.timeout_ms = p_osmt->opt.transaction_timeout; @@ -980,34 +966,34 @@ osmtest_get_path_rec_by_guid_pair( IN osmtest_t * const p_osmt, "osmtest_get_path_rec_by_guid_pair: " "Query for path from 0x%" PRIx64 " to 0x%" PRIx64"\n", sguid, dguid ); + status = osmv_query_sa( p_osmt->h_bind, &req ); if( status != IB_SUCCESS ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_get_path_rec_by_guid_pair: ERR 0063: " - "ib_query failed (%s)\n", ib_get_err_str( status ) ); - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_path_rec_by_guid_pair: ERR 0063: " + "ib_query failed (%s)\n", ib_get_err_str( status ) ); + goto Exit; + } status = (*p_context).result.status; if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_path_rec_by_guid_pair: ERR 0066: " + "ib_query failed (%s)\n", ib_get_err_str( status ) ); + + if( status == IB_REMOTE_ERROR ) { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_get_path_rec_by_guid_pair: ERR 0066: " - "ib_query failed (%s)\n", ib_get_err_str( status ) ); - - if( status == IB_REMOTE_ERROR ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_get_path_rec_by_guid_pair: " - "Remote error = %s\n", - ib_get_mad_status_str( osm_madw_get_mad_ptr - ( (*p_context).result. - p_result_madw ) ) ); - } - goto Exit; + "osmtest_get_path_rec_by_guid_pair: " + "Remote error = %s\n", + ib_get_mad_status_str( osm_madw_get_mad_ptr + ( (*p_context).result.p_result_madw ) ) ); } + goto Exit; + } Exit: @@ -1017,89 +1003,230 @@ osmtest_get_path_rec_by_guid_pair( IN osmtest_t * const p_osmt, /********************************************************************** **********************************************************************/ -ib_api_status_t -osmtest_get_port_rec( IN osmtest_t * const p_osmt, - IN ib_net16_t const lid, - IN OUT osmtest_req_context_t * const p_context ) +static ib_api_status_t +osmtest_get_path_rec_by_gid_pair( IN osmtest_t * const p_osmt, + IN ib_gid_t sgid, + IN ib_gid_t dgid, + IN osmtest_req_context_t *p_context) { - ib_api_status_t status = IB_SUCCESS; - osmv_user_query_t user; + cl_status_t status = IB_SUCCESS; osmv_query_req_t req; - ib_portinfo_record_t record; - - OSM_LOG_ENTER( &p_osmt->log, osmtest_get_port_rec ); - - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_get_port_rec: " - "Getting PortRecord for port with LID 0x%X\n", - cl_ntoh16( lid ) ); - } + osmv_gid_pair_t gid_pair; - /* - * Do a blocking query for this record in the subnet. - * The result is returned in the result field of the caller's - * context structure. - * - * The query structures are locals. - */ - cl_memclr( &req, sizeof( req ) ); - cl_memclr( &user, sizeof( user ) ); - cl_memclr( &record, sizeof( record ) ); + OSM_LOG_ENTER( &p_osmt->log, osmtest_get_path_rec_by_gid_pair); - record.lid = lid; + memset( &req, 0, sizeof( req ) ); + memset( p_context, 0, sizeof( *p_context ) ); p_context->p_osmt = p_osmt; - user.comp_mask = IB_PIR_COMPMASK_LID; - user.attr_id = IB_MAD_ATTR_PORTINFO_RECORD; - user.attr_offset = cl_ntoh16( ( uint16_t ) ( sizeof( record ) >> 3 ) ); - user.p_attr = &record; - - req.query_type = OSMV_QUERY_USER_DEFINED; req.timeout_ms = p_osmt->opt.transaction_timeout; req.retry_cnt = p_osmt->opt.retry_count; req.flags = OSM_SA_FLAGS_SYNC; req.query_context = p_context; req.pfn_query_cb = osmtest_query_res_cb; - req.p_query_input = &user; + + req.query_type = OSMV_QUERY_PATH_REC_BY_GIDS; + + gid_pair.dest_gid = dgid; + gid_pair.src_gid = sgid; + + req.p_query_input = &gid_pair; req.sm_key = 0; + osm_log( &p_osmt->log, OSM_LOG_VERBOSE, + "osmtest_get_path_rec_by_gid_pair: " + "Query for path from 0x%016" PRIx64 " 0x%016" PRIx64 " to 0x%016" PRIx64 " 0x%016" PRIx64"\n", + sgid.unicast.prefix, sgid.unicast.interface_id, + dgid.unicast.prefix, dgid.unicast.interface_id ); + status = osmv_query_sa( p_osmt->h_bind, &req ); + if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_path_rec_by_gid_pair: ERR 006A: " + "ib_query failed (%s)\n", ib_get_err_str( status ) ); + goto Exit; + } + + status = (*p_context).result.status; + if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_path_rec_by_gid_pair: ERR 006B: " + "ib_query failed (%s)\n", ib_get_err_str( status ) ); + + if( status == IB_REMOTE_ERROR ) { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_get_port_rec: ERR 0075: " - "ib_query failed (%s)\n", ib_get_err_str( status ) ); - goto Exit; + "osmtest_get_path_rec_by_gid_pair: " + "Remote error = %s\n", + ib_get_mad_status_str( osm_madw_get_mad_ptr + ( (*p_context).result.p_result_madw ) ) ); } + goto Exit; + } - status = p_context->result.status; + Exit: - if( status != IB_SUCCESS ) + OSM_LOG_EXIT( &p_osmt->log ); + return ( status ); +} + +#if defined (VENDOR_RMPP_SUPPORT) && defined (DUAL_SIDED_RMPP) +/********************************************************************** + **********************************************************************/ +static ib_api_status_t +osmtest_get_multipath_rec( IN osmtest_t * const p_osmt, + IN osmv_multipath_req_t *p_request, + IN osmtest_req_context_t *p_context) +{ + cl_status_t status = IB_SUCCESS; + osmv_query_req_t req; + + OSM_LOG_ENTER( &p_osmt->log, osmtest_get_multipath_rec ); + + /* + * Do a blocking query for this record in the subnet. + * The result is returned in the result field of the caller's + * context structure. + * + * The query structures are locals. + */ + memset( &req, 0, sizeof( req ) ); + + p_context->p_osmt = p_osmt; + req.timeout_ms = p_osmt->opt.transaction_timeout; + req.retry_cnt = p_osmt->opt.retry_count; + req.flags = OSM_SA_FLAGS_SYNC; + req.query_context = p_context; + req.pfn_query_cb = osmtest_query_res_cb; + + req.query_type = OSMV_QUERY_MULTIPATH_REC; + + req.p_query_input = p_request; + req.sm_key = 0; + + status = osmv_query_sa( p_osmt->h_bind, &req ); + if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_multipath_rec: ERR 0068: " + "ib_query failed (%s)\n", ib_get_err_str( status ) ); + goto Exit; + } + + status = p_context->result.status; + + if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_multipath_rec: ERR 0069: " + "ib_query failed (%s)\n", ib_get_err_str( status ) ); + + if( status == IB_REMOTE_ERROR ) { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_get_port_rec: ERR 0076: " - "ib_query failed (%s)\n", ib_get_err_str( status ) ); + "osmtest_get_multipath_rec: " + "Remote error = %s\n", + ib_get_mad_status_str( osm_madw_get_mad_ptr + ( p_context->result.p_result_madw ) ) ); + } + goto Exit; + } - if( status == IB_REMOTE_ERROR ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_get_port_rec: " - "Remote error = %s\n", - ib_get_mad_status_str( osm_madw_get_mad_ptr - ( p_context->result. - p_result_madw ) ) ); - } - goto Exit; + Exit: + OSM_LOG_EXIT( &p_osmt->log ); + return ( status ); +} +#endif + +/********************************************************************** + **********************************************************************/ +ib_api_status_t +osmtest_get_port_rec( IN osmtest_t * const p_osmt, + IN ib_net16_t const lid, + IN OUT osmtest_req_context_t * const p_context ) +{ + ib_api_status_t status = IB_SUCCESS; + osmv_user_query_t user; + osmv_query_req_t req; + ib_portinfo_record_t record; + + OSM_LOG_ENTER( &p_osmt->log, osmtest_get_port_rec ); + + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) + { + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_get_port_rec: " + "Getting PortInfoRecord for port with LID 0x%X\n", + cl_ntoh16( lid ) ); + } + + /* + * Do a blocking query for this record in the subnet. + * The result is returned in the result field of the caller's + * context structure. + * + * The query structures are locals. + */ + memset( &req, 0, sizeof( req ) ); + memset( &user, 0, sizeof( user ) ); + memset( &record, 0, sizeof( record ) ); + + record.lid = lid; + + p_context->p_osmt = p_osmt; + user.comp_mask = IB_PIR_COMPMASK_LID; + user.attr_id = IB_MAD_ATTR_PORTINFO_RECORD; + user.attr_offset = cl_ntoh16( ( uint16_t ) ( sizeof( record ) >> 3 ) ); + user.p_attr = &record; + + req.query_type = OSMV_QUERY_USER_DEFINED; + req.timeout_ms = p_osmt->opt.transaction_timeout; + req.retry_cnt = p_osmt->opt.retry_count; + req.flags = OSM_SA_FLAGS_SYNC; + req.query_context = p_context; + req.pfn_query_cb = osmtest_query_res_cb; + req.p_query_input = &user; + req.sm_key = 0; + + status = osmv_query_sa( p_osmt->h_bind, &req ); + if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_port_rec: ERR 0075: " + "ib_query failed (%s)\n", ib_get_err_str( status ) ); + goto Exit; + } + + status = p_context->result.status; + + if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_port_rec: ERR 0076: " + "ib_query failed (%s)\n", ib_get_err_str( status ) ); + + if( status == IB_REMOTE_ERROR ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_port_rec: " + "Remote error = %s\n", + ib_get_mad_status_str( osm_madw_get_mad_ptr + ( p_context->result.p_result_madw ) ) ); } + goto Exit; + } Exit: OSM_LOG_EXIT( &p_osmt->log ); return ( status ); } +/********************************************************************** + **********************************************************************/ ib_api_status_t osmtest_get_port_rec_by_num( IN osmtest_t * const p_osmt, IN ib_net16_t const lid, @@ -1112,16 +1239,16 @@ osmtest_get_port_rec_by_num( IN osmtest_t * const p_osmt, ib_portinfo_record_t record; ib_mad_t *p_mad; - OSM_LOG_ENTER( &p_osmt->log, osmtest_get_port_rec ); + OSM_LOG_ENTER( &p_osmt->log, osmtest_get_port_rec_by_num ); if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_get_port_rec_by_num: " - "Getting PortRecord for port with LID 0x%X Num:0x%X\n", - cl_ntoh16( lid ), - port_num); - } + { + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_get_port_rec_by_num: " + "Getting PortInfoRecord for port with LID 0x%X Num:0x%X\n", + cl_ntoh16( lid ), + port_num); + } /* * Do a blocking query for this record in the subnet. @@ -1130,9 +1257,9 @@ osmtest_get_port_rec_by_num( IN osmtest_t * const p_osmt, * * The query structures are locals. */ - cl_memclr( &req, sizeof( req ) ); - cl_memclr( &user, sizeof( user ) ); - cl_memclr( &record, sizeof( record ) ); + memset( &req, 0, sizeof( req ) ); + memset( &user, 0, sizeof( user ) ); + memset( &record, 0, sizeof( record ) ); record.lid = lid; record.port_num = port_num; @@ -1150,37 +1277,33 @@ osmtest_get_port_rec_by_num( IN osmtest_t * const p_osmt, req.sm_key = 0; status = osmv_query_sa( p_osmt->h_bind, &req ); - if( status != IB_SUCCESS ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_get_port_rec_by_num: ERR 0077: " - "ib_query failed (%s)\n", ib_get_err_str( status ) ); - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_port_rec_by_num: ERR 0077: " + "ib_query failed (%s)\n", ib_get_err_str( status ) ); + goto Exit; + } status = p_context->result.status; if( status != IB_SUCCESS ) - { - if (status != IB_INVALID_PARAMETER) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_get_port_rec_by_num: ERR 0078: " - "ib_query failed (%s)\n", ib_get_err_str( status ) ); - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_port_rec_by_num: ERR 0078: " + "ib_query failed (%s)\n", ib_get_err_str( status ) ); - if( status == IB_REMOTE_ERROR ) - { - p_mad = osm_madw_get_mad_ptr( p_context->result.p_result_madw ); - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_get_port_rec_by_num: " - "Remote error = %s\n", - ib_get_mad_status_str( p_mad )); - status = (ib_net16_t) (p_mad->status & IB_SMP_STATUS_MASK ); - } - goto Exit; + if( status == IB_REMOTE_ERROR ) + { + p_mad = osm_madw_get_mad_ptr( p_context->result.p_result_madw ); + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_port_rec_by_num: " + "Remote error = %s\n", + ib_get_mad_status_str( p_mad )); + status = (ib_net16_t) (p_mad->status & IB_SMP_STATUS_MASK ); } + goto Exit; + } Exit: OSM_LOG_EXIT( &p_osmt->log ); @@ -1202,21 +1325,21 @@ osmtest_stress_port_recs_large( IN osmtest_t * const p_osmt, OSM_LOG_ENTER( &p_osmt->log, osmtest_stress_port_recs_large ); - cl_memclr( &context, sizeof( context ) ); + memset( &context, 0, sizeof( context ) ); /* - * Do a blocking query for all NodeRecords in the subnet. + * Do a blocking query for all PortInfoRecords in the subnet. */ status = osmtest_get_all_recs( p_osmt, IB_MAD_ATTR_PORTINFO_RECORD, sizeof( *p_rec ), &context ); if( status != IB_SUCCESS ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_stress_port_recs_large: ERR 0006: " - "osmtest_get_all_recs failed (%s)\n", - ib_get_err_str( status ) ); - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_stress_port_recs_large: ERR 0006: " + "osmtest_get_all_recs failed (%s)\n", + ib_get_err_str( status ) ); + goto Exit; + } /* * Populate the database with the received records. @@ -1226,28 +1349,27 @@ osmtest_stress_port_recs_large( IN osmtest_t * const p_osmt, ++*p_num_queries; if( osm_log_is_active( &p_osmt->log, OSM_LOG_VERBOSE ) ) - { - osm_log( &p_osmt->log, OSM_LOG_VERBOSE, - "osmtest_stress_port_recs_large: " - "Received %u records\n", num_recs ); + { + osm_log( &p_osmt->log, OSM_LOG_VERBOSE, + "osmtest_stress_port_recs_large: " + "Received %u records\n", num_recs ); - for( i = 0; i < num_recs; i++ ) - { - p_rec = - osmv_get_query_portinfo_rec( context.result.p_result_madw, i ); - osm_dump_portinfo_record( &p_osmt->log, p_rec, OSM_LOG_VERBOSE ); - } + for( i = 0; i < num_recs; i++ ) + { + p_rec = osmv_get_query_portinfo_rec( context.result.p_result_madw, i ); + osm_dump_portinfo_record( &p_osmt->log, p_rec, OSM_LOG_VERBOSE ); } + } Exit: /* * Return the IB query MAD to the pool as necessary. */ if( context.result.p_result_madw != NULL ) - { - osm_mad_pool_put( &p_osmt->mad_pool, context.result.p_result_madw ); - context.result.p_result_madw = NULL; - } + { + osm_mad_pool_put( &p_osmt->mad_pool, context.result.p_result_madw ); + context.result.p_result_madw = NULL; + } OSM_LOG_EXIT( &p_osmt->log ); return ( status ); @@ -1268,7 +1390,7 @@ osmtest_stress_node_recs_large( IN osmtest_t * const p_osmt, OSM_LOG_ENTER( &p_osmt->log, osmtest_stress_node_recs_large ); - cl_memclr( &context, sizeof( context ) ); + memset( &context, 0, sizeof( context ) ); /* * Do a blocking query for all NodeRecords in the subnet. @@ -1277,13 +1399,13 @@ osmtest_stress_node_recs_large( IN osmtest_t * const p_osmt, sizeof( *p_rec ), &context ); if( status != IB_SUCCESS ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_stress_node_recs_large: ERR 0007: " - "osmtest_get_all_recs failed (%s)\n", - ib_get_err_str( status ) ); - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_stress_node_recs_large: ERR 0007: " + "osmtest_get_all_recs failed (%s)\n", + ib_get_err_str( status ) ); + goto Exit; + } /* * Populate the database with the received records. @@ -1293,27 +1415,27 @@ osmtest_stress_node_recs_large( IN osmtest_t * const p_osmt, ++*p_num_queries; if( osm_log_is_active( &p_osmt->log, OSM_LOG_VERBOSE ) ) - { - osm_log( &p_osmt->log, OSM_LOG_VERBOSE, - "osmtest_stress_node_recs_large: " - "Received %u records\n", num_recs ); + { + osm_log( &p_osmt->log, OSM_LOG_VERBOSE, + "osmtest_stress_node_recs_large: " + "Received %u records\n", num_recs ); - for( i = 0; i < num_recs; i++ ) - { - p_rec = osmv_get_query_node_rec( context.result.p_result_madw, i ); - osm_dump_node_record( &p_osmt->log, p_rec, OSM_LOG_VERBOSE ); - } + for( i = 0; i < num_recs; i++ ) + { + p_rec = osmv_get_query_node_rec( context.result.p_result_madw, i ); + osm_dump_node_record( &p_osmt->log, p_rec, OSM_LOG_VERBOSE ); } + } Exit: /* * Return the IB query MAD to the pool as necessary. */ if( context.result.p_result_madw != NULL ) - { - osm_mad_pool_put( &p_osmt->mad_pool, context.result.p_result_madw ); - context.result.p_result_madw = NULL; - } + { + osm_mad_pool_put( &p_osmt->mad_pool, context.result.p_result_madw ); + context.result.p_result_madw = NULL; + } OSM_LOG_EXIT( &p_osmt->log ); return ( status ); @@ -1334,21 +1456,21 @@ osmtest_stress_path_recs_large( IN osmtest_t * const p_osmt, OSM_LOG_ENTER( &p_osmt->log, osmtest_stress_path_recs_large ); - cl_memclr( &context, sizeof( context ) ); + memset( &context, 0, sizeof( context ) ); /* - * Do a blocking query for all Records in the subnet. + * Do a blocking query for all PathRecords in the subnet. */ status = osmtest_get_all_recs( p_osmt, IB_MAD_ATTR_PATH_RECORD, sizeof( *p_rec ), &context ); if( status != IB_SUCCESS ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_stress_path_recs_large: ERR 0008: " - "osmtest_get_all_recs failed (%s)\n", - ib_get_err_str( status ) ); - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_stress_path_recs_large: ERR 0008: " + "osmtest_get_all_recs failed (%s)\n", + ib_get_err_str( status ) ); + goto Exit; + } /* * Populate the database with the received records. @@ -1358,27 +1480,27 @@ osmtest_stress_path_recs_large( IN osmtest_t * const p_osmt, ++*p_num_queries; if( osm_log_is_active( &p_osmt->log, OSM_LOG_VERBOSE ) ) - { - osm_log( &p_osmt->log, OSM_LOG_VERBOSE, - "osmtest_stress_path_recs_large: " - "Received %u records\n", num_recs ); + { + osm_log( &p_osmt->log, OSM_LOG_VERBOSE, + "osmtest_stress_path_recs_large: " + "Received %u records\n", num_recs ); - for( i = 0; i < num_recs; i++ ) - { - p_rec = osmv_get_query_path_rec( context.result.p_result_madw, i ); - osm_dump_path_record( &p_osmt->log, p_rec, OSM_LOG_VERBOSE ); - } + for( i = 0; i < num_recs; i++ ) + { + p_rec = osmv_get_query_path_rec( context.result.p_result_madw, i ); + osm_dump_path_record( &p_osmt->log, p_rec, OSM_LOG_VERBOSE ); } + } Exit: /* * Return the IB query MAD to the pool as necessary. */ if( context.result.p_result_madw != NULL ) - { - osm_mad_pool_put( &p_osmt->mad_pool, context.result.p_result_madw ); - context.result.p_result_madw = NULL; - } + { + osm_mad_pool_put( &p_osmt->mad_pool, context.result.p_result_madw ); + context.result.p_result_madw = NULL; + } OSM_LOG_EXIT( &p_osmt->log ); return ( status ); @@ -1401,7 +1523,7 @@ osmtest_stress_path_recs_by_guid ( IN osmtest_t * const p_osmt, OSM_LOG_ENTER( &p_osmt->log, osmtest_stress_path_recs_by_guid ); - cl_memclr( &context, sizeof( context ) ); + memset( &context, 0, sizeof( context ) ); context.p_osmt = p_osmt; @@ -1409,77 +1531,82 @@ osmtest_stress_path_recs_by_guid ( IN osmtest_t * const p_osmt, p_src_node = ( node_t * ) cl_qmap_head( p_tbl ); - /* + /* * Go over all nodes that exist in the subnet * for each pair that are not switch nodes get the path record */ - while( p_src_node != ( node_t * ) cl_qmap_end( p_tbl ) ) { + while( p_src_node != ( node_t * ) cl_qmap_end( p_tbl ) ) + { p_dst_node = ( node_t * ) cl_qmap_head( p_tbl ); - while( p_dst_node != ( node_t * ) cl_qmap_end( p_tbl ) ) { + while( p_dst_node != ( node_t * ) cl_qmap_end( p_tbl ) ) + { /* - * Do a blocking query for CA to CA Path Record - */ - osm_log(&p_osmt->log, OSM_LOG_VERBOSE, - "osmtest_stress_path_recs_by_guid:" - "Source : guid = 0x%" PRIx64 " type = %d" - "Target : guid = 0x%" PRIx64 " type = %d\n", - cl_ntoh64(p_src_node->rec.node_info.port_guid),p_src_node->rec.node_info.node_type, - cl_ntoh64(p_dst_node->rec.node_info.port_guid),p_dst_node->rec.node_info.node_type); - - if (p_src_node->rec.node_info.node_type == IB_NODE_TYPE_CA - && p_dst_node->rec.node_info.node_type == IB_NODE_TYPE_CA) - { - status = osmtest_get_path_rec_by_guid_pair(p_osmt, + * Do a blocking query for CA to CA Path Record + */ + osm_log(&p_osmt->log, OSM_LOG_VERBOSE, + "osmtest_stress_path_recs_by_guid:" + "Source : guid = 0x%" PRIx64 " type = %d" + "Target : guid = 0x%" PRIx64 " type = %d\n", + cl_ntoh64(p_src_node->rec.node_info.port_guid), + p_src_node->rec.node_info.node_type, + cl_ntoh64(p_dst_node->rec.node_info.port_guid), + p_dst_node->rec.node_info.node_type); + + if (p_src_node->rec.node_info.node_type == IB_NODE_TYPE_CA && + p_dst_node->rec.node_info.node_type == IB_NODE_TYPE_CA) + { + status = osmtest_get_path_rec_by_guid_pair(p_osmt, p_src_node->rec.node_info.port_guid, p_dst_node->rec.node_info.port_guid, &context); - /* In a case of TIMEOUT you still can try sending but cant count, maybe its a temporary issue */ - if( status != IB_SUCCESS ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_stress_path_recs_by_guid: ERR 0009: " - "osmtest_get_path_rec_by_guid_pair failed (%s)\n", - ib_get_err_str( status ) ); - if (status != IB_TIMEOUT) - goto Exit; - } - else - { - /* we might have received several records */ - num_recs = context.result.result_cnt; - /* - * Populate the database with the received records. - */ - *p_num_recs += num_recs; - ++*p_num_queries; - if( osm_log_is_active( &p_osmt->log, OSM_LOG_VERBOSE ) ) - osm_log( &p_osmt->log, OSM_LOG_VERBOSE, - "osmtest_stress_path_recs_by_guid: " - "Received %u records\n", num_recs ); - /* Dont waste time if not VERBOSE and above */ - if (p_osmt->log.level & OSM_LOG_VERBOSE) { - for (i = 0; i < num_recs; i++) { - p_rec = osmv_get_query_path_rec( context.result.p_result_madw, i); - osm_dump_path_record(&p_osmt->log,p_rec,OSM_LOG_VERBOSE); - } - } - } - if( context.result.p_result_madw != NULL ) - { - osm_mad_pool_put( &p_osmt->mad_pool, context.result.p_result_madw ); - context.result.p_result_madw = NULL; - } + /* In a case of TIMEOUT you still can try sending but cant count, maybe its a temporary issue */ + if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_stress_path_recs_by_guid: ERR 0009: " + "osmtest_get_path_rec_by_guid_pair failed (%s)\n", + ib_get_err_str( status ) ); + if (status != IB_TIMEOUT) + goto Exit; + } + else + { + /* we might have received several records */ + num_recs = context.result.result_cnt; + /* + * Populate the database with the received records. + */ + *p_num_recs += num_recs; + ++*p_num_queries; + if( osm_log_is_active( &p_osmt->log, OSM_LOG_VERBOSE ) ) + osm_log( &p_osmt->log, OSM_LOG_VERBOSE, + "osmtest_stress_path_recs_by_guid: " + "Received %u records\n", num_recs ); + /* Dont waste time if not VERBOSE and above */ + if (p_osmt->log.level & OSM_LOG_VERBOSE) + { + for (i = 0; i < num_recs; i++) + { + p_rec = osmv_get_query_path_rec( context.result.p_result_madw, i); + osm_dump_path_record(&p_osmt->log,p_rec,OSM_LOG_VERBOSE); + } + } + } + if( context.result.p_result_madw != NULL ) + { + osm_mad_pool_put( &p_osmt->mad_pool, context.result.p_result_madw ); + context.result.p_result_madw = NULL; } - /* next one please */ - p_dst_node = ( node_t * ) cl_qmap_next( &p_dst_node->map_item ); } - /* } */ - - p_src_node = ( node_t * ) cl_qmap_next( &p_src_node->map_item ); + /* next one please */ + p_dst_node = ( node_t * ) cl_qmap_next( &p_dst_node->map_item ); } + p_src_node = ( node_t * ) cl_qmap_next( &p_src_node->map_item ); + } + Exit: OSM_LOG_EXIT( &p_osmt->log ); return ( status ); @@ -1500,24 +1627,24 @@ osmtest_stress_port_recs_small( IN osmtest_t * const p_osmt, OSM_LOG_ENTER( &p_osmt->log, osmtest_stress_port_recs_small ); - cl_memclr( &context, sizeof( context ) ); + memset( &context, 0, sizeof( context ) ); /* - * Do a blocking query for our own PortRecord in the subnet. + * Do a blocking query for our own PortInfoRecord in the subnet. */ status = osmtest_get_port_rec( p_osmt, cl_ntoh16(p_osmt->local_port.lid), &context ); if( status != IB_SUCCESS ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_stress_port_recs_small: ERR 0010: " - "osmtest_get_all_recs failed (%s)\n", - ib_get_err_str( status ) ); - goto Exit; - } - + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_stress_port_recs_small: ERR 0010: " + "osmtest_get_port_rec failed (%s)\n", + ib_get_err_str( status ) ); + goto Exit; + } + /* * Populate the database with the received records. */ @@ -1526,28 +1653,96 @@ osmtest_stress_port_recs_small( IN osmtest_t * const p_osmt, ++*p_num_queries; if( osm_log_is_active( &p_osmt->log, OSM_LOG_VERBOSE ) ) - { - osm_log( &p_osmt->log, OSM_LOG_VERBOSE, - "osmtest_stress_port_recs_small: " - "Received %u records\n", num_recs ); + { + osm_log( &p_osmt->log, OSM_LOG_VERBOSE, + "osmtest_stress_port_recs_small: " + "Received %u records\n", num_recs ); - for( i = 0; i < num_recs; i++ ) - { - p_rec = - osmv_get_query_portinfo_rec( context.result.p_result_madw, i ); - osm_dump_portinfo_record( &p_osmt->log, p_rec, OSM_LOG_VERBOSE ); - } + for( i = 0; i < num_recs; i++ ) + { + p_rec = osmv_get_query_portinfo_rec( context.result.p_result_madw, i ); + osm_dump_portinfo_record( &p_osmt->log, p_rec, OSM_LOG_VERBOSE ); } + } Exit: /* * Return the IB query MAD to the pool as necessary. */ if( context.result.p_result_madw != NULL ) + { + osm_mad_pool_put( &p_osmt->mad_pool, context.result.p_result_madw ); + context.result.p_result_madw = NULL; + } + + OSM_LOG_EXIT( &p_osmt->log ); + return ( status ); +} + +/********************************************************************** + **********************************************************************/ +ib_api_status_t +osmtest_get_local_port_lmc( IN osmtest_t * const p_osmt, + IN ib_net16_t lid, + OUT uint8_t * const p_lmc ) +{ + osmtest_req_context_t context; + ib_portinfo_record_t *p_rec; + uint32_t i; + cl_status_t status; + uint32_t num_recs = 0; + + OSM_LOG_ENTER( &p_osmt->log, osmtest_get_local_port_lmc ); + + memset( &context, 0, sizeof( context ) ); + + /* + * Do a blocking query for our own PortInfoRecord in the subnet. + */ + status = osmtest_get_port_rec( p_osmt, + cl_ntoh16( lid ), + &context ); + + if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_local_port_lmc: ERR 001A: " + "osmtest_get_port_rec failed (%s)\n", + ib_get_err_str( status ) ); + goto Exit; + } + + num_recs = context.result.result_cnt; + + if( osm_log_is_active( &p_osmt->log, OSM_LOG_VERBOSE ) ) + { + osm_log( &p_osmt->log, OSM_LOG_VERBOSE, + "osmtest_get_local_port_lmc: " + "Received %u records\n", num_recs ); + } + + for( i = 0; i < num_recs; i++ ) + { + p_rec = osmv_get_query_portinfo_rec( context.result.p_result_madw, i ); + osm_dump_portinfo_record( &p_osmt->log, p_rec, OSM_LOG_VERBOSE ); + if ( p_lmc) { - osm_mad_pool_put( &p_osmt->mad_pool, context.result.p_result_madw ); - context.result.p_result_madw = NULL; + *p_lmc = ib_port_info_get_lmc( &p_rec->port_info ); + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_get_local_port_lmc: " + "LMC %d\n", *p_lmc ); } + } + + Exit: + /* + * Return the IB query MAD to the pool as necessary. + */ + if( context.result.p_result_madw != NULL ) + { + osm_mad_pool_put( &p_osmt->mad_pool, context.result.p_result_madw ); + context.result.p_result_madw = NULL; + } OSM_LOG_EXIT( &p_osmt->log ); return ( status ); @@ -1568,16 +1763,16 @@ osmtest_wrong_sm_key_ignored( IN osmtest_t * const p_osmt) osmtest_req_context_t *p_context = &context; uint8_t port_num = 1; - OSM_LOG_ENTER( &p_osmt->log, osmtest_get_port_rec ); + OSM_LOG_ENTER( &p_osmt->log, osmtest_wrong_sm_key_ignored ); if( osm_log_is_active( &p_osmt->log, OSM_LOG_INFO ) ) - { - osm_log( &p_osmt->log, OSM_LOG_INFO, - "osmtest_wrong_sm_key_ignored: " - "Try PortRecord for port with LID 0x%X Num:0x%X\n", - cl_ntoh16( p_osmt->local_port.sm_lid ), - port_num); - } + { + osm_log( &p_osmt->log, OSM_LOG_INFO, + "osmtest_wrong_sm_key_ignored: " + "Trying PortInfoRecord for port with LID 0x%X Num:0x%X\n", + p_osmt->local_port.sm_lid, + port_num ); + } /* * Do a blocking query for this record in the subnet. @@ -1586,9 +1781,9 @@ osmtest_wrong_sm_key_ignored( IN osmtest_t * const p_osmt) * * The query structures are locals. */ - cl_memclr( &req, sizeof( req ) ); - cl_memclr( &user, sizeof( user ) ); - cl_memclr( &record, sizeof( record ) ); + memset( &req, 0, sizeof( req ) ); + memset( &user, 0, sizeof( user ) ); + memset( &record, 0, sizeof( record ) ); record.lid = p_osmt->local_port.sm_lid; record.port_num = port_num; @@ -1606,27 +1801,36 @@ osmtest_wrong_sm_key_ignored( IN osmtest_t * const p_osmt) req.sm_key = 9999; context.result.p_result_madw = NULL; + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_wrong_sm_key_ignored: " EXPECTING_ERRORS_START "\n" ); status = osmv_query_sa( p_osmt->h_bind, &req ); + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_wrong_sm_key_ignored: " EXPECTING_ERRORS_END "\n" ); /* since we use a wrong sm_key we should get a timeout */ if( status != IB_TIMEOUT ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_wrong_sm_key_ignored: ERR 0011: " + "Did not get a timeout but got (%s)\n", ib_get_err_str( status ) ); + if ( status == IB_SUCCESS ) { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_wrong_sm_key_ignored: ERR 0011: " - "Did not get a timeout but got (%s)\n", ib_get_err_str( status ) ); - goto Exit; + /* assign some error value to status, since IB_SUCCESS is a bad rc */ + status = IB_ERROR; } + goto Exit; + } else - { - status = IB_SUCCESS; - } + { + status = IB_SUCCESS; + } Exit: if( context.result.p_result_madw != NULL ) - { - osm_mad_pool_put( &p_osmt->mad_pool, context.result.p_result_madw ); - context.result.p_result_madw = NULL; - } + { + osm_mad_pool_put( &p_osmt->mad_pool, context.result.p_result_madw ); + context.result.p_result_madw = NULL; + } OSM_LOG_EXIT( &p_osmt->log ); return ( status ); @@ -1716,12 +1920,12 @@ osmtest_write_port_info( IN osmtest_t * const p_osmt, p_rec->port_info.error_threshold ); if( result < 0 ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_write_port_info: ERR 001: " "Write failed\n" ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_write_port_info: ERR 0161: " "Write failed\n" ); + status = IB_ERROR; + goto Exit; + } Exit: OSM_LOG_EXIT( &p_osmt->log ); @@ -1766,12 +1970,12 @@ osmtest_write_path_info( IN osmtest_t * const p_osmt, p_rec->preference ); if( result < 0 ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_write_path_info: ERR 002: " "Write failed\n" ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_write_path_info: ERR 0162: " "Write failed\n" ); + status = IB_ERROR; + goto Exit; + } Exit: OSM_LOG_EXIT( &p_osmt->log ); @@ -1787,9 +1991,13 @@ osmtest_write_node_info( IN osmtest_t * const p_osmt, { int result; cl_status_t status = IB_SUCCESS; + char desc[IB_NODE_DESCRIPTION_SIZE + 1]; OSM_LOG_ENTER( &p_osmt->log, osmtest_write_node_info ); + memcpy(desc, p_rec->node_desc.description, IB_NODE_DESCRIPTION_SIZE); + desc[IB_NODE_DESCRIPTION_SIZE] = '\0'; + result = fprintf( fh, "DEFINE_NODE\n" "lid 0x%X\n" @@ -1822,24 +2030,21 @@ osmtest_write_node_info( IN osmtest_t * const p_osmt, ib_node_info_get_local_port_num( &p_rec->node_info ), cl_ntoh32( ib_node_info_get_vendor_id ( &p_rec->node_info ) ), - p_rec->node_desc.description ); + desc ); if( result < 0 ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_write_node_info: ERR 003: " "Write failed\n" ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_write_node_info: ERR 0163: " "Write failed\n" ); + status = IB_ERROR; + goto Exit; + } Exit: OSM_LOG_EXIT( &p_osmt->log ); return ( status ); } -#if 0 -/* HACK: we do not support link records for now. */ - /********************************************************************** **********************************************************************/ static ib_api_status_t @@ -1864,12 +2069,12 @@ osmtest_write_link( IN osmtest_t * const p_osmt, p_rec->to_port_num, cl_ntoh16( p_rec->to_lid ) ); if( result < 0 ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_write_link: ERR 004: " "Write failed\n" ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_write_link: ERR 0164: " "Write failed\n" ); + status = IB_ERROR; + goto Exit; + } Exit: OSM_LOG_EXIT( &p_osmt->log ); @@ -1891,7 +2096,7 @@ osmtest_write_all_link_recs( IN osmtest_t * const p_osmt, OSM_LOG_ENTER( &p_osmt->log, osmtest_write_all_link_recs ); - cl_memclr( &context, sizeof( context ) ); + memset( &context, 0, sizeof( context ) ); /* * Do a blocking query for all NodeRecords in the subnet. @@ -1900,13 +2105,13 @@ osmtest_write_all_link_recs( IN osmtest_t * const p_osmt, sizeof( *p_rec ), &context ); if( status != IB_SUCCESS ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_write_all_link_recs: ERR 005: " - "osmtest_get_all_recs failed (%s)\n", - ib_get_err_str( status ) ); - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_write_all_link_recs: ERR 0165: " + "osmtest_get_all_recs failed (%s)\n", + ib_get_err_str( status ) ); + goto Exit; + } /* * Write the received records out to the file. @@ -1914,45 +2119,43 @@ osmtest_write_all_link_recs( IN osmtest_t * const p_osmt, num_recs = context.result.result_cnt; if( osm_log_is_active( &p_osmt->log, OSM_LOG_VERBOSE ) ) - { - osm_log( &p_osmt->log, OSM_LOG_VERBOSE, - "osmtest_write_all_link_recs: " - "Received %u records\n", num_recs ); - } + { + osm_log( &p_osmt->log, OSM_LOG_VERBOSE, + "osmtest_write_all_link_recs: " + "Received %zu records\n", num_recs ); + } result = fprintf( fh, "#\n" "# Link Records\n" "#\n" ); if( result < 0 ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_write_all_link_recs: ERR 006: " - "Write failed\n" ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_write_all_link_recs: ERR 0166: " + "Write failed\n" ); + status = IB_ERROR; + goto Exit; + } for( i = 0; i < num_recs; i++ ) - { - p_rec = - ( ib_link_record_t * ) osmv_get_query_result( context.result. - p_result_madw, i ); + { + p_rec = ( ib_link_record_t * ) osmv_get_query_result( context.result. + p_result_madw, i ); - osmtest_write_link( p_osmt, fh, p_rec ); - } + osmtest_write_link( p_osmt, fh, p_rec ); + } Exit: /* * Return the IB query MAD to the pool as necessary. */ if( context.result.p_result_madw != NULL ) - { - osm_mad_pool_put( &p_osmt->mad_pool, context.result.p_result_madw ); - context.result.p_result_madw = NULL; - } + { + osm_mad_pool_put( &p_osmt->mad_pool, context.result.p_result_madw ); + context.result.p_result_madw = NULL; + } OSM_LOG_EXIT( &p_osmt->log ); return ( status ); } -#endif /********************************************************************** **********************************************************************/ @@ -1960,15 +2163,16 @@ static ib_api_status_t osmtest_get_path_rec_by_lid_pair( IN osmtest_t * const p_osmt, IN ib_net16_t slid, IN ib_net16_t dlid, - IN osmtest_req_context_t *p_context) + IN osmtest_req_context_t *p_context ) { cl_status_t status = IB_SUCCESS; osmv_query_req_t req; osmv_lid_pair_t lid_pair; - OSM_LOG_ENTER( &p_osmt->log, osmtest_get_path_rec_by_lid_pair); + OSM_LOG_ENTER( &p_osmt->log, osmtest_get_path_rec_by_lid_pair ); - cl_memclr( p_context, sizeof( *p_context ) ); + memset( &req, 0, sizeof( req ) ); + memset( p_context, 0, sizeof( *p_context ) ); p_context->p_osmt = p_osmt; req.timeout_ms = p_osmt->opt.transaction_timeout; @@ -1991,43 +2195,41 @@ osmtest_get_path_rec_by_lid_pair( IN osmtest_t * const p_osmt, slid,dlid ); status = osmv_query_sa( p_osmt->h_bind, &req ); if( status != IB_SUCCESS ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_get_path_rec_by_lid_pair: ERR 0053: " - "ib_query failed (%s)\n", ib_get_err_str( status ) ); - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_path_rec_by_lid_pair: ERR 0053: " + "ib_query failed (%s)\n", ib_get_err_str( status ) ); + goto Exit; + } status = (*p_context).result.status; if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_path_rec_by_lid_pair: ERR 0067: " + "ib_query failed (%s)\n", ib_get_err_str( status ) ); + + if( status == IB_REMOTE_ERROR ) { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_get_path_rec_by_lid_pair: ERR 0067: " - "ib_query failed (%s)\n", ib_get_err_str( status ) ); - - if( status == IB_REMOTE_ERROR ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_get_path_rec_by_lid_pair: " - "Remote error = %s\n", - ib_get_mad_status_str( osm_madw_get_mad_ptr - ( (*p_context).result. - p_result_madw ) ) ); - } - goto Exit; + "osmtest_get_path_rec_by_lid_pair: " + "Remote error = %s\n", + ib_get_mad_status_str( osm_madw_get_mad_ptr + ( (*p_context).result.p_result_madw ) ) ); } + goto Exit; + } Exit: - OSM_LOG_EXIT( &p_osmt->log ); return ( status ); } #ifdef VENDOR_RMPP_SUPPORT /********************************************************************** -ASSUMES RMPP IMPL -**********************************************************************/ + * ASSUMES RMPP + **********************************************************************/ static ib_api_status_t osmtest_write_all_node_recs( IN osmtest_t * const p_osmt, IN FILE * fh ) @@ -2041,7 +2243,7 @@ osmtest_write_all_node_recs( IN osmtest_t * const p_osmt, OSM_LOG_ENTER( &p_osmt->log, osmtest_write_all_node_recs ); - cl_memclr( &context, sizeof( context ) ); + memset( &context, 0, sizeof( context ) ); /* * Do a blocking query for all NodeRecords in the subnet. @@ -2050,13 +2252,13 @@ osmtest_write_all_node_recs( IN osmtest_t * const p_osmt, sizeof( *p_rec ), &context ); if( status != IB_SUCCESS ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_write_all_node_recs: ERR 0022: " - "osmtest_get_all_recs failed (%s)\n", - ib_get_err_str( status ) ); - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_write_all_node_recs: ERR 0022: " + "osmtest_get_all_recs failed (%s)\n", + ib_get_err_str( status ) ); + goto Exit; + } /* * Write the received records out to the file. @@ -2064,37 +2266,37 @@ osmtest_write_all_node_recs( IN osmtest_t * const p_osmt, num_recs = context.result.result_cnt; if( osm_log_is_active( &p_osmt->log, OSM_LOG_VERBOSE ) ) - { - osm_log( &p_osmt->log, OSM_LOG_VERBOSE, - "osmtest_write_all_node_recs: " - "Received %u records\n", num_recs ); - } + { + osm_log( &p_osmt->log, OSM_LOG_VERBOSE, + "osmtest_write_all_node_recs: " + "Received %zu records\n", num_recs ); + } result = fprintf( fh, "#\n" "# Node Records\n" "#\n" ); if( result < 0 ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_write_all_node_recs: ERR 0023: " - "Write failed\n" ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_write_all_node_recs: ERR 0023: " + "Write failed\n" ); + status = IB_ERROR; + goto Exit; + } for( i = 0; i < num_recs; i++ ) - { - p_rec = osmv_get_query_node_rec( context.result.p_result_madw, i ); - osmtest_write_node_info( p_osmt, fh, p_rec ); - } + { + p_rec = osmv_get_query_node_rec( context.result.p_result_madw, i ); + osmtest_write_node_info( p_osmt, fh, p_rec ); + } Exit: /* * Return the IB query MAD to the pool as necessary. */ if( context.result.p_result_madw != NULL ) - { - osm_mad_pool_put( &p_osmt->mad_pool, context.result.p_result_madw ); - context.result.p_result_madw = NULL; - } + { + osm_mad_pool_put( &p_osmt->mad_pool, context.result.p_result_madw ); + context.result.p_result_madw = NULL; + } OSM_LOG_EXIT( &p_osmt->log ); return ( status ); @@ -2116,7 +2318,7 @@ osmtest_write_all_port_recs( IN osmtest_t * const p_osmt, OSM_LOG_ENTER( &p_osmt->log, osmtest_write_all_port_recs ); - cl_memclr( &context, sizeof( context ) ); + memset( &context, 0, sizeof( context ) ); /* * Do a blocking query for all NodeRecords in the subnet. @@ -2125,13 +2327,13 @@ osmtest_write_all_port_recs( IN osmtest_t * const p_osmt, sizeof( *p_rec ), &context ); if( status != IB_SUCCESS ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_write_all_port_recs: ERR 007: " - "osmtest_get_all_recs failed (%s)\n", - ib_get_err_str( status ) ); - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_write_all_port_recs: ERR 0167: " + "osmtest_get_all_recs failed (%s)\n", + ib_get_err_str( status ) ); + goto Exit; + } /* * Write the received records out to the file. @@ -2139,44 +2341,44 @@ osmtest_write_all_port_recs( IN osmtest_t * const p_osmt, num_recs = context.result.result_cnt; if( osm_log_is_active( &p_osmt->log, OSM_LOG_VERBOSE ) ) - { - osm_log( &p_osmt->log, OSM_LOG_VERBOSE, - "osmtest_write_all_port_recs: " - "Received %u records\n", num_recs ); - } + { + osm_log( &p_osmt->log, OSM_LOG_VERBOSE, + "osmtest_write_all_port_recs: " + "Received %zu records\n", num_recs ); + } result = fprintf( fh, "#\n" "# PortInfo Records\n" "#\n" ); if( result < 0 ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_write_all_port_recs: ERR 0024: " "Write failed\n" ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_write_all_port_recs: ERR 0024: " "Write failed\n" ); + status = IB_ERROR; + goto Exit; + } for( i = 0; i < num_recs; i++ ) - { - p_rec = osmv_get_query_portinfo_rec( context.result.p_result_madw, i ); - osmtest_write_port_info( p_osmt, fh, p_rec ); - } + { + p_rec = osmv_get_query_portinfo_rec( context.result.p_result_madw, i ); + osmtest_write_port_info( p_osmt, fh, p_rec ); + } Exit: /* * Return the IB query MAD to the pool as necessary. */ if( context.result.p_result_madw != NULL ) - { - osm_mad_pool_put( &p_osmt->mad_pool, context.result.p_result_madw ); - context.result.p_result_madw = NULL; - } + { + osm_mad_pool_put( &p_osmt->mad_pool, context.result.p_result_madw ); + context.result.p_result_madw = NULL; + } OSM_LOG_EXIT( &p_osmt->log ); return ( status ); } /********************************************************************** -ASSUMES RMPP IMPL -**********************************************************************/ + * ASSUMES RMPP + **********************************************************************/ static ib_api_status_t osmtest_write_all_path_recs( IN osmtest_t * const p_osmt, @@ -2191,22 +2393,22 @@ osmtest_write_all_path_recs( OSM_LOG_ENTER( &p_osmt->log, osmtest_write_all_path_recs ); - cl_memclr( &context, sizeof( context ) ); + memset( &context, 0, sizeof( context ) ); /* - * Do a blocking query for all records in the subnet. + * Do a blocking query for all PathRecords in the subnet. */ status = osmtest_get_all_recs( p_osmt, IB_MAD_ATTR_PATH_RECORD, sizeof( *p_rec ), &context ); if( status != IB_SUCCESS ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_write_all_path_recs: ERR 0025: " - "osmtest_get_all_recs failed (%s)\n", - ib_get_err_str( status ) ); - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_write_all_path_recs: ERR 0025: " + "osmtest_get_all_recs failed (%s)\n", + ib_get_err_str( status ) ); + goto Exit; + } /* * Write the received records out to the file. @@ -2214,46 +2416,45 @@ osmtest_write_all_path_recs( num_recs = context.result.result_cnt; if( osm_log_is_active( &p_osmt->log, OSM_LOG_VERBOSE ) ) - { - osm_log( &p_osmt->log, OSM_LOG_VERBOSE, - "osmtest_write_all_path_recs: " - "Received %u records\n", num_recs ); - } + { + osm_log( &p_osmt->log, OSM_LOG_VERBOSE, + "osmtest_write_all_path_recs: " + "Received %zu records\n", num_recs ); + } result = fprintf( fh, "#\n" "# Path Records\n" "#\n" ); if( result < 0 ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_write_all_path_recs: ERR 0026: " - "Write failed\n" ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_write_all_path_recs: ERR 0026: " + "Write failed\n" ); + status = IB_ERROR; + goto Exit; + } for( i = 0; i < num_recs; i++ ) - { - p_rec = osmv_get_query_path_rec( context.result.p_result_madw, i ); - osmtest_write_path_info( p_osmt, fh, p_rec ); - } + { + p_rec = osmv_get_query_path_rec( context.result.p_result_madw, i ); + osmtest_write_path_info( p_osmt, fh, p_rec ); + } Exit: /* * Return the IB query MAD to the pool as necessary. */ if( context.result.p_result_madw != NULL ) - { - osm_mad_pool_put( &p_osmt->mad_pool, context.result.p_result_madw ); - context.result.p_result_madw = NULL; - } + { + osm_mad_pool_put( &p_osmt->mad_pool, context.result.p_result_madw ); + context.result.p_result_madw = NULL; + } OSM_LOG_EXIT( &p_osmt->log ); return ( status ); } #else - /* - * NON RMPP BASED QUERY FOR ALL NODES: BASED ON THE MAX LID GIVEN BY THE USER: + * NON RMPP BASED QUERY FOR ALL NODES: BASED ON THE MAX LID GIVEN BY THE USER */ static ib_api_status_t osmtest_write_all_node_recs( @@ -2272,84 +2473,85 @@ osmtest_write_all_node_recs( result = fprintf( fh, "#\n" "# Node Records\n" "#\n" ); if( result < 0 ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_write_all_node_recs: ERR 0027: " - "Write failed\n" ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_write_all_node_recs: ERR 0027: " + "Write failed\n" ); + status = IB_ERROR; + goto Exit; + } /* - * Go over all LIDS in the range 1 to max_lid and do a + * Go over all LIDs in the range 1 to max_lid and do a * NodeRecord query by that lid. */ - for (lid = 1; lid <= p_osmt->max_lid; lid++) { - /* prepare the qury context */ - cl_memclr( &context, sizeof( context ) ); + for (lid = 1; lid <= p_osmt->max_lid; lid++) + { + /* prepare the query context */ + memset( &context, 0, sizeof( context ) ); status = osmtest_get_node_rec_by_lid( p_osmt, cl_ntoh16( lid ), &context ); if( status != IB_SUCCESS ) + { + if ( status != IB_SA_MAD_STATUS_NO_RECORDS ) { - if ( (status != IB_INVALID_PARAMETER) && (status != IB_SA_MAD_STATUS_NO_RECORDS)) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_write_all_node_recs: ERR 0028: " - "failed to get node info for LID:0x%02X (%s)\n", - cl_ntoh16( lid ), - ib_get_err_str( status ) ); - goto Exit; - } - else - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_write_all_node_recs: WRN 0121: " - "failed to get node info for LID:0x%02X (%s)\n", - cl_ntoh16( lid ), - ib_get_err_str( status ) ); - status = IB_SUCCESS; - } + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_write_all_node_recs: ERR 0028: " + "failed to get node info for LID:0x%02X (%s)\n", + cl_ntoh16( lid ), + ib_get_err_str( status ) ); + goto Exit; } - else + else { - /* OK we got something */ - p_rec = osmv_get_query_node_rec( context.result.p_result_madw, 0); - osmtest_write_node_info( p_osmt, fh, p_rec ); + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_write_all_node_recs: WRN 0121: " + "failed to get node info for LID:0x%02X (%s)\n", + cl_ntoh16( lid ), + ib_get_err_str( status ) ); + status = IB_SUCCESS; + } + } + else + { + /* OK we got something */ + p_rec = osmv_get_query_node_rec( context.result.p_result_madw, 0 ); + osmtest_write_node_info( p_osmt, fh, p_rec ); - /* create a subnet object */ - p_node = node_new( ); - CL_ASSERT( p_node != NULL ); + /* create a subnet object */ + p_node = node_new( ); + CL_ASSERT( p_node != NULL ); - /* copy the info to the subnet node object */ - p_node->rec = *p_rec; + /* copy the info to the subnet node object */ + p_node->rec = *p_rec; - cl_qmap_insert( &p_osmt->exp_subn.node_lid_tbl, - p_node->rec.lid, &p_node->map_item ); + cl_qmap_insert( &p_osmt->exp_subn.node_lid_tbl, + p_node->rec.lid, &p_node->map_item ); - p_guid_node = node_new( ); - CL_ASSERT( p_guid_node != NULL ); + p_guid_node = node_new( ); + CL_ASSERT( p_guid_node != NULL ); - *p_guid_node = *p_node; + *p_guid_node = *p_node; - cl_qmap_insert( &p_osmt->exp_subn.node_guid_tbl, - p_guid_node->rec.node_info.node_guid, - &p_guid_node->map_item ); + cl_qmap_insert( &p_osmt->exp_subn.node_guid_tbl, + p_guid_node->rec.node_info.node_guid, + &p_guid_node->map_item ); - } + } if( context.result.p_result_madw != NULL ) - { - osm_mad_pool_put( &p_osmt->mad_pool, context.result.p_result_madw ); - context.result.p_result_madw = NULL; - } - } - - Exit: - if( context.result.p_result_madw != NULL ) { osm_mad_pool_put( &p_osmt->mad_pool, context.result.p_result_madw ); context.result.p_result_madw = NULL; } + } + + Exit: + if( context.result.p_result_madw != NULL ) + { + osm_mad_pool_put( &p_osmt->mad_pool, context.result.p_result_madw ); + context.result.p_result_madw = NULL; + } OSM_LOG_EXIT( &p_osmt->log ); return ( status ); @@ -2359,7 +2561,6 @@ osmtest_write_all_node_recs( * GET ALL PORT RECORDS IN THE FABRIC - * one by one by using the node info received */ - static ib_api_status_t osmtest_write_all_port_recs( IN osmtest_t * const p_osmt, IN FILE * fh ) @@ -2376,86 +2577,87 @@ osmtest_write_all_port_recs( IN osmtest_t * const p_osmt, OSM_LOG_ENTER( &p_osmt->log, osmtest_write_all_port_recs ); - cl_memclr( &context, sizeof( context ) ); + memset( &context, 0, sizeof( context ) ); /* print header */ result = fprintf( fh, "#\n" "# PortInfo Records\n" "#\n" ); if( result < 0 ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_write_all_port_recs: ERR 0029: " "Write failed\n" ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_write_all_port_recs: ERR 0029: " "Write failed\n" ); + status = IB_ERROR; + goto Exit; + } /* use the pre-explored set of nodes */ p_tbl = &p_osmt->exp_subn.node_lid_tbl; p_node = ( node_t * ) cl_qmap_head( p_tbl ); /* - * Go over all LIDS in the range 1 to max_lid and do a + * Go over all LIDs in the range 1 to max_lid and do a * NodeRecord query by that lid. */ while( p_node != ( node_t * ) cl_qmap_end( p_tbl ) ) - { + { - p_node_rec = &(p_node->rec); + p_node_rec = &(p_node->rec); - /* go through all ports of the node: */ - for (port_num = 0; port_num <= p_node_rec->node_info.num_ports; port_num++) { - /* prepare the qury context */ - cl_memclr( &context, sizeof( context ) ); + /* go through all ports of the node: */ + for (port_num = 0; port_num <= p_node_rec->node_info.num_ports; port_num++) + { + /* prepare the query context */ + memset( &context, 0, sizeof( context ) ); - status = osmtest_get_port_rec_by_num( p_osmt, - p_node_rec->lid, - port_num, - &context ); - if( status != IB_SUCCESS ) - { - if( (status != IB_INVALID_PARAMETER) && (status != IB_SA_MAD_STATUS_NO_RECORDS)) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_write_all_port_recs: WRN 0121: " - "Error encountered getting port info for LID:0x%04X Num:0x%02X (%s)\n", - p_node_rec->lid, port_num, - ib_get_err_str( status ) ); - goto Exit; - } - else - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_write_all_port_recs: WRN 0121: " - "failed to get port info for LID:0x%04X Num:0x%02X (%s)\n", - p_node_rec->lid, port_num, - ib_get_err_str( status ) ); - status = IB_SUCCESS; - } - } + status = osmtest_get_port_rec_by_num( p_osmt, + p_node_rec->lid, + port_num, + &context ); + if( status != IB_SUCCESS ) + { + if( status != IB_SA_MAD_STATUS_NO_RECORDS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_write_all_port_recs: WRN 0122: " + "Error encountered getting port info for LID:0x%04X Num:0x%02X (%s)\n", + p_node_rec->lid, port_num, + ib_get_err_str( status ) ); + goto Exit; + } else - { - /* OK we got something */ - p_rec = osmv_get_query_portinfo_rec( context.result.p_result_madw, 0); - osmtest_write_port_info( p_osmt, fh, p_rec ); + { + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_write_all_port_recs: WRN 0123: " + "failed to get port info for LID:0x%04X Num:0x%02X (%s)\n", + p_node_rec->lid, port_num, + ib_get_err_str( status ) ); + status = IB_SUCCESS; + } + } + else + { + /* OK we got something */ + p_rec = osmv_get_query_portinfo_rec( context.result.p_result_madw, 0 ); + osmtest_write_port_info( p_osmt, fh, p_rec ); - /* create a subnet object */ - p_port = port_new( ); - CL_ASSERT( p_port != NULL ); + /* create a subnet object */ + p_port = port_new( ); + CL_ASSERT( p_port != NULL ); - /* copy the info to the subnet node object */ - p_port->rec = *p_rec; + /* copy the info to the subnet node object */ + p_port->rec = *p_rec; - cl_qmap_insert( &p_osmt->exp_subn.port_key_tbl, - port_gen_id(p_node_rec->lid, port_num), &p_port->map_item ); - } + cl_qmap_insert( &p_osmt->exp_subn.port_key_tbl, + port_gen_id(p_node_rec->lid, port_num), &p_port->map_item ); + } - if( context.result.p_result_madw != NULL ) - { - osm_mad_pool_put( &p_osmt->mad_pool, context.result.p_result_madw ); - context.result.p_result_madw = NULL; - } + if( context.result.p_result_madw != NULL ) + { + osm_mad_pool_put( &p_osmt->mad_pool, context.result.p_result_madw ); + context.result.p_result_madw = NULL; } - p_node = ( node_t * ) cl_qmap_next( &p_node->map_item ); } + p_node = ( node_t * ) cl_qmap_next( &p_node->map_item ); + } /* we must set the exist status to avoid abort of the over all algorith */ @@ -2465,18 +2667,18 @@ osmtest_write_all_port_recs( IN osmtest_t * const p_osmt, */ if( context.result.p_result_madw != NULL ) - { - osm_mad_pool_put( &p_osmt->mad_pool, context.result.p_result_madw ); - context.result.p_result_madw = NULL; - } + { + osm_mad_pool_put( &p_osmt->mad_pool, context.result.p_result_madw ); + context.result.p_result_madw = NULL; + } OSM_LOG_EXIT( &p_osmt->log ); return ( status ); } /********************************************************************** -ASSUMES NO RMPP -**********************************************************************/ + * ASSUMES NO RMPP + **********************************************************************/ static ib_api_status_t osmtest_write_all_path_recs( IN osmtest_t * const p_osmt, IN FILE * fh ) @@ -2487,10 +2689,11 @@ osmtest_write_all_path_recs( IN osmtest_t * const p_osmt, int num_recs, i; cl_qmap_t *p_tbl; node_t *p_src_node, *p_dst_node; + ib_api_status_t got_status = IB_SUCCESS; OSM_LOG_ENTER( &p_osmt->log, osmtest_write_all_path_recs ); - cl_memclr( &context, sizeof( context ) ); + memset( &context, 0, sizeof( context ) ); /* * Go over all nodes that exist in the subnet @@ -2503,12 +2706,14 @@ osmtest_write_all_path_recs( IN osmtest_t * const p_osmt, p_src_node = ( node_t * ) cl_qmap_head( p_tbl ); - while( p_src_node != ( node_t * ) cl_qmap_end( p_tbl ) ) { + while( p_src_node != ( node_t * ) cl_qmap_end( p_tbl ) ) + { /* HACK we use capability_mask to know diff a CA node from switch node */ /* if(p_src_node->rec.node_info.capability_mask ) { */ p_dst_node = ( node_t * ) cl_qmap_head( p_tbl ); - while( p_dst_node != ( node_t * ) cl_qmap_end( p_tbl ) ) { + while( p_dst_node != ( node_t * ) cl_qmap_end( p_tbl ) ) + { /* HACK we use capability_mask to know diff a CA node from switch node */ /* if (p_dst_node->rec.node_info.capability_mask) { */ @@ -2516,49 +2721,55 @@ osmtest_write_all_path_recs( IN osmtest_t * const p_osmt, status = osmtest_get_path_rec_by_lid_pair( p_osmt, p_src_node->rec.lid, p_dst_node->rec.lid, - &context); + &context ); if( status != IB_SUCCESS ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_write_all_path_recs: WRN 0121: " - "failed to get path info from LID:0x%X To LID:0x%X (%s)\n", - p_src_node->rec.lid, p_dst_node->rec.lid, - ib_get_err_str( status ) ); - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_write_all_path_recs: ERR 012D: " + "failed to get path info from LID:0x%X To LID:0x%X (%s)\n", + p_src_node->rec.lid, p_dst_node->rec.lid, + ib_get_err_str( status ) ); + /* remember the first error status */ + got_status = ( got_status == IB_SUCCESS ) ? status : got_status; + } else + { + /* we might have received several records */ + num_recs = context.result.result_cnt; + for (i = 0; i < num_recs; i++) { - /* we might have received several records */ - num_recs = context.result.result_cnt; - for (i = 0; i < num_recs; i++) { - p_rec = osmv_get_query_path_rec( context.result.p_result_madw, i); - osmtest_write_path_info( p_osmt, fh, p_rec ); - } + p_rec = osmv_get_query_path_rec( context.result.p_result_madw, i ); + osmtest_write_path_info( p_osmt, fh, p_rec ); } - /* } */ + } +/* } */ if( context.result.p_result_madw != NULL ) - { - osm_mad_pool_put( &p_osmt->mad_pool, context.result.p_result_madw ); - context.result.p_result_madw = NULL; - } + { + osm_mad_pool_put( &p_osmt->mad_pool, context.result.p_result_madw ); + context.result.p_result_madw = NULL; + } /* next one please */ p_dst_node = ( node_t * ) cl_qmap_next( &p_dst_node->map_item ); } - /* } */ +/* } */ p_src_node = ( node_t * ) cl_qmap_next( &p_src_node->map_item ); } + if( got_status != IB_SUCCESS ) + status = got_status; + /* * Return the IB query MAD to the pool as necessary. */ if( context.result.p_result_madw != NULL ) - { - osm_mad_pool_put( &p_osmt->mad_pool, context.result.p_result_madw ); - context.result.p_result_madw = NULL; - } + { + osm_mad_pool_put( &p_osmt->mad_pool, context.result.p_result_madw ); + context.result.p_result_madw = NULL; + } OSM_LOG_EXIT( &p_osmt->log ); return ( status ); @@ -2578,13 +2789,14 @@ osmtest_create_inventory_file( IN osmtest_t * const p_osmt ) fh = fopen( p_osmt->opt.file_name, "w" ); if( fh == NULL ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_create_inventory_file: ERR 0079: " - "Unable to open inventory file (%s)\n" ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_create_inventory_file: ERR 0079: " + "Unable to open inventory file (%s)\n", + p_osmt->opt.file_name ); + status = IB_ERROR; + goto Exit; + } /* HACK: the order is important: nodes ports paths */ status = osmtest_write_all_node_recs( p_osmt, fh ); @@ -2596,17 +2808,16 @@ osmtest_create_inventory_file( IN osmtest_t * const p_osmt ) goto Exit; if (! p_osmt->opt.ignore_path_records) - { - status = osmtest_write_all_path_recs( p_osmt, fh ); - if( status != IB_SUCCESS ) - goto Exit; - } - - /* - status = osmtest_write_all_link_recs( p_osmt, fh ); + { + status = osmtest_write_all_path_recs( p_osmt, fh ); if( status != IB_SUCCESS ) + goto Exit; + } + + status = osmtest_write_all_link_recs( p_osmt, fh ); + if( status != IB_SUCCESS ) goto Exit; - */ + fclose( fh ); Exit: @@ -2631,60 +2842,66 @@ osmtest_stress_large_rmpp_pr( IN osmtest_t * const p_osmt ) OSM_LOG_ENTER( &p_osmt->log, osmtest_stress_large_rmpp_pr ); gettimeofday( &start_tv, NULL ); - printf("-I- Start time is : %09ld:%06ld [sec:usec]\n",start_tv.tv_sec, (long)start_tv.tv_usec); + printf("-I- Start time is : %09ld:%06ld [sec:usec]\n", start_tv.tv_sec, (long)start_tv.tv_usec); while( num_queries < STRESS_LARGE_PR_RMPP_THR ) - { - delta_recs = 0; - delta_queries = 0; + { + delta_recs = 0; + delta_queries = 0; - status = osmtest_stress_path_recs_by_guid( p_osmt, &delta_recs, - &delta_queries ); - if( status != IB_SUCCESS ) - goto Exit; + status = osmtest_stress_path_recs_by_guid( p_osmt, &delta_recs, + &delta_queries ); + if( status != IB_SUCCESS ) + goto Exit; - num_recs += delta_recs; - num_queries += delta_queries; + num_recs += delta_recs; + num_queries += delta_queries; - print_freq += delta_recs; - if( print_freq > 10000 ) - { - gettimeofday( &end_tv, NULL ); - if (end_tv.tv_usec > start_tv.tv_usec) { - sec_diff = end_tv.tv_sec-start_tv.tv_sec; - usec_diff = end_tv.tv_usec-start_tv.tv_usec; - } else { - sec_diff = end_tv.tv_sec-start_tv.tv_sec - 1; - usec_diff = 1000000 - (start_tv.tv_usec - end_tv.tv_usec); - } - printf("-I- End time is : %09ld:%06ld [sec:usec]\n", - end_tv.tv_sec, (long)end_tv.tv_usec); - printf("-I- Querying %" PRId64 " Path Record queries CA to CA (rmpp) \n\ttook %04ld:%06ld [sec:usec]\n",num_queries, - sec_diff,usec_diff); - if (num_recs == 0) - ratio = 0; - else - ratio = (float)(num_queries / num_recs); - printf( "-I- Queries to Record Ratio is %" PRIu64 " records, %" PRIu64 " queries : %.2f \n", - num_recs, num_queries, ratio); - print_freq = 0; - } + print_freq += delta_recs; + if( print_freq > 10000 ) + { + gettimeofday( &end_tv, NULL ); + if (end_tv.tv_usec > start_tv.tv_usec) + { + sec_diff = end_tv.tv_sec-start_tv.tv_sec; + usec_diff = end_tv.tv_usec-start_tv.tv_usec; + } + else + { + sec_diff = end_tv.tv_sec-start_tv.tv_sec - 1; + usec_diff = 1000000 - (start_tv.tv_usec - end_tv.tv_usec); + } + printf("-I- End time is : %09ld:%06ld [sec:usec]\n", + end_tv.tv_sec, (long)end_tv.tv_usec); + printf("-I- Querying %" PRId64 " Path Record queries CA to CA (rmpp)\n\ttook %04ld:%06ld [sec:usec]\n", + num_queries, sec_diff, usec_diff); + if (num_recs == 0) + ratio = 0; + else + ratio = ((float)num_queries / (float)num_recs); + printf( "-I- Queries to Record Ratio is %" PRIu64 " records, %" PRIu64 " queries : %.2f \n", + num_recs, num_queries, ratio); + print_freq = 0; } + } Exit: gettimeofday( &end_tv, NULL ); printf("-I- End time is : %09ld:%06ld [sec:usec]\n", end_tv.tv_sec, (long)end_tv.tv_usec); - if (end_tv.tv_usec > start_tv.tv_usec) { - sec_diff = end_tv.tv_sec-start_tv.tv_sec; - usec_diff = end_tv.tv_usec-start_tv.tv_usec; - } else { - sec_diff = end_tv.tv_sec-start_tv.tv_sec - 1; - usec_diff = 1000000 - (start_tv.tv_usec - end_tv.tv_usec); + if (end_tv.tv_usec > start_tv.tv_usec) + { + sec_diff = end_tv.tv_sec-start_tv.tv_sec; + usec_diff = end_tv.tv_usec-start_tv.tv_usec; + } + else + { + sec_diff = end_tv.tv_sec-start_tv.tv_sec - 1; + usec_diff = 1000000 - (start_tv.tv_usec - end_tv.tv_usec); } - printf("-I- Querying %" PRId64 " Path Record queries (rmpp) took %04ld:%06ld [sec:usec]\n",num_queries, - sec_diff,usec_diff); + printf("-I- Querying %" PRId64 " Path Record queries (rmpp) took %04ld:%06ld [sec:usec]\n", + num_queries, sec_diff, usec_diff); OSM_LOG_EXIT( &p_osmt->log ); return ( status ); @@ -2706,67 +2923,73 @@ osmtest_stress_large_rmpp( IN osmtest_t * const p_osmt ) OSM_LOG_ENTER( &p_osmt->log, osmtest_stress_large_rmpp ); gettimeofday( &start_tv, NULL ); - printf("-I- Start time is : %09ld:%06ld [sec:usec]\n",start_tv.tv_sec, (long)start_tv.tv_usec); + printf("-I- Start time is : %09ld:%06ld [sec:usec]\n", start_tv.tv_sec, (long)start_tv.tv_usec); while( num_queries < STRESS_LARGE_RMPP_THR ) - { - delta_recs = 0; - delta_queries = 0; + { + delta_recs = 0; + delta_queries = 0; - status = osmtest_stress_node_recs_large( p_osmt, &delta_recs, - &delta_queries ); - if( status != IB_SUCCESS ) - goto Exit; + status = osmtest_stress_node_recs_large( p_osmt, &delta_recs, + &delta_queries ); + if( status != IB_SUCCESS ) + goto Exit; - status = osmtest_stress_path_recs_large( p_osmt, &delta_recs, - &delta_queries ); - if( status != IB_SUCCESS ) - goto Exit; + status = osmtest_stress_path_recs_large( p_osmt, &delta_recs, + &delta_queries ); + if( status != IB_SUCCESS ) + goto Exit; - status = osmtest_stress_port_recs_large( p_osmt, &delta_recs, - &delta_queries ); - if( status != IB_SUCCESS ) - goto Exit; + status = osmtest_stress_port_recs_large( p_osmt, &delta_recs, + &delta_queries ); + if( status != IB_SUCCESS ) + goto Exit; - num_recs += delta_recs; - num_queries += delta_queries; + num_recs += delta_recs; + num_queries += delta_queries; - print_freq += delta_recs; + print_freq += delta_recs; - if( print_freq > 100000 ) - { - gettimeofday( &end_tv, NULL ); - if (end_tv.tv_usec > start_tv.tv_usec) { - sec_diff = end_tv.tv_sec-start_tv.tv_sec; - usec_diff = end_tv.tv_usec-start_tv.tv_usec; - } else { - sec_diff = end_tv.tv_sec-start_tv.tv_sec - 1; - usec_diff = 1000000 - (start_tv.tv_usec - end_tv.tv_usec); - } - printf("-I- End time is : %09ld:%06ld [sec:usec]\n", - end_tv.tv_sec, (long)end_tv.tv_usec); - printf("-I- Querying %" PRId64 " large mixed queries (rmpp) took %04ld:%06ld [sec:usec]\n",num_queries, - sec_diff,usec_diff); - printf( "%" PRIu64 " records, %" PRIu64 " queries\n", - num_recs, num_queries ); - print_freq = 0; - } + if( print_freq > 100000 ) + { + gettimeofday( &end_tv, NULL ); + if (end_tv.tv_usec > start_tv.tv_usec) + { + sec_diff = end_tv.tv_sec-start_tv.tv_sec; + usec_diff = end_tv.tv_usec-start_tv.tv_usec; + } + else + { + sec_diff = end_tv.tv_sec-start_tv.tv_sec - 1; + usec_diff = 1000000 - (start_tv.tv_usec - end_tv.tv_usec); + } + printf("-I- End time is : %09ld:%06ld [sec:usec]\n", + end_tv.tv_sec, (long)end_tv.tv_usec); + printf("-I- Querying %" PRId64 " large mixed queries (rmpp) took %04ld:%06ld [sec:usec]\n", + num_queries, sec_diff, usec_diff); + printf("%" PRIu64 " records, %" PRIu64 " queries\n", + num_recs, num_queries); + print_freq = 0; } + } Exit: gettimeofday( &end_tv, NULL ); printf("-I- End time is : %09ld:%06ld [sec:usec]\n", end_tv.tv_sec, (long)end_tv.tv_usec); - if (end_tv.tv_usec > start_tv.tv_usec) { - sec_diff = end_tv.tv_sec-start_tv.tv_sec; - usec_diff = end_tv.tv_usec-start_tv.tv_usec; - } else { - sec_diff = end_tv.tv_sec-start_tv.tv_sec - 1; - usec_diff = 1000000 - (start_tv.tv_usec - end_tv.tv_usec); + if (end_tv.tv_usec > start_tv.tv_usec) + { + sec_diff = end_tv.tv_sec-start_tv.tv_sec; + usec_diff = end_tv.tv_usec-start_tv.tv_usec; + } + else + { + sec_diff = end_tv.tv_sec-start_tv.tv_sec - 1; + usec_diff = 1000000 - (start_tv.tv_usec - end_tv.tv_usec); } - printf("-I- Querying %" PRId64 " large mixed queries (rmpp) took %04ld:%06ld [sec:usec]\n",num_queries, - sec_diff,usec_diff); + printf("-I- Querying %" PRId64 " large mixed queries (rmpp) took %04ld:%06ld [sec:usec]\n", + num_queries, sec_diff, usec_diff); OSM_LOG_EXIT( &p_osmt->log ); return ( status ); @@ -2789,51 +3012,63 @@ osmtest_stress_small_rmpp( IN osmtest_t * const p_osmt ) OSM_LOG_ENTER( &p_osmt->log, osmtest_stress_small_rmpp ); gettimeofday( &start_tv, NULL ); - printf("-I- Start time is : %09ld:%06ld [sec:usec]\n",start_tv.tv_sec, (long)start_tv.tv_usec); + printf("-I- Start time is : %09ld:%06ld [sec:usec]\n", + start_tv.tv_sec, (long)start_tv.tv_usec); + while( (num_queries < STRESS_SMALL_RMPP_THR) && (num_timeouts < 100) ) - { - delta_recs = 0; - delta_queries = 0; + { + delta_recs = 0; + delta_queries = 0; - status = osmtest_stress_port_recs_small( p_osmt, &delta_recs, - &delta_queries ); + status = osmtest_stress_port_recs_small( p_osmt, &delta_recs, + &delta_queries ); + if( status != IB_SUCCESS ) + goto Exit; - num_recs += delta_recs; - num_queries += delta_queries; + num_recs += delta_recs; + num_queries += delta_queries; - print_freq += delta_recs; - if( print_freq > 5000 ) - { - gettimeofday( &end_tv, NULL ); - printf( "%" PRIu64 " records, %" PRIu64 " queries\n", - num_recs, num_queries ); - if (end_tv.tv_usec > start_tv.tv_usec) { - sec_diff = end_tv.tv_sec-start_tv.tv_sec; - usec_diff = end_tv.tv_usec-start_tv.tv_usec; - } else { - sec_diff = end_tv.tv_sec-start_tv.tv_sec - 1; - usec_diff = 1000000 - (start_tv.tv_usec - end_tv.tv_usec); - } - printf("-I- End time is : %09ld:%06ld [sec:usec]\n", - end_tv.tv_sec, (long)end_tv.tv_usec); - printf("-I- Querying %" PRId64 " port_info queries (single mad) took %04ld:%06ld [sec:usec]\n",num_queries, - sec_diff,usec_diff); - print_freq = 0; - } + print_freq += delta_recs; + if( print_freq > 5000 ) + { + gettimeofday( &end_tv, NULL ); + printf( "%" PRIu64 " records, %" PRIu64 " queries\n", + num_recs, num_queries ); + if (end_tv.tv_usec > start_tv.tv_usec) + { + sec_diff = end_tv.tv_sec-start_tv.tv_sec; + usec_diff = end_tv.tv_usec-start_tv.tv_usec; + } + else + { + sec_diff = end_tv.tv_sec-start_tv.tv_sec - 1; + usec_diff = 1000000 - (start_tv.tv_usec - end_tv.tv_usec); + } + printf("-I- End time is : %09ld:%06ld [sec:usec]\n", + end_tv.tv_sec, (long)end_tv.tv_usec); + printf("-I- Querying %" PRId64 " port_info queries (single mad) took %04ld:%06ld [sec:usec]\n", + num_queries, sec_diff, usec_diff); + print_freq = 0; } + } + + Exit: gettimeofday( &end_tv, NULL ); printf("-I- End time is : %09ld:%06ld [sec:usec]\n", end_tv.tv_sec, (long)end_tv.tv_usec); - if (end_tv.tv_usec > start_tv.tv_usec) { - sec_diff = end_tv.tv_sec-start_tv.tv_sec; - usec_diff = end_tv.tv_usec-start_tv.tv_usec; - } else { - sec_diff = end_tv.tv_sec-start_tv.tv_sec - 1; - usec_diff = 1000000 - (start_tv.tv_usec - end_tv.tv_usec); + if (end_tv.tv_usec > start_tv.tv_usec) + { + sec_diff = end_tv.tv_sec-start_tv.tv_sec; + usec_diff = end_tv.tv_usec-start_tv.tv_usec; + } + else + { + sec_diff = end_tv.tv_sec-start_tv.tv_sec - 1; + usec_diff = 1000000 - (start_tv.tv_usec - end_tv.tv_usec); } - printf("-I- Querying %" PRId64 " port_info queries (single mad) took %04ld:%06ld [sec:usec]\n",num_queries, - sec_diff,usec_diff); + printf("-I- Querying %" PRId64 " port_info queries (single mad) took %04ld:%06ld [sec:usec]\n", + num_queries, sec_diff, usec_diff); if (num_timeouts > 50) { status = IB_TIMEOUT; @@ -2856,10 +3091,10 @@ osmtest_prepare_db_generic( IN osmtest_t * const p_osmt, p_generic = ( generic_t * ) cl_qmap_head( p_tbl ); while( p_generic != ( generic_t * ) cl_qmap_end( p_tbl ) ) - { - p_generic->count = 0; - p_generic = ( generic_t * ) cl_qmap_next( &p_generic->map_item ); - } + { + p_generic->count = 0; + p_generic = ( generic_t * ) cl_qmap_next( &p_generic->map_item ); + } OSM_LOG_EXIT( &p_osmt->log ); } @@ -2893,22 +3128,22 @@ osmtest_check_missing_nodes( IN osmtest_t * const p_osmt ) p_node = ( node_t * ) cl_qmap_head( p_tbl ); while( p_node != ( node_t * ) cl_qmap_end( p_tbl ) ) + { + if( p_node->count == 0 ) { - if( p_node->count == 0 ) - { - /* - * This node was not reported by the SA - */ - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_check_missing_nodes: ERR 0080: " - "Missing node 0x%016" PRIx64 "\n", - cl_ntoh64( p_node->rec.node_info.node_guid ) ); - status = IB_ERROR; - } - - p_node = ( node_t * ) cl_qmap_next( &p_node->map_item ); - } - + /* + * This node was not reported by the SA + */ + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_check_missing_nodes: ERR 0080: " + "Missing node 0x%016" PRIx64 "\n", + cl_ntoh64( p_node->rec.node_info.node_guid ) ); + status = IB_ERROR; + } + + p_node = ( node_t * ) cl_qmap_next( &p_node->map_item ); + } + OSM_LOG_EXIT( &p_osmt->log ); return ( status ); } @@ -2929,22 +3164,22 @@ osmtest_check_missing_ports( IN osmtest_t * const p_osmt ) p_port = ( port_t * ) cl_qmap_head( p_tbl ); while( p_port != ( port_t * ) cl_qmap_end( p_tbl ) ) + { + if( p_port->count == 0 ) { - if( p_port->count == 0 ) - { - /* - * This port was not reported by the SA - */ - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_check_missing_ports: ERR 0081: " - "Missing port LID:0x%X Num:0x%X\n", - cl_ntoh16( p_port->rec.lid), p_port->rec.port_num); - status = IB_ERROR; - } - - p_port = ( port_t * ) cl_qmap_next( &p_port->map_item ); + /* + * This port was not reported by the SA + */ + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_check_missing_ports: ERR 0081: " + "Missing port LID:0x%X Num:0x%X\n", + cl_ntoh16( p_port->rec.lid), p_port->rec.port_num); + status = IB_ERROR; } + p_port = ( port_t * ) cl_qmap_next( &p_port->map_item ); + } + OSM_LOG_EXIT( &p_osmt->log ); return ( status ); } @@ -2965,24 +3200,24 @@ osmtest_check_missing_paths( IN osmtest_t * const p_osmt ) p_path = ( path_t * ) cl_qmap_head( p_tbl ); while( p_path != ( path_t * ) cl_qmap_end( p_tbl ) ) + { + if( p_path->count == 0 ) { - if( p_path->count == 0 ) - { - /* - * This path was not reported by the SA - */ - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_check_missing_paths: ERR 0051: " - "SA did not return path SLID 0x%X to DLID 0x%X\n", - cl_ntoh16( p_path->rec.slid ), - cl_ntoh16( p_path->rec.dlid ) ); - status = IB_ERROR; - goto Exit; - } - - p_path = ( path_t * ) cl_qmap_next( &p_path->map_item ); + /* + * This path was not reported by the SA + */ + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_check_missing_paths: ERR 0051: " + "SA did not return path SLID 0x%X to DLID 0x%X\n", + cl_ntoh16( p_path->rec.slid ), + cl_ntoh16( p_path->rec.dlid ) ); + status = IB_ERROR; + goto Exit; } + p_path = ( path_t * ) cl_qmap_next( &p_path->map_item ); + } + Exit: OSM_LOG_EXIT( &p_osmt->log ); return ( status ); @@ -3003,12 +3238,12 @@ osmtest_path_rec_kay_is_valid( IN osmtest_t * const p_osmt, IN const path_t * const p_path ) { if( ( p_path->comp.dlid == 0 ) || ( p_path->comp.slid == 0 ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_path_rec_kay_is_valid: ERR 008: " - "SLID and DLID must be specified for defined paths\n" ); - return ( FALSE ); - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_path_rec_kay_is_valid: ERR 0168: " + "SLID and DLID must be specified for defined paths\n" ); + return ( FALSE ); + } return ( TRUE ); } @@ -3021,21 +3256,31 @@ osmtest_validate_path_data( IN osmtest_t * const p_osmt, IN const ib_path_rec_t * const p_rec ) { cl_status_t status = IB_SUCCESS; + uint8_t lmc = 0; OSM_LOG_ENTER( &p_osmt->log, osmtest_validate_path_data ); if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_path_data: " - "Checking path SLID 0x%X to DLID 0x%X\n", - cl_ntoh16( p_rec->slid ), cl_ntoh16( p_rec->dlid ) ); - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_path_data: " + "Checking path SLID 0x%X to DLID 0x%X\n", + cl_ntoh16( p_rec->slid ), cl_ntoh16( p_rec->dlid ) ); + } - /* - * Has this record already been returned? - */ - if( p_path->count != 0 ) + status = osmtest_get_local_port_lmc( p_osmt, p_osmt->local_port.lid, &lmc ); + if (status != IB_SUCCESS) + goto Exit; + + /* HACK: Assume uniform LMC across endports in the subnet */ + /* This is the only LMC mode which OpenSM currently supports */ + /* In absence of this assumption, validation of this is much more complicated */ + if ( lmc == 0 ) + { + /* + * Has this record already been returned? + */ + if( p_path->count != 0 ) { osm_log( &p_osmt->log, OSM_LOG_ERROR, "osmtest_validate_path_data: ERR 0056: " @@ -3044,6 +3289,21 @@ osmtest_validate_path_data( IN osmtest_t * const p_osmt, status = IB_ERROR; goto Exit; } + } + else + { + /* Also, this doesn't detect fewer than the correct number of paths being returned */ + if ( p_path->count >= (uint32_t)( 1 << (2*lmc) ) ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_path_data: ERR 0052: " + "Already received path SLID 0x%X to DLID 0x%X count %d LMC %d\n", + cl_ntoh16( p_rec->slid ), cl_ntoh16( p_rec->dlid ), + p_path->count, lmc ); + status = IB_ERROR; + goto Exit; + } + } ++p_path->count; @@ -3054,21 +3314,21 @@ osmtest_validate_path_data( IN osmtest_t * const p_osmt, p_path->rec.dgid.unicast.interface_id ) != ( p_path->comp.dgid.unicast.interface_id & p_rec->dgid.unicast.interface_id ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_path_data: ERR 009: " - "DGID mismatch on path SLID 0x%X to DLID 0x%X\n" - "\t\t\t\tExpected 0x%016" PRIx64 " 0x%016" PRIx64 "\n" - "\t\t\t\tReceived 0x%016" PRIx64 " 0x%016" PRIx64 "\n", - cl_ntoh16( p_path->rec.slid ), - cl_ntoh16( p_path->rec.dlid ), - cl_ntoh64( p_path->rec.dgid.unicast.prefix ), - cl_ntoh64( p_path->rec.dgid.unicast.interface_id ), - cl_ntoh64( p_rec->dgid.unicast.prefix ), - cl_ntoh64( p_rec->dgid.unicast.interface_id ) ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_path_data: ERR 0169: " + "DGID mismatch on path SLID 0x%X to DLID 0x%X\n" + "\t\t\t\tExpected 0x%016" PRIx64 " 0x%016" PRIx64 "\n" + "\t\t\t\tReceived 0x%016" PRIx64 " 0x%016" PRIx64 "\n", + cl_ntoh16( p_path->rec.slid ), + cl_ntoh16( p_path->rec.dlid ), + cl_ntoh64( p_path->rec.dgid.unicast.prefix ), + cl_ntoh64( p_path->rec.dgid.unicast.interface_id ), + cl_ntoh64( p_rec->dgid.unicast.prefix ), + cl_ntoh64( p_rec->dgid.unicast.interface_id ) ); + status = IB_ERROR; + goto Exit; + } /* * Check the fields the user wants checked. @@ -3077,38 +3337,39 @@ osmtest_validate_path_data( IN osmtest_t * const p_osmt, p_path->rec.sgid.unicast.interface_id ) != ( p_path->comp.sgid.unicast.interface_id & p_rec->sgid.unicast.interface_id ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_path_data: ERR 0057: " - "SGID mismatch on path SLID 0x%X to DLID 0x%X\n" - "\t\t\t\tExpected 0x%016" PRIx64 " 0x%016" PRIx64 ",\n" - "\t\t\t\tReceived 0x%016" PRIx64 " 0x%016" PRIx64 ".\n", - cl_ntoh16( p_path->rec.slid ), - cl_ntoh16( p_path->rec.dlid ), - cl_ntoh64( p_path->rec.sgid.unicast.prefix ), - cl_ntoh64( p_path->rec.sgid.unicast.interface_id ), - cl_ntoh64( p_rec->sgid.unicast.prefix ), - cl_ntoh64( p_rec->sgid.unicast.interface_id ) ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_path_data: ERR 0057: " + "SGID mismatch on path SLID 0x%X to DLID 0x%X\n" + "\t\t\t\tExpected 0x%016" PRIx64 " 0x%016" PRIx64 ",\n" + "\t\t\t\tReceived 0x%016" PRIx64 " 0x%016" PRIx64 ".\n", + cl_ntoh16( p_path->rec.slid ), + cl_ntoh16( p_path->rec.dlid ), + cl_ntoh64( p_path->rec.sgid.unicast.prefix ), + cl_ntoh64( p_path->rec.sgid.unicast.interface_id ), + cl_ntoh64( p_rec->sgid.unicast.prefix ), + cl_ntoh64( p_rec->sgid.unicast.interface_id ) ); + status = IB_ERROR; + goto Exit; + } /* * Compare the fields the user wishes to validate. */ if( ( p_path->comp.pkey & p_path->rec.pkey ) != ( p_path->comp.pkey & p_rec->pkey ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_path_data: ERR 0012: " - "PKEY mismatch on path SLID 0x%X to DLID 0x%X\n" - "\t\t\t\tExpected 0x%X, received 0x%X\n", - cl_ntoh16( p_path->rec.slid ), - cl_ntoh16( p_path->rec.dlid ), - cl_ntoh64( p_path->rec.pkey ), cl_ntoh64( p_rec->pkey ) ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_path_data: ERR 0012: " + "PKEY mismatch on path SLID 0x%X to DLID 0x%X\n" + "\t\t\t\tExpected 0x%X, received 0x%X\n", + cl_ntoh16( p_path->rec.slid ), + cl_ntoh16( p_path->rec.dlid ), + cl_ntoh16( p_path->rec.pkey ), + cl_ntoh16( p_rec->pkey ) ); + status = IB_ERROR; + goto Exit; + } Exit: OSM_LOG_EXIT( &p_osmt->log ); @@ -3127,26 +3388,26 @@ osmtest_validate_node_data( IN osmtest_t * const p_osmt, OSM_LOG_ENTER( &p_osmt->log, osmtest_validate_node_data ); if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_node_data: " - "Checking node 0x%016" PRIx64 ", LID 0x%X\n", - cl_ntoh64( p_rec->node_info.node_guid ), - cl_ntoh16( p_rec->lid ) ); - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_node_data: " + "Checking node 0x%016" PRIx64 ", LID 0x%X\n", + cl_ntoh64( p_rec->node_info.node_guid ), + cl_ntoh16( p_rec->lid ) ); + } /* * Has this record already been returned? */ if( p_node->count != 0 ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_node_data: ERR 0013: " - "Already received node 0x%016" PRIx64 "\n", - cl_ntoh64( p_node->rec.node_info.node_guid ) ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_node_data: ERR 0013: " + "Already received node 0x%016" PRIx64 "\n", + cl_ntoh64( p_node->rec.node_info.node_guid ) ); + status = IB_ERROR; + goto Exit; + } ++p_node->count; @@ -3155,169 +3416,169 @@ osmtest_validate_node_data( IN osmtest_t * const p_osmt, */ if( ( p_node->comp.lid & p_node->rec.lid ) != ( p_node->comp.lid & p_rec->lid ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_node_data: ERR 0014: " - "Field mismatch node 0x%016" PRIx64 ", LID 0x%X\n" - "\t\t\t\tExpected LID 0x%X, received 0x%X\n", - cl_ntoh64( p_rec->node_info.node_guid ), - cl_ntoh16( p_rec->lid ), p_node->rec.lid, p_rec->lid ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_node_data: ERR 0014: " + "Field mismatch node 0x%016" PRIx64 ", LID 0x%X\n" + "\t\t\t\tExpected LID 0x%X, received 0x%X\n", + cl_ntoh64( p_rec->node_info.node_guid ), + cl_ntoh16( p_rec->lid ), p_node->rec.lid, p_rec->lid ); + status = IB_ERROR; + goto Exit; + } if( ( p_node->comp.node_info.base_version & p_node->rec.node_info.base_version ) != ( p_node->comp.node_info.base_version & p_rec->node_info.base_version ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_node_data: ERR 0015: " - "Field mismatch node 0x%016" PRIx64 ", LID 0x%X\n" - "\t\t\t\tExpected base_version 0x%X, received 0x%X\n", - cl_ntoh64( p_rec->node_info.node_guid ), - cl_ntoh16( p_rec->lid ), - p_node->rec.node_info.base_version, - p_rec->node_info.base_version ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_node_data: ERR 0015: " + "Field mismatch node 0x%016" PRIx64 ", LID 0x%X\n" + "\t\t\t\tExpected base_version 0x%X, received 0x%X\n", + cl_ntoh64( p_rec->node_info.node_guid ), + cl_ntoh16( p_rec->lid ), + p_node->rec.node_info.base_version, + p_rec->node_info.base_version ); + status = IB_ERROR; + goto Exit; + } if( ( p_node->comp.node_info.class_version & p_node->rec.node_info.class_version ) != ( p_node->comp.node_info.class_version & p_rec->node_info.class_version ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_node_data: ERR 0016: " - "Field mismatch node 0x%016" PRIx64 ", LID 0x%X\n" - "\t\t\t\tExpected class_version 0x%X, received 0x%X\n", - cl_ntoh64( p_rec->node_info.node_guid ), - cl_ntoh16( p_rec->lid ), - p_node->rec.node_info.class_version, - p_rec->node_info.class_version ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_node_data: ERR 0016: " + "Field mismatch node 0x%016" PRIx64 ", LID 0x%X\n" + "\t\t\t\tExpected class_version 0x%X, received 0x%X\n", + cl_ntoh64( p_rec->node_info.node_guid ), + cl_ntoh16( p_rec->lid ), + p_node->rec.node_info.class_version, + p_rec->node_info.class_version ); + status = IB_ERROR; + goto Exit; + } if( ( p_node->comp.node_info.node_type & p_node->rec.node_info.node_type ) != ( p_node->comp.node_info.node_type & p_rec->node_info.node_type ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_node_data: ERR 0017: " - "Field mismatch node 0x%016" PRIx64 ", LID 0x%X\n" - "\t\t\t\tExpected node_type 0x%X, received 0x%X\n", - cl_ntoh64( p_rec->node_info.node_guid ), - cl_ntoh16( p_rec->lid ), - p_node->rec.node_info.node_type, - p_rec->node_info.node_type ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_node_data: ERR 0017: " + "Field mismatch node 0x%016" PRIx64 ", LID 0x%X\n" + "\t\t\t\tExpected node_type 0x%X, received 0x%X\n", + cl_ntoh64( p_rec->node_info.node_guid ), + cl_ntoh16( p_rec->lid ), + p_node->rec.node_info.node_type, + p_rec->node_info.node_type ); + status = IB_ERROR; + goto Exit; + } if( ( p_node->comp.node_info.sys_guid & p_node->rec.node_info.sys_guid ) != ( p_node->comp.node_info.sys_guid & p_rec->node_info.sys_guid ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_node_data: ERR 0018: " - "Field mismatch node 0x%016" PRIx64 ", LID 0x%X\n" - "\t\t\t\tExpected sys_guid 0x%016" PRIx64 - ", received 0x%016" PRIx64 "\n", - cl_ntoh64( p_rec->node_info.node_guid ), - cl_ntoh16( p_rec->lid ), - cl_ntoh64( p_node->rec.node_info.sys_guid ), - cl_ntoh64( p_rec->node_info.sys_guid ) ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_node_data: ERR 0018: " + "Field mismatch node 0x%016" PRIx64 ", LID 0x%X\n" + "\t\t\t\tExpected sys_guid 0x%016" PRIx64 + ", received 0x%016" PRIx64 "\n", + cl_ntoh64( p_rec->node_info.node_guid ), + cl_ntoh16( p_rec->lid ), + cl_ntoh64( p_node->rec.node_info.sys_guid ), + cl_ntoh64( p_rec->node_info.sys_guid ) ); + status = IB_ERROR; + goto Exit; + } if( ( p_node->comp.node_info.node_guid & p_node->rec.node_info.node_guid ) != ( p_node->comp.node_info.node_guid & p_rec->node_info.node_guid ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_node_data: ERR 0019: " - "Field mismatch node 0x%016" PRIx64 ", LID 0x%X\n" - "\t\t\t\tExpected node_guid 0x%016" PRIx64 - ", received 0x%016" PRIx64 "\n", - cl_ntoh64( p_rec->node_info.node_guid ), - cl_ntoh16( p_rec->lid ), - cl_ntoh64( p_node->rec.node_info.node_guid ), - cl_ntoh64( p_rec->node_info.node_guid ) ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_node_data: ERR 0019: " + "Field mismatch node 0x%016" PRIx64 ", LID 0x%X\n" + "\t\t\t\tExpected node_guid 0x%016" PRIx64 + ", received 0x%016" PRIx64 "\n", + cl_ntoh64( p_rec->node_info.node_guid ), + cl_ntoh16( p_rec->lid ), + cl_ntoh64( p_node->rec.node_info.node_guid ), + cl_ntoh64( p_rec->node_info.node_guid ) ); + status = IB_ERROR; + goto Exit; + } if( ( p_node->comp.node_info.port_guid & p_node->rec.node_info.port_guid ) != ( p_node->comp.node_info.port_guid & p_rec->node_info.port_guid ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_node_data: ERR 0031: " - "Field mismatch node 0x%016" PRIx64 ", LID 0x%X\n" - "\t\t\t\tExpected port_guid 0x%016" PRIx64 - ", received 0x%016" PRIx64 "\n", - cl_ntoh64( p_rec->node_info.node_guid ), - cl_ntoh16( p_rec->lid ), - cl_ntoh64( p_node->rec.node_info.port_guid ), - cl_ntoh64( p_rec->node_info.port_guid ) ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_node_data: ERR 0031: " + "Field mismatch node 0x%016" PRIx64 ", LID 0x%X\n" + "\t\t\t\tExpected port_guid 0x%016" PRIx64 + ", received 0x%016" PRIx64 "\n", + cl_ntoh64( p_rec->node_info.node_guid ), + cl_ntoh16( p_rec->lid ), + cl_ntoh64( p_node->rec.node_info.port_guid ), + cl_ntoh64( p_rec->node_info.port_guid ) ); + status = IB_ERROR; + goto Exit; + } if( ( p_node->comp.node_info.partition_cap & p_node->rec.node_info.partition_cap ) != ( p_node->comp.node_info.partition_cap & p_rec->node_info.partition_cap ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_node_data: ERR 0032: " - "Field mismatch node 0x%016" PRIx64 ", LID 0x%X\n" - "\t\t\t\tExpected partition_cap 0x%X" - ", received 0x%X\n", - cl_ntoh64( p_rec->node_info.node_guid ), - cl_ntoh16( p_rec->lid ), - cl_ntoh16( p_node->rec.node_info.partition_cap ), - cl_ntoh16( p_rec->node_info.partition_cap ) ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_node_data: ERR 0032: " + "Field mismatch node 0x%016" PRIx64 ", LID 0x%X\n" + "\t\t\t\tExpected partition_cap 0x%X" + ", received 0x%X\n", + cl_ntoh64( p_rec->node_info.node_guid ), + cl_ntoh16( p_rec->lid ), + cl_ntoh16( p_node->rec.node_info.partition_cap ), + cl_ntoh16( p_rec->node_info.partition_cap ) ); + status = IB_ERROR; + goto Exit; + } if( ( p_node->comp.node_info.device_id & p_node->rec.node_info.device_id ) != ( p_node->comp.node_info.device_id & p_rec->node_info.device_id ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_node_data: ERR 0033: " - "Field mismatch node 0x%016" PRIx64 ", LID 0x%X\n" - "\t\t\t\tExpected device_id 0x%X" - ", received 0x%X\n", - cl_ntoh64( p_rec->node_info.node_guid ), - cl_ntoh16( p_rec->lid ), - cl_ntoh16( p_node->rec.node_info.device_id ), - cl_ntoh16( p_rec->node_info.device_id ) ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_node_data: ERR 0033: " + "Field mismatch node 0x%016" PRIx64 ", LID 0x%X\n" + "\t\t\t\tExpected device_id 0x%X" + ", received 0x%X\n", + cl_ntoh64( p_rec->node_info.node_guid ), + cl_ntoh16( p_rec->lid ), + cl_ntoh16( p_node->rec.node_info.device_id ), + cl_ntoh16( p_rec->node_info.device_id ) ); + status = IB_ERROR; + goto Exit; + } if( ( p_node->comp.node_info.revision & p_node->rec.node_info.revision ) != ( p_node->comp.node_info.revision & p_rec->node_info.revision ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_node_data: ERR 0034: " - "Field mismatch node 0x%016" PRIx64 ", LID 0x%X\n" - "\t\t\t\tExpected revision 0x%X" - ", received 0x%X\n", - cl_ntoh64( p_rec->node_info.node_guid ), - cl_ntoh16( p_rec->lid ), - cl_ntoh32( p_node->rec.node_info.revision ), - cl_ntoh32( p_rec->node_info.revision ) ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_node_data: ERR 0034: " + "Field mismatch node 0x%016" PRIx64 ", LID 0x%X\n" + "\t\t\t\tExpected revision 0x%X" + ", received 0x%X\n", + cl_ntoh64( p_rec->node_info.node_guid ), + cl_ntoh16( p_rec->lid ), + cl_ntoh32( p_node->rec.node_info.revision ), + cl_ntoh32( p_rec->node_info.revision ) ); + status = IB_ERROR; + goto Exit; + } Exit: OSM_LOG_EXIT( &p_osmt->log ); @@ -3342,15 +3603,15 @@ osmtest_validate_node_rec( IN osmtest_t * const p_osmt, p_tbl = &p_osmt->exp_subn.node_lid_tbl; p_node = ( node_t * ) cl_qmap_get( p_tbl, p_rec->lid ); if( p_node == ( node_t * ) cl_qmap_end( p_tbl ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_node_rec: ERR 0035: " - "Unexpected node 0x%016" PRIx64 ", LID 0x%X\n", - cl_ntoh64( p_rec->node_info.node_guid ), - cl_ntoh16( p_rec->lid ) ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_node_rec: ERR 0035: " + "Unexpected node 0x%016" PRIx64 ", LID 0x%X\n", + cl_ntoh64( p_rec->node_info.node_guid ), + cl_ntoh16( p_rec->lid ) ); + status = IB_ERROR; + goto Exit; + } status = osmtest_validate_node_data( p_osmt, p_node, p_rec ); @@ -3371,25 +3632,25 @@ osmtest_validate_port_data( IN osmtest_t * const p_osmt, OSM_LOG_ENTER( &p_osmt->log, osmtest_validate_port_data ); if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_port_data: " - "Checking port LID 0x%X, Num 0x%X\n", - cl_ntoh16( p_rec->lid ), p_rec->port_num); - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_port_data: " + "Checking port LID 0x%X, Num 0x%X\n", + cl_ntoh16( p_rec->lid ), p_rec->port_num); + } /* * Has this record already been returned? */ if( p_port->count != 0 ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_port_data: ERR 0036: " - "Already received port LID 0x%X, Num 0x%X\n", - cl_ntoh16( p_rec->lid ), p_rec->port_num); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_port_data: ERR 0036: " + "Already received port LID 0x%X, Num 0x%X\n", + cl_ntoh16( p_rec->lid ), p_rec->port_num); + status = IB_ERROR; + goto Exit; + } ++p_port->count; @@ -3398,435 +3659,442 @@ osmtest_validate_port_data( IN osmtest_t * const p_osmt, */ if( ( p_port->comp.lid & p_port->rec.lid ) != ( p_port->comp.lid & p_rec->lid ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_port_data: ERR 0037: " - "Field mismatch port LID 0x%X Num:0x%X\n" - "\t\t\t\tExpected LID 0x%X, received 0x%X\n", - cl_ntoh16( p_rec->lid ), p_rec->port_num, - p_port->rec.lid, p_rec->lid ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_port_data: ERR 0037: " + "Field mismatch port LID 0x%X Num:0x%X\n" + "\t\t\t\tExpected LID 0x%X, received 0x%X\n", + cl_ntoh16( p_rec->lid ), p_rec->port_num, + p_port->rec.lid, p_rec->lid ); + status = IB_ERROR; + goto Exit; + } if( ( p_port->comp.port_num & p_port->rec.port_num ) != ( p_port->comp.port_num & p_rec->port_num ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_port_data: ERR 0038: " - "Field mismatch port LID 0x%X Num:0x%X\n" - "\t\t\t\tExpected port_num 0x%X, received 0x%X\n", - cl_ntoh16( p_rec->lid ), p_rec->port_num, - p_port->rec.port_num, p_rec->port_num ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_port_data: ERR 0038: " + "Field mismatch port LID 0x%X Num:0x%X\n" + "\t\t\t\tExpected port_num 0x%X, received 0x%X\n", + cl_ntoh16( p_rec->lid ), p_rec->port_num, + p_port->rec.port_num, p_rec->port_num ); + status = IB_ERROR; + goto Exit; + } if( ( p_port->comp.port_info.m_key & p_port->rec.port_info.m_key ) != ( p_port->comp.port_info.m_key & p_rec->port_info.m_key ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_port_data: ERR 0039: " - "Field mismatch port LID 0x%X Num:0x%X\n" - "\t\t\t\tExpected m_key 0x%016" PRIx64 ", received 0x%016" PRIx64 "\n", - cl_ntoh16( p_rec->lid ), p_rec->port_num, - p_port->rec.port_info.m_key, p_rec->port_info.m_key ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_port_data: ERR 0039: " + "Field mismatch port LID 0x%X Num:0x%X\n" + "\t\t\t\tExpected m_key 0x%016" PRIx64 ", received 0x%016" PRIx64 "\n", + cl_ntoh16( p_rec->lid ), p_rec->port_num, + p_port->rec.port_info.m_key, p_rec->port_info.m_key ); + status = IB_ERROR; + goto Exit; + } if( ( p_port->comp.port_info.subnet_prefix & p_port->rec.port_info.subnet_prefix ) != ( p_port->comp.port_info.subnet_prefix & p_rec->port_info.subnet_prefix ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_port_data: ERR 0040: " - "Field mismatch port LID 0x%X Num:0x%X\n" - "\t\t\t\tExpected subnet_prefix 0x%016" PRIx64 ", received 0x%016" PRIx64 "\n", - cl_ntoh16( p_rec->lid ), p_rec->port_num, - p_port->rec.port_info.subnet_prefix, p_rec->port_info.subnet_prefix ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_port_data: ERR 0040: " + "Field mismatch port LID 0x%X Num:0x%X\n" + "\t\t\t\tExpected subnet_prefix 0x%016" PRIx64 ", received 0x%016" PRIx64 "\n", + cl_ntoh16( p_rec->lid ), p_rec->port_num, + p_port->rec.port_info.subnet_prefix, p_rec->port_info.subnet_prefix ); + status = IB_ERROR; + goto Exit; + } if( ( p_port->comp.port_info.base_lid & p_port->rec.port_info.base_lid ) != ( p_port->comp.port_info.base_lid & p_rec->port_info.base_lid ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_port_data: ERR 0041: " - "Field mismatch port LID 0x%X Num:0x%X\n" - "\t\t\t\tExpected base_lid 0x%X, received 0x%X\n", - cl_ntoh16( p_rec->lid ), p_rec->port_num, - p_port->rec.port_info.base_lid, p_rec->port_info.base_lid ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_port_data: ERR 0041: " + "Field mismatch port LID 0x%X Num:0x%X\n" + "\t\t\t\tExpected base_lid 0x%X, received 0x%X\n", + cl_ntoh16( p_rec->lid ), p_rec->port_num, + p_port->rec.port_info.base_lid, p_rec->port_info.base_lid ); + status = IB_ERROR; + goto Exit; + } if( ( p_port->comp.port_info.master_sm_base_lid & p_port->rec.port_info.master_sm_base_lid ) != ( p_port->comp.port_info.master_sm_base_lid & p_rec->port_info.master_sm_base_lid ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_port_data: ERR 0042: " - "Field mismatch port LID 0x%X Num:0x%X\n" - "\t\t\t\tExpected master_sm_base_lid 0x%X, received 0x%X\n", - cl_ntoh16( p_rec->lid ), p_rec->port_num, - p_port->rec.port_info.master_sm_base_lid, p_rec->port_info.master_sm_base_lid ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_port_data: ERR 0042: " + "Field mismatch port LID 0x%X Num:0x%X\n" + "\t\t\t\tExpected master_sm_base_lid 0x%X, received 0x%X\n", + cl_ntoh16( p_rec->lid ), p_rec->port_num, + p_port->rec.port_info.master_sm_base_lid, p_rec->port_info.master_sm_base_lid ); + status = IB_ERROR; + goto Exit; + } if( ( p_port->comp.port_info.capability_mask & p_port->rec.port_info.capability_mask ) != ( p_port->comp.port_info.capability_mask & p_rec->port_info.capability_mask ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_port_data: ERR 0043: " - "Field mismatch port LID 0x%X Num:0x%X\n" - "\t\t\t\tExpected capability_mask 0x%X, received 0x%X\n", - cl_ntoh16( p_rec->lid ), p_rec->port_num, - p_port->rec.port_info.capability_mask, p_rec->port_info.capability_mask ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_port_data: ERR 0043: " + "Field mismatch port LID 0x%X Num:0x%X\n" + "\t\t\t\tExpected capability_mask 0x%X, received 0x%X\n", + cl_ntoh16( p_rec->lid ), p_rec->port_num, + p_port->rec.port_info.capability_mask, p_rec->port_info.capability_mask ); + status = IB_ERROR; + goto Exit; + } if( ( p_port->comp.port_info.diag_code & p_port->rec.port_info.diag_code ) != ( p_port->comp.port_info.diag_code & p_rec->port_info.diag_code ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_port_data: ERR 0044: " - "Field mismatch port LID 0x%X Num:0x%X\n" - "\t\t\t\tExpected diag_code 0x%X, received 0x%X\n", - cl_ntoh16( p_rec->lid ), p_rec->port_num, - p_port->rec.port_info.diag_code, p_rec->port_info.diag_code ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_port_data: ERR 0044: " + "Field mismatch port LID 0x%X Num:0x%X\n" + "\t\t\t\tExpected diag_code 0x%X, received 0x%X\n", + cl_ntoh16( p_rec->lid ), p_rec->port_num, + p_port->rec.port_info.diag_code, p_rec->port_info.diag_code ); + status = IB_ERROR; + goto Exit; + } if( ( p_port->comp.port_info.m_key_lease_period & p_port->rec.port_info.m_key_lease_period ) != ( p_port->comp.port_info.m_key_lease_period & p_rec->port_info.m_key_lease_period ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_port_data: ERR 0045: " - "Field mismatch port LID 0x%X Num:0x%X\n" - "\t\t\t\tExpected m_key_lease_period 0x%X, received 0x%X\n", - cl_ntoh16( p_rec->lid ), p_rec->port_num, - p_port->rec.port_info.m_key_lease_period, p_rec->port_info.m_key_lease_period ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_port_data: ERR 0045: " + "Field mismatch port LID 0x%X Num:0x%X\n" + "\t\t\t\tExpected m_key_lease_period 0x%X, received 0x%X\n", + cl_ntoh16( p_rec->lid ), p_rec->port_num, + p_port->rec.port_info.m_key_lease_period, p_rec->port_info.m_key_lease_period ); + status = IB_ERROR; + goto Exit; + } if( ( p_port->comp.port_info.local_port_num & p_port->rec.port_info.local_port_num ) != ( p_port->comp.port_info.local_port_num & p_rec->port_info.local_port_num ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_port_data: ERR 0046: " - "Field mismatch port LID 0x%X Num:0x%X\n" - "\t\t\t\tExpected local_port_num 0x%X, received 0x%X\n", - cl_ntoh16( p_rec->lid ), p_rec->port_num, - p_port->rec.port_info.local_port_num, p_rec->port_info.local_port_num ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_port_data: ERR 0046: " + "Field mismatch port LID 0x%X Num:0x%X\n" + "\t\t\t\tExpected local_port_num 0x%X, received 0x%X\n", + cl_ntoh16( p_rec->lid ), p_rec->port_num, + p_port->rec.port_info.local_port_num, p_rec->port_info.local_port_num ); + status = IB_ERROR; + goto Exit; + } if( ( p_port->comp.port_info.link_width_enabled & p_port->rec.port_info.link_width_enabled ) != ( p_port->comp.port_info.link_width_enabled & p_rec->port_info.link_width_enabled ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_port_data: ERR 0047: " - "Field mismatch port LID 0x%X Num:0x%X\n" - "\t\t\t\tExpected link_width_enabled 0x%X, received 0x%X\n", - cl_ntoh16( p_rec->lid ), p_rec->port_num, - p_port->rec.port_info.link_width_enabled, p_rec->port_info.link_width_enabled ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_port_data: ERR 0047: " + "Field mismatch port LID 0x%X Num:0x%X\n" + "\t\t\t\tExpected link_width_enabled 0x%X, received 0x%X\n", + cl_ntoh16( p_rec->lid ), p_rec->port_num, + p_port->rec.port_info.link_width_enabled, p_rec->port_info.link_width_enabled ); + status = IB_ERROR; + goto Exit; + } if( ( p_port->comp.port_info.link_width_supported & p_port->rec.port_info.link_width_supported ) != ( p_port->comp.port_info.link_width_supported & p_rec->port_info.link_width_supported ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_port_data: ERR 0048: " - "Field mismatch port LID 0x%X Num:0x%X\n" - "\t\t\t\tExpected link_width_supported 0x%X, received 0x%X\n", - cl_ntoh16( p_rec->lid ), p_rec->port_num, - p_port->rec.port_info.link_width_supported, p_rec->port_info.link_width_supported ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_port_data: ERR 0048: " + "Field mismatch port LID 0x%X Num:0x%X\n" + "\t\t\t\tExpected link_width_supported 0x%X, received 0x%X\n", + cl_ntoh16( p_rec->lid ), p_rec->port_num, + p_port->rec.port_info.link_width_supported, p_rec->port_info.link_width_supported ); + status = IB_ERROR; + goto Exit; + } if( ( p_port->comp.port_info.link_width_active & p_port->rec.port_info.link_width_active ) != ( p_port->comp.port_info.link_width_active & p_rec->port_info.link_width_active ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_port_data: ERR 0049: " - "Field mismatch port LID 0x%X Num:0x%X\n" - "\t\t\t\tExpected link_width_active 0x%X, received 0x%X\n", - cl_ntoh16( p_rec->lid ), p_rec->port_num, - p_port->rec.port_info.link_width_active, p_rec->port_info.link_width_active ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_port_data: ERR 0049: " + "Field mismatch port LID 0x%X Num:0x%X\n" + "\t\t\t\tExpected link_width_active 0x%X, received 0x%X\n", + cl_ntoh16( p_rec->lid ), p_rec->port_num, + p_port->rec.port_info.link_width_active, p_rec->port_info.link_width_active ); + status = IB_ERROR; + goto Exit; + } if( ( p_port->comp.port_info.link_speed & p_port->rec.port_info.link_speed ) != ( p_port->comp.port_info.link_speed & p_rec->port_info.link_speed ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_port_data: ERR 0054: " - "Field mismatch port LID 0x%X Num:0x%X\n" - "\t\t\t\tExpected link_speed 0x%X, received 0x%X\n", - cl_ntoh16( p_rec->lid ), p_rec->port_num, - p_port->rec.port_info.link_speed, p_rec->port_info.link_speed ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_port_data: ERR 0054: " + "Field mismatch port LID 0x%X Num:0x%X\n" + "\t\t\t\tExpected link_speed 0x%X, received 0x%X\n", + cl_ntoh16( p_rec->lid ), p_rec->port_num, + p_port->rec.port_info.link_speed, p_rec->port_info.link_speed ); + status = IB_ERROR; + goto Exit; + } if( ( p_port->comp.port_info.state_info1 & p_port->rec.port_info.state_info1 ) != ( p_port->comp.port_info.state_info1 & p_rec->port_info.state_info1 ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_port_data: ERR 0055: " - "Field mismatch port LID 0x%X Num:0x%X\n" - "\t\t\t\tExpected state_info1 0x%X, received 0x%X\n", - cl_ntoh16( p_rec->lid ), p_rec->port_num, - p_port->rec.port_info.state_info1, p_rec->port_info.state_info1 ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_port_data: ERR 0055: " + "Field mismatch port LID 0x%X Num:0x%X\n" + "\t\t\t\tExpected state_info1 0x%X, received 0x%X\n", + cl_ntoh16( p_rec->lid ), p_rec->port_num, + p_port->rec.port_info.state_info1, p_rec->port_info.state_info1 ); + status = IB_ERROR; + goto Exit; + } if( ( p_port->comp.port_info.state_info2 & p_port->rec.port_info.state_info2 ) != ( p_port->comp.port_info.state_info2 & p_rec->port_info.state_info2 ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_port_data: ERR 0058: " - "Field mismatch port LID 0x%X Num:0x%X\n" - "\t\t\t\tExpected state_info2 0x%X, received 0x%X\n", - cl_ntoh16( p_rec->lid ), p_rec->port_num, - p_port->rec.port_info.state_info2, p_rec->port_info.state_info2 ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_port_data: ERR 0058: " + "Field mismatch port LID 0x%X Num:0x%X\n" + "\t\t\t\tExpected state_info2 0x%X, received 0x%X\n", + cl_ntoh16( p_rec->lid ), p_rec->port_num, + p_port->rec.port_info.state_info2, p_rec->port_info.state_info2 ); + status = IB_ERROR; + goto Exit; + } if( ( p_port->comp.port_info.mkey_lmc & p_port->rec.port_info.mkey_lmc ) != ( p_port->comp.port_info.mkey_lmc & p_rec->port_info.mkey_lmc ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_port_data: ERR 0059: " - "Field mismatch port LID 0x%X Num:0x%X\n" - "\t\t\t\tExpected mkey_lmc 0x%X, received 0x%X\n", - cl_ntoh16( p_rec->lid ), p_rec->port_num, - p_port->rec.port_info.mkey_lmc, p_rec->port_info.mkey_lmc ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_port_data: ERR 0059: " + "Field mismatch port LID 0x%X Num:0x%X\n" + "\t\t\t\tExpected mkey_lmc 0x%X, received 0x%X\n", + cl_ntoh16( p_rec->lid ), p_rec->port_num, + p_port->rec.port_info.mkey_lmc, p_rec->port_info.mkey_lmc ); + status = IB_ERROR; + goto Exit; + } if( ( p_port->comp.port_info.link_speed & p_port->rec.port_info.link_speed ) != ( p_port->comp.port_info.link_speed & p_rec->port_info.link_speed ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_port_data: ERR 0060: " - "Field mismatch port LID 0x%X Num:0x%X\n" - "\t\t\t\tExpected link_speed 0x%X, received 0x%X\n", - cl_ntoh16( p_rec->lid ), p_rec->port_num, - p_port->rec.port_info.link_speed, p_rec->port_info.link_speed ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_port_data: ERR 0060: " + "Field mismatch port LID 0x%X Num:0x%X\n" + "\t\t\t\tExpected link_speed 0x%X, received 0x%X\n", + cl_ntoh16( p_rec->lid ), p_rec->port_num, + p_port->rec.port_info.link_speed, p_rec->port_info.link_speed ); + status = IB_ERROR; + goto Exit; + } if( ( p_port->comp.port_info.mtu_smsl & p_port->rec.port_info.mtu_smsl ) != ( p_port->comp.port_info.mtu_smsl & p_rec->port_info.mtu_smsl ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_port_data: ERR 0061: " - "Field mismatch port LID 0x%X Num:0x%X\n" - "\t\t\t\tExpected mtu_smsl 0x%X, received 0x%X\n", - cl_ntoh16( p_rec->lid ), p_rec->port_num, - p_port->rec.port_info.mtu_smsl, p_rec->port_info.mtu_smsl ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_port_data: ERR 0061: " + "Field mismatch port LID 0x%X Num:0x%X\n" + "\t\t\t\tExpected mtu_smsl 0x%X, received 0x%X\n", + cl_ntoh16( p_rec->lid ), p_rec->port_num, + p_port->rec.port_info.mtu_smsl, p_rec->port_info.mtu_smsl ); + status = IB_ERROR; + goto Exit; + } if( ( p_port->comp.port_info.vl_cap & p_port->rec.port_info.vl_cap ) != ( p_port->comp.port_info.vl_cap & p_rec->port_info.vl_cap ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_port_data: ERR 0062: " - "Field mismatch port LID 0x%X Num:0x%X\n" - "\t\t\t\tExpected vl_cap 0x%X, received 0x%X\n", - cl_ntoh16( p_rec->lid ), p_rec->port_num, - p_port->rec.port_info.vl_cap, p_rec->port_info.vl_cap ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_port_data: ERR 0062: " + "Field mismatch port LID 0x%X Num:0x%X\n" + "\t\t\t\tExpected vl_cap 0x%X, received 0x%X\n", + cl_ntoh16( p_rec->lid ), p_rec->port_num, + p_port->rec.port_info.vl_cap, p_rec->port_info.vl_cap ); + status = IB_ERROR; + goto Exit; + } if( ( p_port->comp.port_info.vl_high_limit & p_port->rec.port_info.vl_high_limit ) != ( p_port->comp.port_info.vl_high_limit & p_rec->port_info.vl_high_limit ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_port_data: ERR 0082: " - "Field mismatch port LID 0x%X Num:0x%X\n" - "\t\t\t\tExpected vl_high_limit 0x%X, received 0x%X\n", - cl_ntoh16( p_rec->lid ), p_rec->port_num, - p_port->rec.port_info.vl_high_limit, p_rec->port_info.vl_high_limit ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_port_data: ERR 0082: " + "Field mismatch port LID 0x%X Num:0x%X\n" + "\t\t\t\tExpected vl_high_limit 0x%X, received 0x%X\n", + cl_ntoh16( p_rec->lid ), p_rec->port_num, + p_port->rec.port_info.vl_high_limit, p_rec->port_info.vl_high_limit ); + status = IB_ERROR; + goto Exit; + } if( ( p_port->comp.port_info.vl_arb_high_cap & p_port->rec.port_info.vl_arb_high_cap ) != ( p_port->comp.port_info.vl_arb_high_cap & p_rec->port_info.vl_arb_high_cap ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_port_data: ERR 0083: " - "Field mismatch port LID 0x%X Num:0x%X\n" - "\t\t\t\tExpected vl_arb_high_cap 0x%X, received 0x%X\n", - cl_ntoh16( p_rec->lid ), p_rec->port_num, - p_port->rec.port_info.vl_arb_high_cap, p_rec->port_info.vl_arb_high_cap ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_port_data: ERR 0083: " + "Field mismatch port LID 0x%X Num:0x%X\n" + "\t\t\t\tExpected vl_arb_high_cap 0x%X, received 0x%X\n", + cl_ntoh16( p_rec->lid ), p_rec->port_num, + p_port->rec.port_info.vl_arb_high_cap, p_rec->port_info.vl_arb_high_cap ); + status = IB_ERROR; + goto Exit; + } if( ( p_port->comp.port_info.vl_arb_low_cap & p_port->rec.port_info.vl_arb_low_cap ) != ( p_port->comp.port_info.vl_arb_low_cap & p_rec->port_info.vl_arb_low_cap ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_port_data: ERR 0084: " - "Field mismatch port LID 0x%X Num:0x%X\n" - "\t\t\t\tExpected vl_arb_low_cap 0x%X, received 0x%X\n", - cl_ntoh16( p_rec->lid ), p_rec->port_num, - p_port->rec.port_info.vl_arb_low_cap, p_rec->port_info.vl_arb_low_cap ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_port_data: ERR 0084: " + "Field mismatch port LID 0x%X Num:0x%X\n" + "\t\t\t\tExpected vl_arb_low_cap 0x%X, received 0x%X\n", + cl_ntoh16( p_rec->lid ), p_rec->port_num, + p_port->rec.port_info.vl_arb_low_cap, p_rec->port_info.vl_arb_low_cap ); + status = IB_ERROR; + goto Exit; + } if( ( p_port->comp.port_info.mtu_cap & p_port->rec.port_info.mtu_cap ) != ( p_port->comp.port_info.mtu_cap & p_rec->port_info.mtu_cap ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_port_data: ERR 0085: " - "Field mismatch port LID 0x%X Num:0x%X\n" - "\t\t\t\tExpected mtu_cap 0x%X, received 0x%X\n", - cl_ntoh16( p_rec->lid ), p_rec->port_num, - p_port->rec.port_info.mtu_cap, p_rec->port_info.mtu_cap ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_port_data: ERR 0085: " + "Field mismatch port LID 0x%X Num:0x%X\n" + "\t\t\t\tExpected mtu_cap 0x%X, received 0x%X\n", + cl_ntoh16( p_rec->lid ), p_rec->port_num, + p_port->rec.port_info.mtu_cap, p_rec->port_info.mtu_cap ); + status = IB_ERROR; + goto Exit; + } - /* this is a dynamic attribute - if( ( p_port->comp.port_info.vl_stall_life & p_port->rec.port_info.vl_stall_life ) != - ( p_port->comp.port_info.vl_stall_life & p_rec->port_info.vl_stall_life ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_port_data: ERR 0129: " - "Field mismatch port LID 0x%X Num:0x%X\n" - "\t\t\t\tExpected vl_stall_life 0x%X, received 0x%X\n", - cl_ntoh16( p_rec->lid ), p_rec->port_num, - p_port->rec.port_info.vl_stall_life, p_rec->port_info.vl_stall_life ); - status = IB_ERROR; - goto Exit; - } - */ +#if 0 + /* this is a dynamic attribute */ + if( ( p_port->comp.port_info.vl_stall_life & p_port->rec.port_info.vl_stall_life ) != + ( p_port->comp.port_info.vl_stall_life & p_rec->port_info.vl_stall_life ) ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_port_data: ERR 012F: " + "Field mismatch port LID 0x%X Num:0x%X\n" + "\t\t\t\tExpected vl_stall_life 0x%X, received 0x%X\n", + cl_ntoh16( p_rec->lid ), p_rec->port_num, + p_port->rec.port_info.vl_stall_life, + p_rec->port_info.vl_stall_life ); + status = IB_ERROR; + goto Exit; + } +#endif if( ( p_port->comp.port_info.vl_enforce & p_port->rec.port_info.vl_enforce ) != ( p_port->comp.port_info.vl_enforce & p_rec->port_info.vl_enforce ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_port_data: ERR 0086: " - "Field mismatch port LID 0x%X Num:0x%X\n" - "\t\t\t\tExpected vl_enforce 0x%X, received 0x%X\n", - cl_ntoh16( p_rec->lid ), p_rec->port_num, - p_port->rec.port_info.vl_enforce, p_rec->port_info.vl_enforce ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_port_data: ERR 0086: " + "Field mismatch port LID 0x%X Num:0x%X\n" + "\t\t\t\tExpected vl_enforce 0x%X, received 0x%X\n", + cl_ntoh16( p_rec->lid ), p_rec->port_num, + p_port->rec.port_info.vl_enforce, p_rec->port_info.vl_enforce ); + status = IB_ERROR; + goto Exit; + } if( ( p_port->comp.port_info.m_key_violations & p_port->rec.port_info.m_key_violations ) != ( p_port->comp.port_info.m_key_violations & p_rec->port_info.m_key_violations ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_port_data: ERR 0087: " - "Field mismatch port LID 0x%X Num:0x%X\n" - "\t\t\t\tExpected m_key_violations 0x%X, received 0x%X\n", - cl_ntoh16( p_rec->lid ), p_rec->port_num, - p_port->rec.port_info.m_key_violations, p_rec->port_info.m_key_violations ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_port_data: ERR 0087: " + "Field mismatch port LID 0x%X Num:0x%X\n" + "\t\t\t\tExpected m_key_violations 0x%X, received 0x%X\n", + cl_ntoh16( p_rec->lid ), p_rec->port_num, + cl_ntoh16( p_port->rec.port_info.m_key_violations ), + cl_ntoh16( p_rec->port_info.m_key_violations ) ); + status = IB_ERROR; + goto Exit; + } if( ( p_port->comp.port_info.p_key_violations & p_port->rec.port_info.p_key_violations ) != ( p_port->comp.port_info.p_key_violations & p_rec->port_info.p_key_violations ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_port_data: ERR 0088: " - "Field mismatch port LID 0x%X Num:0x%X\n" - "\t\t\t\tExpected p_key_violations 0x%X, received 0x%X\n", - cl_ntoh16( p_rec->lid ), p_rec->port_num, - p_port->rec.port_info.p_key_violations, p_rec->port_info.p_key_violations ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_port_data: ERR 0088: " + "Field mismatch port LID 0x%X Num:0x%X\n" + "\t\t\t\tExpected p_key_violations 0x%X, received 0x%X\n", + cl_ntoh16( p_rec->lid ), p_rec->port_num, + cl_ntoh16( p_port->rec.port_info.p_key_violations ), + cl_ntoh16( p_rec->port_info.p_key_violations ) ); + status = IB_ERROR; + goto Exit; + } if( ( p_port->comp.port_info.q_key_violations & p_port->rec.port_info.q_key_violations ) != ( p_port->comp.port_info.q_key_violations & p_rec->port_info.q_key_violations ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_port_data: ERR 0089: " - "Field mismatch port LID 0x%X Num:0x%X\n" - "\t\t\t\tExpected q_key_violations 0x%X, received 0x%X\n", - cl_ntoh16( p_rec->lid ), p_rec->port_num, - p_port->rec.port_info.q_key_violations, p_rec->port_info.q_key_violations ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_port_data: ERR 0089: " + "Field mismatch port LID 0x%X Num:0x%X\n" + "\t\t\t\tExpected q_key_violations 0x%X, received 0x%X\n", + cl_ntoh16( p_rec->lid ), p_rec->port_num, + cl_ntoh16( p_port->rec.port_info.q_key_violations ), + cl_ntoh16( p_rec->port_info.q_key_violations ) ); + status = IB_ERROR; + goto Exit; + } if( ( p_port->comp.port_info.guid_cap & p_port->rec.port_info.guid_cap ) != ( p_port->comp.port_info.guid_cap & p_rec->port_info.guid_cap ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_port_data: ERR 0090: " - "Field mismatch port LID 0x%X Num:0x%X\n" - "\t\t\t\tExpected guid_cap 0x%X, received 0x%X\n", - cl_ntoh16( p_rec->lid ), p_rec->port_num, - p_port->rec.port_info.guid_cap, p_rec->port_info.guid_cap ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_port_data: ERR 0090: " + "Field mismatch port LID 0x%X Num:0x%X\n" + "\t\t\t\tExpected guid_cap 0x%X, received 0x%X\n", + cl_ntoh16( p_rec->lid ), p_rec->port_num, + p_port->rec.port_info.guid_cap, p_rec->port_info.guid_cap ); + status = IB_ERROR; + goto Exit; + } if( ( p_port->comp.port_info.subnet_timeout & p_port->rec.port_info.subnet_timeout ) != ( p_port->comp.port_info.subnet_timeout & p_rec->port_info.subnet_timeout ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_port_data: ERR 0091: " - "Field mismatch port LID 0x%X Num:0x%X\n" - "\t\t\t\tExpected subnet_timeout 0x%X, received 0x%X\n", - cl_ntoh16( p_rec->lid ), p_rec->port_num, - ib_port_info_get_timeout(&p_port->rec.port_info), - ib_port_info_get_timeout(&p_rec->port_info) ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_port_data: ERR 0091: " + "Field mismatch port LID 0x%X Num:0x%X\n" + "\t\t\t\tExpected subnet_timeout 0x%X, received 0x%X\n", + cl_ntoh16( p_rec->lid ), p_rec->port_num, + ib_port_info_get_timeout(&p_port->rec.port_info), + ib_port_info_get_timeout(&p_rec->port_info) ); + status = IB_ERROR; + goto Exit; + } if( ( p_port->comp.port_info.resp_time_value & p_port->rec.port_info.resp_time_value ) != ( p_port->comp.port_info.resp_time_value & p_rec->port_info.resp_time_value ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_port_data: ERR 0092: " - "Field mismatch port LID 0x%X Num:0x%X\n" - "\t\t\t\tExpected resp_time_value 0x%X, received 0x%X\n", - cl_ntoh16( p_rec->lid ), p_rec->port_num, - p_port->rec.port_info.resp_time_value, p_rec->port_info.resp_time_value ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_port_data: ERR 0092: " + "Field mismatch port LID 0x%X Num:0x%X\n" + "\t\t\t\tExpected resp_time_value 0x%X, received 0x%X\n", + cl_ntoh16( p_rec->lid ), p_rec->port_num, + p_port->rec.port_info.resp_time_value, + p_rec->port_info.resp_time_value ); + status = IB_ERROR; + goto Exit; + } if( ( p_port->comp.port_info.error_threshold & p_port->rec.port_info.error_threshold ) != ( p_port->comp.port_info.error_threshold & p_rec->port_info.error_threshold ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_port_data: ERR 0093: " - "Field mismatch port LID 0x%X Num:0x%X\n" - "\t\t\t\tExpected error_threshold 0x%X, received 0x%X\n", - cl_ntoh16( p_rec->lid ), p_rec->port_num, - p_port->rec.port_info.error_threshold, p_rec->port_info.error_threshold ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_port_data: ERR 0093: " + "Field mismatch port LID 0x%X Num:0x%X\n" + "\t\t\t\tExpected error_threshold 0x%X, received 0x%X\n", + cl_ntoh16( p_rec->lid ), p_rec->port_num, + p_port->rec.port_info.error_threshold, + p_rec->port_info.error_threshold ); + status = IB_ERROR; + goto Exit; + } Exit: OSM_LOG_EXIT( &p_osmt->log ); @@ -3852,14 +4120,14 @@ osmtest_validate_port_rec( IN osmtest_t * const p_osmt, p_tbl = &p_osmt->exp_subn.port_key_tbl; p_port = ( port_t * ) cl_qmap_get( p_tbl, port_gen_id( p_rec->lid, p_rec->port_num)); if( p_port == ( port_t * ) cl_qmap_end( p_tbl ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_port_rec: ERR 0094: " - "Unexpected port LID 0x%X, Num:0x%X\n", - cl_ntoh16( p_rec->lid ), p_rec->port_num ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_port_rec: ERR 0094: " + "Unexpected port LID 0x%X, Num:0x%X\n", + cl_ntoh16( p_rec->lid ), p_rec->port_num ); + status = IB_ERROR; + goto Exit; + } status = osmtest_validate_port_data( p_osmt, p_port, p_rec ); @@ -3887,14 +4155,14 @@ osmtest_validate_path_rec( IN osmtest_t * const p_osmt, p_path = ( path_t * ) cl_qmap_get( p_tbl, osmtest_path_rec_key_get( p_rec ) ); if( p_path == ( path_t * ) cl_qmap_end( p_tbl ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_path_rec: ERR 0095: " - "Unexpected path SLID 0x%X to DLID 0x%X\n", - cl_ntoh16( p_rec->slid ), cl_ntoh16( p_rec->dlid ) ); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_path_rec: ERR 0095: " + "Unexpected path SLID 0x%X to DLID 0x%X\n", + cl_ntoh16( p_rec->slid ), cl_ntoh16( p_rec->dlid ) ); + status = IB_ERROR; + goto Exit; + } status = osmtest_validate_path_data( p_osmt, p_path, p_rec ); @@ -3904,6 +4172,8 @@ osmtest_validate_path_rec( IN osmtest_t * const p_osmt, } #ifdef VENDOR_RMPP_SUPPORT +ib_net64_t portguid = 0; + /********************************************************************** **********************************************************************/ static ib_api_status_t @@ -3917,7 +4187,7 @@ osmtest_validate_all_node_recs( IN osmtest_t * const p_osmt ) OSM_LOG_ENTER( &p_osmt->log, osmtest_validate_all_node_recs ); - cl_memclr( &context, sizeof( context ) ); + memset( &context, 0, sizeof( context ) ); /* * Do a blocking query for all NodeRecords in the subnet. @@ -3926,22 +4196,22 @@ osmtest_validate_all_node_recs( IN osmtest_t * const p_osmt ) sizeof( *p_rec ), &context ); if( status != IB_SUCCESS ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_all_node_recs: ERR 0096: " - "osmtest_get_all_recs failed (%s)\n", - ib_get_err_str( status ) ); - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_all_node_recs: ERR 0096: " + "osmtest_get_all_recs failed (%s)\n", + ib_get_err_str( status ) ); + goto Exit; + } num_recs = context.result.result_cnt; if( osm_log_is_active( &p_osmt->log, OSM_LOG_VERBOSE ) ) - { - osm_log( &p_osmt->log, OSM_LOG_VERBOSE, - "osmtest_validate_all_node_recs: " - "Received %u records\n", num_recs ); - } + { + osm_log( &p_osmt->log, OSM_LOG_VERBOSE, + "osmtest_validate_all_node_recs: " + "Received %zu records\n", num_recs ); + } /* * Compare the received records to the database. @@ -3949,354 +4219,833 @@ osmtest_validate_all_node_recs( IN osmtest_t * const p_osmt ) osmtest_prepare_db( p_osmt ); for( i = 0; i < num_recs; i++ ) - { - p_rec = osmv_get_query_node_rec( context.result.p_result_madw, i ); + { + p_rec = osmv_get_query_node_rec( context.result.p_result_madw, i ); - status = osmtest_validate_node_rec( p_osmt, p_rec ); - if( status != IB_SUCCESS ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_all_node_recs: ERR 0097: " - "osmtest_valid_node_rec failed (%s)\n", - ib_get_err_str( status ) ); - goto Exit; - } - } - - status = osmtest_check_missing_nodes( p_osmt ); - if( status != IB_SUCCESS ) + status = osmtest_validate_node_rec( p_osmt, p_rec ); + if( status != IB_SUCCESS ) { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_all_node_recs: ERR 0098: " - "osmtest_check_missing_nodes failed (%s)\n", + "osmtest_validate_all_node_recs: ERR 0097: " + "osmtest_valid_node_rec failed (%s)\n", ib_get_err_str( status ) ); goto Exit; } + if (!portguid) + portguid = p_rec->node_info.port_guid; + } + + status = osmtest_check_missing_nodes( p_osmt ); + if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_all_node_recs: ERR 0098: " + "osmtest_check_missing_nodes failed (%s)\n", + ib_get_err_str( status ) ); + goto Exit; + } Exit: /* * Return the IB query MAD to the pool as necessary. */ if( context.result.p_result_madw != NULL ) - { - osm_mad_pool_put( &p_osmt->mad_pool, context.result.p_result_madw ); - context.result.p_result_madw = NULL; - } + { + osm_mad_pool_put( &p_osmt->mad_pool, context.result.p_result_madw ); + context.result.p_result_madw = NULL; + } OSM_LOG_EXIT( &p_osmt->log ); return ( status ); } -#endif -#ifdef VENDOR_RMPP_SUPPORT /********************************************************************** **********************************************************************/ static ib_api_status_t -osmtest_validate_all_path_recs( IN osmtest_t * const p_osmt ) -{ +osmtest_validate_all_guidinfo_recs( IN osmtest_t * const p_osmt ) +{ osmtest_req_context_t context; - const ib_path_rec_t *p_rec; - uint32_t i; + const ib_guidinfo_record_t *p_rec; cl_status_t status; size_t num_recs; - OSM_LOG_ENTER( &p_osmt->log, osmtest_validate_all_path_recs ); + OSM_LOG_ENTER( &p_osmt->log, osmtest_validate_all_guidinfo_recs ); - cl_memclr( &context, sizeof( context ) ); + memset( &context, 0, sizeof( context ) ); /* - * Do a blocking query for all PathRecords in the subnet. + * Do a blocking query for all GuidInfoRecords in the subnet. */ - status = osmtest_get_all_recs( p_osmt, IB_MAD_ATTR_PATH_RECORD, + status = osmtest_get_all_recs( p_osmt, IB_MAD_ATTR_GUIDINFO_RECORD, sizeof( *p_rec ), &context ); + if( status != IB_SUCCESS ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_all_path_recs: ERR 0099: " - "osmtest_get_all_recs failed (%s)\n", - ib_get_err_str( status ) ); - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_all_guidinfo_recs: ERR 0099: " + "osmtest_get_all_recs failed (%s)\n", + ib_get_err_str( status ) ); + goto Exit; + } num_recs = context.result.result_cnt; if( osm_log_is_active( &p_osmt->log, OSM_LOG_VERBOSE ) ) - { - osm_log( &p_osmt->log, OSM_LOG_VERBOSE, - "osmtest_validate_all_path_recs: " - "Received %u records\n", num_recs ); - } - - /* - * Compare the received records to the database. - */ - osmtest_prepare_db( p_osmt ); - - for( i = 0; i < num_recs; i++ ) - { - p_rec = osmv_get_query_path_rec( context.result.p_result_madw, i ); - - status = osmtest_validate_path_rec( p_osmt, p_rec ); - if( status != IB_SUCCESS ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_all_path_recs: ERR 00100: " - "osmtest_valid_node_rec failed (%s)\n", - ib_get_err_str( status ) ); - goto Exit; - } - } + { + osm_log( &p_osmt->log, OSM_LOG_VERBOSE, + "osmtest_validate_all_guidinfo_recs: " + "Received %zu records\n", num_recs ); + } - status = osmtest_check_missing_paths( p_osmt ); - if( status != IB_SUCCESS ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_all_path_recs: ERR 00101: " - "osmtest_check_missing_paths failed (%s)\n", - ib_get_err_str( status ) ); - goto Exit; - } + /* No validation as yet */ Exit: /* * Return the IB query MAD to the pool as necessary. */ if( context.result.p_result_madw != NULL ) - { - osm_mad_pool_put( &p_osmt->mad_pool, context.result.p_result_madw ); - context.result.p_result_madw = NULL; - } + { + osm_mad_pool_put( &p_osmt->mad_pool, context.result.p_result_madw ); + context.result.p_result_madw = NULL; + } OSM_LOG_EXIT( &p_osmt->log ); return ( status ); } -#endif /********************************************************************** **********************************************************************/ static ib_api_status_t -osmtest_validate_single_path_rec_lid_pair( IN osmtest_t * const p_osmt, - IN path_t * const p_path ) +osmtest_validate_all_path_recs( IN osmtest_t * const p_osmt ) { osmtest_req_context_t context; const ib_path_rec_t *p_rec; - cl_status_t status = IB_SUCCESS; + uint32_t i; + cl_status_t status; size_t num_recs; - OSM_LOG_ENTER( &p_osmt->log, osmtest_validate_single_path_rec_lid_pair ); + OSM_LOG_ENTER( &p_osmt->log, osmtest_validate_all_path_recs ); - cl_memclr( &context, sizeof( context ) ); + memset( &context, 0, sizeof( context ) ); + + /* + * Do a blocking query for all PathRecords in the subnet. + */ + status = osmtest_get_all_recs( p_osmt, IB_MAD_ATTR_PATH_RECORD, + sizeof( *p_rec ), &context ); - status = osmtest_get_path_rec_by_lid_pair( p_osmt, - p_path->rec.slid, - p_path->rec.dlid, - &context); if( status != IB_SUCCESS ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_single_path_rec_lid_pair: ERR 00102: " - "ib_query failed (%s)\n", ib_get_err_str( status ) ); - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_all_path_recs: ERR 009A: " + "osmtest_get_all_recs failed (%s)\n", + ib_get_err_str( status ) ); + goto Exit; + } num_recs = context.result.result_cnt; - if( num_recs != 1 ) + + if( osm_log_is_active( &p_osmt->log, OSM_LOG_VERBOSE ) ) + { + osm_log( &p_osmt->log, OSM_LOG_VERBOSE, + "osmtest_validate_all_path_recs: " + "Received %zu records\n", num_recs ); + } + + /* + * Compare the received records to the database. + */ + osmtest_prepare_db( p_osmt ); + + for( i = 0; i < num_recs; i++ ) + { + p_rec = osmv_get_query_path_rec( context.result.p_result_madw, i ); + + status = osmtest_validate_path_rec( p_osmt, p_rec ); + if( status != IB_SUCCESS ) { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_single_path_rec_lid_pair: ERR 00103: " - "Too many records. Expected 1, received %u\n", num_recs ); - - status = IB_ERROR; + "osmtest_validate_all_path_recs: ERR 0100: " + "osmtest_validate_path_rec failed (%s)\n", + ib_get_err_str( status ) ); + goto Exit; } - else - { - p_rec = osmv_get_query_path_rec( context.result.p_result_madw, 0 ); + } - status = osmtest_validate_path_data( p_osmt, p_path, p_rec ); - if( status != IB_SUCCESS ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_single_path_rec_lid_pair: ERR 00104: " - "osmtest_validate_path_data failed (%s)\n", - ib_get_err_str( status ) ); - } - } + status = osmtest_check_missing_paths( p_osmt ); + if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_all_path_recs: ERR 0101: " + "osmtest_check_missing_paths failed (%s)\n", + ib_get_err_str( status ) ); + goto Exit; + } Exit: /* * Return the IB query MAD to the pool as necessary. */ if( context.result.p_result_madw != NULL ) - { - osm_mad_pool_put( &p_osmt->mad_pool, context.result.p_result_madw ); - context.result.p_result_madw = NULL; - } + { + osm_mad_pool_put( &p_osmt->mad_pool, context.result.p_result_madw ); + context.result.p_result_madw = NULL; + } OSM_LOG_EXIT( &p_osmt->log ); return ( status ); } /********************************************************************** + * Get link record by LID **********************************************************************/ -static ib_api_status_t -osmtest_validate_single_node_rec_lid( IN osmtest_t * const p_osmt, - IN ib_net16_t const lid, - IN node_t * const p_node ) +ib_api_status_t +osmtest_get_link_rec_by_lid( IN osmtest_t * const p_osmt, + IN ib_net16_t const from_lid, + IN ib_net16_t const to_lid, + IN OUT osmtest_req_context_t * const p_context ) { - cl_status_t status = IB_SUCCESS; + ib_api_status_t status = IB_SUCCESS; osmv_user_query_t user; osmv_query_req_t req; - ib_node_record_t record; - - osmtest_req_context_t context; - const ib_node_record_t *p_rec; - int num_recs, i; - - OSM_LOG_ENTER( &p_osmt->log, osmtest_validate_single_node_rec_lid ); + ib_link_record_t record; + ib_mad_t *p_mad; - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_validate_single_node_rec_lid: " - "Getting NodeRecord for node with LID 0x%X\n", - cl_ntoh16( lid ) ); - } + OSM_LOG_ENTER( &p_osmt->log, osmtest_get_link_rec_by_lid ); - cl_memclr( &context, sizeof( context ) ); - cl_memclr( &req, sizeof( req ) ); - cl_memclr( &user, sizeof( user ) ); - cl_memclr( &record, sizeof( record ) ); + if( osm_log_is_active( &p_osmt->log, OSM_LOG_VERBOSE ) ) + { + osm_log( &p_osmt->log, OSM_LOG_VERBOSE, + "osmtest_get_link_rec_by_lid: " + "Getting link record from LID 0x%02X to LID 0x%02X\n", + cl_ntoh16( from_lid ), cl_ntoh16( to_lid ) ); + } - record.lid = lid; + /* + * Do a blocking query for this record in the subnet. + * The result is returned in the result field of the caller's + * context structure. + * + * The query structures are locals. + */ + memset( &req, 0, sizeof( req ) ); + memset( &user, 0, sizeof( user ) ); + memset( &record, 0, sizeof( record ) ); - context.p_osmt = p_osmt; - user.comp_mask = IB_NR_COMPMASK_LID; - user.attr_id = IB_MAD_ATTR_NODE_RECORD; - user.attr_offset = cl_ntoh16( (uint16_t) ( sizeof( record ) >> 3 ) ); + record.from_lid = from_lid; + record.to_lid = to_lid; + p_context->p_osmt = p_osmt; + if (from_lid) + user.comp_mask |= IB_LR_COMPMASK_FROM_LID; + if (to_lid) + user.comp_mask |= IB_LR_COMPMASK_TO_LID; + user.attr_id = IB_MAD_ATTR_LINK_RECORD; + user.attr_offset = cl_ntoh16( ( uint16_t ) ( sizeof( record ) >> 3 ) ); user.p_attr = &record; req.query_type = OSMV_QUERY_USER_DEFINED; req.timeout_ms = p_osmt->opt.transaction_timeout; req.retry_cnt = p_osmt->opt.retry_count; req.flags = OSM_SA_FLAGS_SYNC; - req.query_context = &context; + req.query_context = p_context; req.pfn_query_cb = osmtest_query_res_cb; req.p_query_input = &user; req.sm_key = 0; status = osmv_query_sa( p_osmt->h_bind, &req ); - if( status != IB_SUCCESS ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_single_node_rec_lid: ERR 00105: " - "ib_query failed (%s)\n", ib_get_err_str( status ) ); - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_link_rec_by_lid: ERR 007A: " + "ib_query failed (%s)\n", ib_get_err_str( status ) ); + goto Exit; + } - status = context.result.status; + status = p_context->result.status; if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_link_rec_by_lid: ERR 007B: " + "ib_query failed (%s)\n", ib_get_err_str( status ) ); + if( status == IB_REMOTE_ERROR ) { + p_mad = osm_madw_get_mad_ptr( p_context->result.p_result_madw ); osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_single_node_rec_lid: ERR 00106: " - "ib_query failed (%s)\n", ib_get_err_str( status ) ); - - if( status == IB_REMOTE_ERROR ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_single_node_rec_lid: " - "Remote error = %s\n", - ib_get_mad_status_str( osm_madw_get_mad_ptr - ( context.result. - p_result_madw ) ) ); - } - goto Exit; - } - - num_recs = context.result.result_cnt; - osm_log( &p_osmt->log, OSM_LOG_VERBOSE, - "osmtest_validate_single_node_rec_lid: " - "Received %d nodes\n", num_recs); - - for( i = 0; i < num_recs; i++ ) - { - p_rec = osmv_get_query_node_rec( context.result.p_result_madw, i ); + "osmtest_get_link_rec_by_lid: " + "Remote error = %s\n", + ib_get_mad_status_str( p_mad )); - status = osmtest_validate_node_rec( p_osmt, p_rec ); - if( status != IB_SUCCESS ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_single_node_rec_lid: ERR 00107: " - "osmtest_validate_node_data failed (%s)\n", - ib_get_err_str( status ) ); - } + status = (ib_net16_t) (p_mad->status & IB_SMP_STATUS_MASK ); } + goto Exit; + } Exit: - /* - * Return the IB query MAD to the pool as necessary. - */ - if( context.result.p_result_madw != NULL ) - { - osm_mad_pool_put( &p_osmt->mad_pool, context.result.p_result_madw ); - context.result.p_result_madw = NULL; - } - OSM_LOG_EXIT( &p_osmt->log ); return ( status ); } /********************************************************************** + * Get GUIDInfo record by LID **********************************************************************/ -static ib_api_status_t -osmtest_validate_single_port_rec_lid( IN osmtest_t * const p_osmt, - IN port_t * const p_port ) -{ - osmtest_req_context_t context; +ib_api_status_t +osmtest_get_guidinfo_rec_by_lid( IN osmtest_t * const p_osmt, + IN ib_net16_t const lid, + IN OUT osmtest_req_context_t * const p_context ) +{ + ib_api_status_t status = IB_SUCCESS; + osmv_user_query_t user; + osmv_query_req_t req; + ib_guidinfo_record_t record; + ib_mad_t *p_mad; - const ib_portinfo_record_t *p_rec; - cl_status_t status = IB_SUCCESS; + OSM_LOG_ENTER( &p_osmt->log, osmtest_get_guidinfo_rec_by_lid ); - OSM_LOG_ENTER( &p_osmt->log, osmtest_validate_single_port_rec_lid ); + if( osm_log_is_active( &p_osmt->log, OSM_LOG_VERBOSE ) ) + { + osm_log( &p_osmt->log, OSM_LOG_VERBOSE, + "osmtest_get_guidinfo_rec_by_lid: " + "Getting GUIDInfo record for LID 0x%02X\n", + cl_ntoh16( lid ) ); + } - cl_memclr( &context, sizeof( context ) ); + /* + * Do a blocking query for this record in the subnet. + * The result is returned in the result field of the caller's + * context structure. + * + * The query structures are locals. + */ + memset( &req, 0, sizeof( req ) ); + memset( &user, 0, sizeof( user ) ); + memset( &record, 0, sizeof( record ) ); - context.p_osmt = p_osmt; - osmtest_get_port_rec_by_num( p_osmt, - p_port->rec.lid, - p_port->rec.port_num, - &context); - if( status != IB_SUCCESS ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_single_port_rec_lid: ERR 00108: " - "ib_query failed (%s)\n", ib_get_err_str( status ) ); + record.lid = lid; + p_context->p_osmt = p_osmt; + user.comp_mask = IB_GIR_COMPMASK_LID; + user.attr_id = IB_MAD_ATTR_GUIDINFO_RECORD; + user.attr_offset = cl_ntoh16( ( uint16_t ) ( sizeof( record ) >> 3 ) ); + user.p_attr = &record; - goto Exit; + req.query_type = OSMV_QUERY_USER_DEFINED; + req.timeout_ms = p_osmt->opt.transaction_timeout; + req.retry_cnt = p_osmt->opt.retry_count; + + req.flags = OSM_SA_FLAGS_SYNC; + req.query_context = p_context; + req.pfn_query_cb = osmtest_query_res_cb; + req.p_query_input = &user; + req.sm_key = 0; + + status = osmv_query_sa( p_osmt->h_bind, &req ); + if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_guidinfo_rec_by_lid: ERR 007C: " + "ib_query failed (%s)\n", ib_get_err_str( status ) ); + goto Exit; + } + + status = p_context->result.status; + + if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_guidinfo_rec_by_lid: ERR 007D: " + "ib_query failed (%s)\n", ib_get_err_str( status ) ); + if( status == IB_REMOTE_ERROR ) + { + p_mad = osm_madw_get_mad_ptr( p_context->result.p_result_madw ); + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_guidinfo_rec_by_lid: " + "Remote error = %s\n", + ib_get_mad_status_str( p_mad )); + + status = (ib_net16_t) (p_mad->status & IB_SMP_STATUS_MASK ); } + goto Exit; + } - /* we should have got exactly one port */ - p_rec = osmv_get_query_portinfo_rec( context.result.p_result_madw, 0); - status = osmtest_validate_port_rec( p_osmt, p_rec ); + Exit: + OSM_LOG_EXIT( &p_osmt->log ); + return ( status ); +} + +/********************************************************************** + * Get PKeyTable record by LID + **********************************************************************/ +ib_api_status_t +osmtest_get_pkeytbl_rec_by_lid( IN osmtest_t * const p_osmt, + IN ib_net16_t const lid, + IN ib_net64_t const sm_key, + IN OUT osmtest_req_context_t * const p_context ) +{ + ib_api_status_t status = IB_SUCCESS; + osmv_user_query_t user; + osmv_query_req_t req; + ib_pkey_table_record_t record; + ib_mad_t *p_mad; + + OSM_LOG_ENTER( &p_osmt->log, osmtest_get_pkeytbl_rec_by_lid ); + + if( osm_log_is_active( &p_osmt->log, OSM_LOG_VERBOSE ) ) + { + osm_log( &p_osmt->log, OSM_LOG_VERBOSE, + "osmtest_get_pkeytbl_rec_by_lid: " + "Getting PKeyTable record for LID 0x%02X\n", + cl_ntoh16( lid ) ); + } + + /* + * Do a blocking query for this record in the subnet. + * The result is returned in the result field of the caller's + * context structure. + * + * The query structures are locals. + */ + memset( &req, 0, sizeof( req ) ); + memset( &user, 0, sizeof( user ) ); + memset( &record, 0, sizeof( record ) ); + + record.lid = lid; + p_context->p_osmt = p_osmt; + user.comp_mask = IB_PKEY_COMPMASK_LID; + user.attr_id = IB_MAD_ATTR_PKEY_TBL_RECORD; + user.attr_offset = cl_ntoh16( ( uint16_t ) ( sizeof( record ) >> 3 ) ); + user.p_attr = &record; + + req.query_type = OSMV_QUERY_USER_DEFINED; + req.timeout_ms = p_osmt->opt.transaction_timeout; + req.retry_cnt = p_osmt->opt.retry_count; + + req.flags = OSM_SA_FLAGS_SYNC; + req.query_context = p_context; + req.pfn_query_cb = osmtest_query_res_cb; + req.p_query_input = &user; + req.sm_key = sm_key; + + status = osmv_query_sa( p_osmt->h_bind, &req ); + if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_pkeytbl_rec_by_lid: ERR 007E: " + "ib_query failed (%s)\n", ib_get_err_str( status ) ); + goto Exit; + } + + status = p_context->result.status; + + if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_pkeytbl_rec_by_lid: ERR 007F: " + "ib_query failed (%s)\n", ib_get_err_str( status ) ); + if( status == IB_REMOTE_ERROR ) + { + p_mad = osm_madw_get_mad_ptr( p_context->result.p_result_madw ); + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_pkeytbl_rec_by_lid: " + "Remote error = %s\n", + ib_get_mad_status_str( p_mad )); + + status = (ib_net16_t) (p_mad->status & IB_SMP_STATUS_MASK ); + } + goto Exit; + } + + Exit: + OSM_LOG_EXIT( &p_osmt->log ); + return ( status ); +} + +/********************************************************************** + * Get LFT record by LID + **********************************************************************/ +ib_api_status_t +osmtest_get_lft_rec_by_lid( IN osmtest_t * const p_osmt, + IN ib_net16_t const lid, + IN OUT osmtest_req_context_t * const p_context ) +{ + ib_api_status_t status = IB_SUCCESS; + osmv_user_query_t user; + osmv_query_req_t req; + ib_lft_record_t record; + ib_mad_t *p_mad; + + OSM_LOG_ENTER( &p_osmt->log, osmtest_get_lft_rec_by_lid ); + + if( osm_log_is_active( &p_osmt->log, OSM_LOG_VERBOSE ) ) + { + osm_log( &p_osmt->log, OSM_LOG_VERBOSE, + "osmtest_get_lft_rec_by_lid: " + "Getting LFT record for LID 0x%02X\n", + cl_ntoh16( lid ) ); + } + + /* + * Do a blocking query for this record in the subnet. + * The result is returned in the result field of the caller's + * context structure. + * + * The query structures are locals. + */ + memset( &req, 0, sizeof( req ) ); + memset( &user, 0, sizeof( user ) ); + memset( &record, 0, sizeof( record ) ); + + record.lid = lid; + p_context->p_osmt = p_osmt; + user.comp_mask = IB_LFTR_COMPMASK_LID; + user.attr_id = IB_MAD_ATTR_LFT_RECORD; + user.attr_offset = cl_ntoh16( ( uint16_t ) ( sizeof( record ) >> 3 ) ); + user.p_attr = &record; + + req.query_type = OSMV_QUERY_USER_DEFINED; + req.timeout_ms = p_osmt->opt.transaction_timeout; + req.retry_cnt = p_osmt->opt.retry_count; + + req.flags = OSM_SA_FLAGS_SYNC; + req.query_context = p_context; + req.pfn_query_cb = osmtest_query_res_cb; + req.p_query_input = &user; + req.sm_key = 0; + + status = osmv_query_sa( p_osmt->h_bind, &req ); + if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_lft_rec_by_lid: ERR 008A: " + "ib_query failed (%s)\n", ib_get_err_str( status ) ); + goto Exit; + } + + status = p_context->result.status; + + if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_lft_rec_by_lid: ERR 008B: " + "ib_query failed (%s)\n", ib_get_err_str( status ) ); + if( status == IB_REMOTE_ERROR ) + { + p_mad = osm_madw_get_mad_ptr( p_context->result.p_result_madw ); + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_lft_rec_by_lid: " + "Remote error = %s\n", + ib_get_mad_status_str( p_mad )); + + status = (ib_net16_t) (p_mad->status & IB_SMP_STATUS_MASK ); + } + goto Exit; + } + + Exit: + OSM_LOG_EXIT( &p_osmt->log ); + return ( status ); +} + +/********************************************************************** + **********************************************************************/ +ib_api_status_t +osmtest_sminfo_record_request( + IN osmtest_t * const p_osmt, + IN OUT osmtest_req_context_t * const p_context ) +{ + ib_api_status_t status = IB_SUCCESS; + osmv_user_query_t user; + osmv_query_req_t req; + ib_sminfo_record_t record; + ib_mad_t *p_mad; + + OSM_LOG_ENTER( &p_osmt->log, osmtest_sminfo_record_request ); + + /* + * Do a blocking query for these records in the subnet. + * The result is returned in the result field of the caller's + * context structure. + * + * The query structures are locals. + */ + memset( &req, 0, sizeof( req ) ); + memset( &user, 0, sizeof( user ) ); + memset( &record, 0, sizeof( record ) ); + + p_context->p_osmt = p_osmt; + user.attr_id = IB_MAD_ATTR_SMINFO_RECORD; + user.attr_offset = cl_ntoh16( ( uint16_t ) ( sizeof( record ) >> 3 ) ); + user.p_attr = &record; + + req.query_type = OSMV_QUERY_USER_DEFINED; + req.timeout_ms = p_osmt->opt.transaction_timeout; + req.retry_cnt = p_osmt->opt.retry_count; + + req.flags = OSM_SA_FLAGS_SYNC; + req.query_context = p_context; + req.pfn_query_cb = osmtest_query_res_cb; + req.p_query_input = &user; + req.sm_key = 0; + + status = osmv_query_sa( p_osmt->h_bind, &req ); + if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_sminfo_record_request: ERR 008C: " + "ib_query failed (%s)\n", ib_get_err_str( status ) ); + goto Exit; + } + + status = p_context->result.status; + + if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_sminfo_record_request: ERR 008D: " + "ib_query failed (%s)\n", ib_get_err_str( status ) ); + if( status == IB_REMOTE_ERROR ) + { + p_mad = osm_madw_get_mad_ptr( p_context->result.p_result_madw ); + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_sminfo_record_request: " + "Remote error = %s\n", + ib_get_mad_status_str( p_mad )); + + status = (ib_net16_t) (p_mad->status & IB_SMP_STATUS_MASK ); + } + goto Exit; + } + + Exit: + OSM_LOG_EXIT( &p_osmt->log ); + return ( status ); +} +#endif + +/********************************************************************** + **********************************************************************/ +static ib_api_status_t +osmtest_validate_single_path_rec_lid_pair( IN osmtest_t * const p_osmt, + IN path_t * const p_path ) +{ + osmtest_req_context_t context; + const ib_path_rec_t *p_rec; + cl_status_t status = IB_SUCCESS; + size_t num_recs; + + OSM_LOG_ENTER( &p_osmt->log, osmtest_validate_single_path_rec_lid_pair ); + + memset( &context, 0, sizeof( context ) ); + + status = osmtest_get_path_rec_by_lid_pair( p_osmt, + p_path->rec.slid, + p_path->rec.dlid, + &context ); if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_single_path_rec_lid_pair: ERR 0102: " + "ib_query failed (%s)\n", ib_get_err_str( status ) ); + goto Exit; + } + + num_recs = context.result.result_cnt; + if( num_recs != 1 ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_single_path_rec_lid_pair: ERR 0103: " + "Too many records. Expected 1, received %zu\n", num_recs ); + + status = IB_ERROR; + } + else + { + p_rec = osmv_get_query_path_rec( context.result.p_result_madw, 0 ); + + status = osmtest_validate_path_data( p_osmt, p_path, p_rec ); + if( status != IB_SUCCESS ) { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_single_port_rec_lid: ERR 00109: " - "osmtest_validate_port_data failed (%s)\n", + "osmtest_validate_single_path_rec_lid_pair: ERR 0104: " + "osmtest_validate_path_data failed (%s)\n", ib_get_err_str( status ) ); } + } Exit: /* * Return the IB query MAD to the pool as necessary. */ if( context.result.p_result_madw != NULL ) + { + osm_mad_pool_put( &p_osmt->mad_pool, context.result.p_result_madw ); + context.result.p_result_madw = NULL; + } + + OSM_LOG_EXIT( &p_osmt->log ); + return ( status ); +} + +/********************************************************************** + **********************************************************************/ +static ib_api_status_t +osmtest_validate_single_node_rec_lid( IN osmtest_t * const p_osmt, + IN ib_net16_t const lid, + IN node_t * const p_node ) +{ + cl_status_t status = IB_SUCCESS; + osmv_user_query_t user; + osmv_query_req_t req; + ib_node_record_t record; + + osmtest_req_context_t context; + const ib_node_record_t *p_rec; + int num_recs, i; + + OSM_LOG_ENTER( &p_osmt->log, osmtest_validate_single_node_rec_lid ); + + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) + { + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_validate_single_node_rec_lid: " + "Getting NodeRecord for node with LID 0x%X\n", + cl_ntoh16( lid ) ); + } + + memset( &context, 0, sizeof( context ) ); + memset( &req, 0, sizeof( req ) ); + memset( &user, 0, sizeof( user ) ); + memset( &record, 0, sizeof( record ) ); + + record.lid = lid; + + context.p_osmt = p_osmt; + user.comp_mask = IB_NR_COMPMASK_LID; + user.attr_id = IB_MAD_ATTR_NODE_RECORD; + user.attr_offset = cl_ntoh16( (uint16_t) ( sizeof( record ) >> 3 ) ); + user.p_attr = &record; + + req.query_type = OSMV_QUERY_USER_DEFINED; + req.timeout_ms = p_osmt->opt.transaction_timeout; + req.retry_cnt = p_osmt->opt.retry_count; + req.flags = OSM_SA_FLAGS_SYNC; + req.query_context = &context; + req.pfn_query_cb = osmtest_query_res_cb; + req.p_query_input = &user; + req.sm_key = 0; + + status = osmv_query_sa( p_osmt->h_bind, &req ); + + if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_single_node_rec_lid: ERR 0105: " + "ib_query failed (%s)\n", ib_get_err_str( status ) ); + goto Exit; + } + + status = context.result.status; + + if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_single_node_rec_lid: ERR 0106: " + "ib_query failed (%s)\n", ib_get_err_str( status ) ); + + if( status == IB_REMOTE_ERROR ) { - osm_mad_pool_put( &p_osmt->mad_pool, context.result.p_result_madw ); - context.result.p_result_madw = NULL; + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_single_node_rec_lid: " + "Remote error = %s\n", + ib_get_mad_status_str( osm_madw_get_mad_ptr + ( context.result.p_result_madw ) ) ); + } + goto Exit; + } + + num_recs = context.result.result_cnt; + osm_log( &p_osmt->log, OSM_LOG_VERBOSE, + "osmtest_validate_single_node_rec_lid: " + "Received %d nodes\n", num_recs); + + for( i = 0; i < num_recs; i++ ) + { + p_rec = osmv_get_query_node_rec( context.result.p_result_madw, i ); + + status = osmtest_validate_node_rec( p_osmt, p_rec ); + if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_single_node_rec_lid: ERR 0107: " + "osmtest_validate_node_data failed (%s)\n", + ib_get_err_str( status ) ); + goto Exit; } + } + + Exit: + /* + * Return the IB query MAD to the pool as necessary. + */ + if( context.result.p_result_madw != NULL ) + { + osm_mad_pool_put( &p_osmt->mad_pool, context.result.p_result_madw ); + context.result.p_result_madw = NULL; + } + + OSM_LOG_EXIT( &p_osmt->log ); + return ( status ); +} + +/********************************************************************** + **********************************************************************/ +static ib_api_status_t +osmtest_validate_single_port_rec_lid( IN osmtest_t * const p_osmt, + IN port_t * const p_port ) +{ + osmtest_req_context_t context; + + const ib_portinfo_record_t *p_rec; + cl_status_t status = IB_SUCCESS; + + OSM_LOG_ENTER( &p_osmt->log, osmtest_validate_single_port_rec_lid ); + + memset( &context, 0, sizeof( context ) ); + + context.p_osmt = p_osmt; + osmtest_get_port_rec_by_num( p_osmt, + p_port->rec.lid, + p_port->rec.port_num, + &context); + if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_single_port_rec_lid: ERR 0108: " + "ib_query failed (%s)\n", ib_get_err_str( status ) ); + + goto Exit; + } + + /* we should have got exactly one port */ + p_rec = osmv_get_query_portinfo_rec( context.result.p_result_madw, 0); + status = osmtest_validate_port_rec( p_osmt, p_rec ); + if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_single_port_rec_lid: ERR 0109: " + "osmtest_validate_port_data failed (%s)\n", + ib_get_err_str( status ) ); + } + + Exit: + /* + * Return the IB query MAD to the pool as necessary. + */ + if( context.result.p_result_madw != NULL ) + { + osm_mad_pool_put( &p_osmt->mad_pool, context.result.p_result_madw ); + context.result.p_result_madw = NULL; + } OSM_LOG_EXIT( &p_osmt->log ); return ( status ); @@ -4315,20 +5064,22 @@ osmtest_validate_single_path_rec_guid_pair( IN osmtest_t * const p_osmt, size_t num_recs; osmv_query_req_t req; uint32_t i; + boolean_t got_error = FALSE; OSM_LOG_ENTER( &p_osmt->log, osmtest_validate_single_path_rec_guid_pair ); - cl_memclr( &context, sizeof( context ) ); + memset( &req, 0, sizeof( req ) ); + memset( &context, 0, sizeof( context ) ); if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_single_path_rec_guid_pair: " - "\n\t\t\t\tChecking src 0x%016" PRIx64 - " to dest 0x%016" PRIx64 "\n", - cl_ntoh64( p_pair->src_guid ), - cl_ntoh64( p_pair->dest_guid ) ); - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_single_path_rec_guid_pair: " + "\n\t\t\t\tChecking src 0x%016" PRIx64 + " to dest 0x%016" PRIx64 "\n", + cl_ntoh64( p_pair->src_guid ), + cl_ntoh64( p_pair->dest_guid ) ); + } context.p_osmt = p_osmt; @@ -4344,90 +5095,95 @@ osmtest_validate_single_path_rec_guid_pair( IN osmtest_t * const p_osmt, status = osmv_query_sa( p_osmt->h_bind, &req ); if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_single_path_rec_guid_pair: ERR 0110: " + "ib_query failed (%s)\n", ib_get_err_str( status ) ); + goto Exit; + } + + status = context.result.status; + + if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_single_path_rec_guid_pair: ERR 0111: " + "ib_query failed (%s)\n", ib_get_err_str( status ) ); + + if( status == IB_REMOTE_ERROR ) { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_single_path_rec_guid_pair: ERR 00110: " - "ib_query failed (%s)\n", ib_get_err_str( status ) ); - goto Exit; + "osmtest_validate_single_path_rec_guid_pair: " + "Remote error = %s\n", + ib_get_mad_status_str( osm_madw_get_mad_ptr + ( context.result.p_result_madw ) ) ); } + goto Exit; + } - status = context.result.status; + num_recs = context.result.result_cnt; + osm_log( &p_osmt->log, OSM_LOG_VERBOSE, + "osmtest_validate_single_path_rec_guid_pair: %zu records\n", + num_recs); - if( status != IB_SUCCESS ) + for( i = 0; i < num_recs; i++ ) + { + p_rec = osmv_get_query_path_rec( context.result.p_result_madw, i ); + + /* + * Make sure the GUID values are correct + */ + if( p_rec->dgid.unicast.interface_id != p_pair->dest_guid ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_single_path_rec_guid_pair: ERR 0112: " + "Destination GUID mismatch\n" + "\t\t\t\texpected 0x%016" PRIx64 + ", received 0x%016" PRIx64 "\n", + cl_ntoh64( p_pair->dest_guid ), + cl_ntoh64( p_rec->dgid.unicast.interface_id ) ); + got_error = TRUE; + } + + if( p_rec->sgid.unicast.interface_id != p_pair->src_guid ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_single_path_rec_guid_pair: ERR 0113: " + "Source GUID mismatch\n" + "\t\t\t\texpected 0x%016" PRIx64 + ", received 0x%016" PRIx64 ".\n", + cl_ntoh64( p_pair->src_guid ), + cl_ntoh64( p_rec->sgid.unicast.interface_id ) ); + got_error = TRUE; + } + + status = osmtest_validate_path_rec( p_osmt, p_rec ); + if( status != IB_SUCCESS ) { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_single_path_rec_guid_pair: ERR 00111: " - "ib_query failed (%s)\n", ib_get_err_str( status ) ); - - if( status == IB_REMOTE_ERROR ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_single_path_rec_guid_pair: " - "Remote error = %s\n", - ib_get_mad_status_str( osm_madw_get_mad_ptr - ( context.result. - p_result_madw ) ) ); - } - goto Exit; + "osmtest_validate_single_path_rec_guid_pair: ERR 0114: " + "osmtest_validate_path_rec failed (%s)\n", + ib_get_err_str( status ) ); + got_error = TRUE; } - - num_recs = context.result.result_cnt; - osm_log( &p_osmt->log, OSM_LOG_VERBOSE, - "osmtest_validate_single_path_rec_guid_pair: %u records\n", - num_recs); - - for( i = 0; i < num_recs; i++ ) + if( got_error || (status != IB_SUCCESS) ) { - p_rec = osmv_get_query_path_rec( context.result.p_result_madw, i ); - - /* - * Make sure the GUID values are correct - */ - if( p_rec->dgid.unicast.interface_id != p_pair->dest_guid ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_single_path_rec_guid_pair: ERR 00112: " - "Destination GUID mismatch\n" - "\t\t\t\texpected 0x%016" PRIx64 - ", received 0x%016" PRIx64 "\n", - cl_ntoh64( p_pair->dest_guid ), - cl_ntoh64( p_rec->dgid.unicast.interface_id ) ); - } - - if( p_rec->sgid.unicast.interface_id != p_pair->src_guid ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_single_path_rec_guid_pair: ERR 00113: " - "Source GUID mismatch\n" - "\t\t\t\texpected 0x%016" PRIx64 - ", received 0x%016" PRIx64 ".\n", - cl_ntoh64( p_pair->src_guid ), - cl_ntoh64( p_rec->sgid.unicast.interface_id ) ); - } - - status = osmtest_validate_path_rec( p_osmt, p_rec ); - if( status != IB_SUCCESS ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_single_path_rec_guid_pair: ERR 00114: " - "osmtest_validate_path_data failed (%s)\n", - ib_get_err_str( status ) ); - } - if (status != IB_SUCCESS ) - { - osm_dump_path_record( &p_osmt->log, p_rec, OSM_LOG_VERBOSE ); - } + osm_dump_path_record( &p_osmt->log, p_rec, OSM_LOG_VERBOSE ); + if( status == IB_SUCCESS ) + status = IB_ERROR; + goto Exit; } + } Exit: /* * Return the IB query MAD to the pool as necessary. */ if( context.result.p_result_madw != NULL ) - { - osm_mad_pool_put( &p_osmt->mad_pool, context.result.p_result_madw ); - context.result.p_result_madw = NULL; - } + { + osm_mad_pool_put( &p_osmt->mad_pool, context.result.p_result_madw ); + context.result.p_result_madw = NULL; + } OSM_LOG_EXIT( &p_osmt->log ); return ( status ); @@ -4449,11 +5205,11 @@ osmtest_validate_single_path_recs( IN osmtest_t * const p_osmt ) OSM_LOG_ENTER( &p_osmt->log, osmtest_validate_single_path_recs ); if( osm_log_is_active( &p_osmt->log, OSM_LOG_VERBOSE ) ) - { - osm_log( &p_osmt->log, OSM_LOG_VERBOSE, - "osmtest_validate_single_path_recs: " - "Validating individual path record queries\n" ); - } + { + osm_log( &p_osmt->log, OSM_LOG_VERBOSE, + "osmtest_validate_single_path_recs: " + "Validating individual path record queries\n" ); + } p_path_tbl = &p_osmt->exp_subn.path_tbl; osmtest_prepare_db( p_osmt ); @@ -4465,30 +5221,30 @@ osmtest_validate_single_path_recs( IN osmtest_t * const p_osmt ) cnt = 0; p_path = ( path_t * ) cl_qmap_head( p_path_tbl ); while( p_path != ( path_t * ) cl_qmap_end( p_path_tbl ) ) - { - status = osmtest_validate_single_path_rec_lid_pair( p_osmt, p_path ); - if( status != IB_SUCCESS ) - goto Exit; - cnt++; - p_path = ( path_t * ) cl_qmap_next( &p_path->map_item ); - } + { + status = osmtest_validate_single_path_rec_lid_pair( p_osmt, p_path ); + if( status != IB_SUCCESS ) + goto Exit; + cnt++; + p_path = ( path_t * ) cl_qmap_next( &p_path->map_item ); + } if( osm_log_is_active( &p_osmt->log, OSM_LOG_VERBOSE ) ) - { - osm_log( &p_osmt->log, OSM_LOG_VERBOSE, - "osmtest_validate_single_path_recs: " - "Total of %u path records validated using LID based query\n", cnt ); - } + { + osm_log( &p_osmt->log, OSM_LOG_VERBOSE, + "osmtest_validate_single_path_recs: " + "Total of %u path records validated using LID based query\n", cnt ); + } status = osmtest_check_missing_paths( p_osmt ); if( status != IB_SUCCESS ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_single_path_recs: ERR 00115: " - "osmtest_check_missing_paths failed (%s)\n", - ib_get_err_str( status ) ); - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_single_path_recs: ERR 0115: " + "osmtest_check_missing_paths failed (%s)\n", + ib_get_err_str( status ) ); + goto Exit; + } /* * Do the whole thing again with port GUID pairs. @@ -4499,34 +5255,33 @@ osmtest_validate_single_path_recs( IN osmtest_t * const p_osmt ) cnt = 0; p_path = ( path_t * ) cl_qmap_head( p_path_tbl ); while( p_path != ( path_t * ) cl_qmap_end( p_path_tbl ) ) - { - guid_pair.src_guid = p_path->rec.sgid.unicast.interface_id; - guid_pair.dest_guid = p_path->rec.dgid.unicast.interface_id; - status = - osmtest_validate_single_path_rec_guid_pair( p_osmt, - &guid_pair ); - if( status != IB_SUCCESS ) - goto Exit; - cnt++; - p_path = ( path_t * ) cl_qmap_next( &p_path->map_item ); - } + { + guid_pair.src_guid = p_path->rec.sgid.unicast.interface_id; + guid_pair.dest_guid = p_path->rec.dgid.unicast.interface_id; + status = osmtest_validate_single_path_rec_guid_pair( p_osmt, + &guid_pair ); + if( status != IB_SUCCESS ) + goto Exit; + cnt++; + p_path = ( path_t * ) cl_qmap_next( &p_path->map_item ); + } if( osm_log_is_active( &p_osmt->log, OSM_LOG_VERBOSE ) ) - { - osm_log( &p_osmt->log, OSM_LOG_VERBOSE, - "osmtest_validate_single_path_recs: " - "Total of %u path records validated using GUID based query\n", cnt ); - } + { + osm_log( &p_osmt->log, OSM_LOG_VERBOSE, + "osmtest_validate_single_path_recs: " + "Total of %u path records validated using GUID based query\n", cnt ); + } status = osmtest_check_missing_paths( p_osmt ); if( status != IB_SUCCESS ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_single_path_recs: ERR 00116: " - "osmtest_check_missing_paths failed (%s)\n", - ib_get_err_str( status ) ); - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_single_path_recs: ERR 0116: " + "osmtest_check_missing_paths failed (%s)\n", + ib_get_err_str( status ) ); + goto Exit; + } Exit: OSM_LOG_EXIT( &p_osmt->log ); @@ -4550,11 +5305,11 @@ osmtest_validate_single_node_recs( IN osmtest_t * const p_osmt ) osmtest_prepare_db( p_osmt ); if( osm_log_is_active( &p_osmt->log, OSM_LOG_VERBOSE ) ) - { - osm_log( &p_osmt->log, OSM_LOG_VERBOSE, - "osmtest_validate_single_node_recs: " - "Validating individual node record queries\n" ); - } + { + osm_log( &p_osmt->log, OSM_LOG_VERBOSE, + "osmtest_validate_single_node_recs: " + "Validating individual node record queries\n" ); + } /* * Walk the list of all node records, and ask for each one @@ -4562,30 +5317,38 @@ osmtest_validate_single_node_recs( IN osmtest_t * const p_osmt ) */ p_node = ( node_t * ) cl_qmap_head( p_node_lid_tbl ); while( p_node != ( node_t * ) cl_qmap_end( p_node_lid_tbl ) ) + { + status = osmtest_validate_single_node_rec_lid( p_osmt, + (ib_net16_t) cl_qmap_key ((cl_map_item_t*)p_node), + p_node ); + if( status != IB_SUCCESS ) { - status = osmtest_validate_single_node_rec_lid( p_osmt, - (ib_net16_t) cl_qmap_key ((cl_map_item_t*)p_node), - p_node ); - cnt++; - p_node = ( node_t * ) cl_qmap_next( &p_node->map_item ); + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_single_node_recs: ERR 011A: " + "osmtest_validate_single_node_rec_lid (%s)\n", + ib_get_err_str( status ) ); + goto Exit; } + cnt++; + p_node = ( node_t * ) cl_qmap_next( &p_node->map_item ); + } if( osm_log_is_active( &p_osmt->log, OSM_LOG_VERBOSE ) ) - { - osm_log( &p_osmt->log, OSM_LOG_VERBOSE, - "osmtest_validate_single_node_recs: " - "Total of %u node records validated\n", cnt ); - } + { + osm_log( &p_osmt->log, OSM_LOG_VERBOSE, + "osmtest_validate_single_node_recs: " + "Total of %u node records validated\n", cnt ); + } status = osmtest_check_missing_nodes( p_osmt ); if( status != IB_SUCCESS ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_single_node_recs: ERR 00117: " - "osmtest_check_missing_nodes (%s)\n", - ib_get_err_str( status ) ); - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_single_node_recs: ERR 0117: " + "osmtest_check_missing_nodes (%s)\n", + ib_get_err_str( status ) ); + goto Exit; + } Exit: OSM_LOG_EXIT( &p_osmt->log ); @@ -4609,11 +5372,11 @@ osmtest_validate_single_port_recs( IN osmtest_t * const p_osmt ) osmtest_prepare_db( p_osmt ); if( osm_log_is_active( &p_osmt->log, OSM_LOG_VERBOSE ) ) - { - osm_log( &p_osmt->log, OSM_LOG_VERBOSE, - "osmtest_validate_single_port_recs: " - "Validating individual port record queries\n" ); - } + { + osm_log( &p_osmt->log, OSM_LOG_VERBOSE, + "osmtest_validate_single_port_recs: " + "Validating individual port record queries\n" ); + } /* * Walk the list of all port records, and ask for each one @@ -4621,28 +5384,36 @@ osmtest_validate_single_port_recs( IN osmtest_t * const p_osmt ) */ p_port = ( port_t * ) cl_qmap_head( p_port_key_tbl ); while( p_port != ( port_t * ) cl_qmap_end( p_port_key_tbl ) ) + { + status = osmtest_validate_single_port_rec_lid( p_osmt, p_port ); + if( status != IB_SUCCESS ) { - status = osmtest_validate_single_port_rec_lid( p_osmt, p_port ); - cnt++; - p_port = ( port_t * ) cl_qmap_next( &p_port->map_item ); + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_single_port_recs: ERR 011B: " + "osmtest_validate_single_port_rec_lid (%s)\n", + ib_get_err_str( status ) ); + goto Exit; } + cnt++; + p_port = ( port_t * ) cl_qmap_next( &p_port->map_item ); + } if( osm_log_is_active( &p_osmt->log, OSM_LOG_VERBOSE ) ) - { - osm_log( &p_osmt->log, OSM_LOG_VERBOSE, - "osmtest_validate_single_port_recs: " - "Total of %u port records validated\n", cnt ); - } + { + osm_log( &p_osmt->log, OSM_LOG_VERBOSE, + "osmtest_validate_single_port_recs: " + "Total of %u port records validated\n", cnt ); + } status = osmtest_check_missing_ports( p_osmt ); if( status != IB_SUCCESS ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_validate_single_port_recs: ERR 00118: " - "osmtest_check_missing_paths failed (%s)\n", - ib_get_err_str( status ) ); - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_validate_single_port_recs: ERR 0118: " + "osmtest_check_missing_paths failed (%s)\n", + ib_get_err_str( status ) ); + goto Exit; + } Exit: OSM_LOG_EXIT( &p_osmt->log ); @@ -4655,6 +5426,16 @@ static ib_api_status_t osmtest_validate_against_db( IN osmtest_t * const p_osmt ) { ib_api_status_t status = IB_SUCCESS; + ib_gid_t portgid, mgid; +#ifdef VENDOR_RMPP_SUPPORT + ib_net64_t sm_key; + ib_net16_t test_lid; + uint8_t lmc; + osmtest_req_context_t context; +#ifdef DUAL_SIDED_RMPP + osmv_multipath_req_t request; +#endif +#endif OSM_LOG_ENTER( &p_osmt->log, osmtest_validate_against_db ); @@ -4668,13 +5449,345 @@ osmtest_validate_against_db( IN osmtest_t * const p_osmt ) if( status != IB_SUCCESS ) goto Exit; + /* Exercise SA PathRecord multicast destination code */ + memset( &context, 0, sizeof( context ) ); + ib_gid_set_default( &portgid, portguid ); + /* Set IPoIB broadcast MGID */ + mgid.unicast.prefix = CL_HTON64(0xff12401bffff0000ULL); + mgid.unicast.interface_id = CL_HTON64(0x00000000ffffffffULL); + /* Can't check status as don't know whether port is running IPoIB */ + osmtest_get_path_rec_by_gid_pair( p_osmt, portgid, mgid, &context); + +#if defined (VENDOR_RMPP_SUPPORT) && defined (DUAL_SIDED_RMPP) + memset( &context, 0, sizeof( context ) ); + memset( &request, 0, sizeof( request ) ); + request.comp_mask = IB_MPR_COMPMASK_SGIDCOUNT | IB_MPR_COMPMASK_DGIDCOUNT; + request.sgid_count = 1; + request.dgid_count = 1; + ib_gid_set_default( &request.gids[0], portguid ); + ib_gid_set_default( &request.gids[1], portguid ); + status = osmtest_get_multipath_rec( p_osmt, &request, &context ); + if( status != IB_SUCCESS ) + goto Exit; + + memset( &context, 0, sizeof( context ) ); + memset( &request, 0, sizeof( request ) ); + + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_multipath_rec: " EXPECTING_ERRORS_START "\n" ); + status = osmtest_get_multipath_rec( p_osmt, &request, &context ); + if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_multipath_rec: " + "Got error %s\n", ib_get_err_str(status) ); + } + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_multipath_rec: " EXPECTING_ERRORS_END "\n" ); + + if( status == IB_SUCCESS ) + { + status = IB_ERROR; + goto Exit; + } + + memset( &context, 0, sizeof( context ) ); + memset( &request, 0, sizeof( request ) ); + request.comp_mask = IB_MPR_COMPMASK_SGIDCOUNT; + request.sgid_count = 1; + ib_gid_set_default( &request.gids[0], portguid ); + + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_multipath_rec: " EXPECTING_ERRORS_START "\n" ); + status = osmtest_get_multipath_rec( p_osmt, &request, &context ); + if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_multipath_rec: " + "Got error %s\n", ib_get_err_str(status) ); + } + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_multipath_rec: " EXPECTING_ERRORS_END "\n" ); + + if( status == IB_SUCCESS ) + { + status = IB_ERROR; + goto Exit; + } + + memset( &context, 0, sizeof( context ) ); + memset( &request, 0, sizeof( request ) ); + request.comp_mask = IB_MPR_COMPMASK_SGIDCOUNT | IB_MPR_COMPMASK_DGIDCOUNT; + request.sgid_count = 1; + request.dgid_count = 1; + ib_gid_set_default( &request.gids[0], portguid ); + /* Set IPoIB broadcast MGID */ + request.gids[1].unicast.prefix = CL_HTON64(0xff12401bffff0000ULL); + request.gids[1].unicast.interface_id = CL_HTON64(0x00000000ffffffffULL); + + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_multipath_rec: " EXPECTING_ERRORS_START "\n" ); + status = osmtest_get_multipath_rec( p_osmt, &request, &context ); + if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_multipath_rec: " + "Got error %s\n", ib_get_err_str(status) ); + } + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_multipath_rec: " EXPECTING_ERRORS_END "\n" ); + + if( status == IB_SUCCESS ) + { + status = IB_ERROR; + goto Exit; + } + + memset( &context, 0, sizeof( context ) ); + request.comp_mask = IB_MPR_COMPMASK_SGIDCOUNT | IB_MPR_COMPMASK_DGIDCOUNT; + request.sgid_count = 1; + request.dgid_count = 1; + /* Set IPoIB broadcast MGID */ + request.gids[0].unicast.prefix = CL_HTON64(0xff12401bffff0000ULL); + request.gids[0].unicast.interface_id = CL_HTON64(0x00000000ffffffffULL); + ib_gid_set_default( &request.gids[1], portguid ); + + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_multipath_rec: " EXPECTING_ERRORS_START "\n" ); + status = osmtest_get_multipath_rec( p_osmt, &request, &context ); + if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_multipath_rec: " + "Got error %s\n", ib_get_err_str(status) ); + } + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_multipath_rec: " EXPECTING_ERRORS_END "\n" ); + + if( status == IB_SUCCESS ) + { + status = IB_ERROR; + goto Exit; + } + + memset( &context, 0, sizeof( context ) ); + memset( &request, 0, sizeof( request ) ); + request.comp_mask = IB_MPR_COMPMASK_SGIDCOUNT | IB_MPR_COMPMASK_DGIDCOUNT | + IB_MPR_COMPMASK_NUMBPATH; + request.sgid_count = 2; + request.dgid_count = 2; + request.num_path = 2; + ib_gid_set_default( &request.gids[0], portguid ); + ib_gid_set_default( &request.gids[1], portguid ); + ib_gid_set_default( &request.gids[2], portguid ); + ib_gid_set_default( &request.gids[3], portguid ); + status = osmtest_get_multipath_rec( p_osmt, &request, &context ); + if( status != IB_SUCCESS ) + goto Exit; +#endif + #ifdef VENDOR_RMPP_SUPPORT + /* GUIDInfoRecords */ + status = osmtest_validate_all_guidinfo_recs( p_osmt ); + if( status != IB_SUCCESS ) + goto Exit; + + /* If LMC > 0, test non base LID SA PortInfoRecord request */ + status = osmtest_get_local_port_lmc( p_osmt, p_osmt->local_port.lid, &lmc ); + if ( status != IB_SUCCESS ) + goto Exit; + + if (lmc != 0) + { + status = osmtest_get_local_port_lmc( p_osmt, p_osmt->local_port.lid + 1, NULL ); + if ( status != IB_SUCCESS ) + goto Exit; + } + + status = osmtest_get_local_port_lmc( p_osmt, 0xffff, NULL ); + if ( status != IB_SUCCESS ) + goto Exit; + + test_lid = cl_ntoh16( p_osmt->local_port.lid ); + + /* More GUIDInfo Record tests */ + memset( &context, 0, sizeof( context ) ); + status = osmtest_get_guidinfo_rec_by_lid( p_osmt, test_lid, &context ); + if ( status != IB_SUCCESS ) + goto Exit; + + memset( &context, 0, sizeof( context ) ); + status = osmtest_get_guidinfo_rec_by_lid( p_osmt, 0xffff, &context ); + if ( status != IB_SUCCESS ) + goto Exit; + + /* Some PKeyTable Record tests */ + sm_key = OSM_DEFAULT_SM_KEY; + memset( &context, 0, sizeof( context ) ); + status = osmtest_get_pkeytbl_rec_by_lid( p_osmt, test_lid, sm_key, &context ); + if ( status != IB_SUCCESS ) + goto Exit; + + memset( &context, 0, sizeof( context ) ); + + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_multipath_rec: " EXPECTING_ERRORS_START "\n" ); + status = osmtest_get_pkeytbl_rec_by_lid( p_osmt, test_lid, 0, &context ); + if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_multipath_rec: " + "Got error %s\n", ib_get_err_str(status) ); + } + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_multipath_rec: " EXPECTING_ERRORS_END "\n" ); + + if( status == IB_SUCCESS ) + { + status = IB_ERROR; + goto Exit; + } + + memset( &context, 0, sizeof( context ) ); + status = osmtest_get_pkeytbl_rec_by_lid( p_osmt, 0xffff, sm_key, &context ); + if ( status != IB_SUCCESS ) + goto Exit; + + /* LFT Record test */ + memset( &context, 0, sizeof( context ) ); + status = osmtest_get_lft_rec_by_lid( p_osmt, test_lid, &context ); + if ( status != IB_SUCCESS ) + goto Exit; + + /* Some LinkRecord tests */ + /* FromLID */ + memset( &context, 0, sizeof( context ) ); + status = osmtest_get_link_rec_by_lid( p_osmt, test_lid, 0, &context ); + if ( status != IB_SUCCESS ) + goto Exit; + + /* ToLID */ + memset( &context, 0, sizeof( context ) ); + status = osmtest_get_link_rec_by_lid( p_osmt, 0, test_lid, &context ); + if ( status != IB_SUCCESS ) + goto Exit; + + /* FromLID & ToLID */ + memset( &context, 0, sizeof( context ) ); + status = osmtest_get_link_rec_by_lid( p_osmt, test_lid, test_lid, &context ); + if ( status != IB_SUCCESS ) + goto Exit; + + /* NodeRecord test */ + memset( &context, 0, sizeof( context ) ); + status = osmtest_get_node_rec_by_lid( p_osmt, 0xffff , &context ); + if ( status != IB_SUCCESS ) + goto Exit; + + /* SMInfoRecord test */ + memset( &context, 0, sizeof( context ) ); + status = osmtest_sminfo_record_request( p_osmt, &context ); + if ( status != IB_SUCCESS ) + goto Exit; + + if (lmc != 0) + { + test_lid = cl_ntoh16( p_osmt->local_port.lid + 1 ); + + /* Another GUIDInfo Record test */ + memset( &context, 0, sizeof( context ) ); + status = osmtest_get_guidinfo_rec_by_lid( p_osmt, test_lid, &context ); + if ( status != IB_SUCCESS ) + goto Exit; + + /* Another PKeyTable Record test */ + memset( &context, 0, sizeof( context ) ); + status = osmtest_get_pkeytbl_rec_by_lid( p_osmt, test_lid, sm_key, &context ); + if ( status != IB_SUCCESS ) + goto Exit; + + /* Another LFT Record test */ + memset( &context, 0, sizeof( context ) ); + status = osmtest_get_lft_rec_by_lid( p_osmt, test_lid, &context ); + if ( status != IB_SUCCESS ) + goto Exit; + + /* More LinkRecord tests */ + /* FromLID */ + memset( &context, 0, sizeof( context ) ); + status = osmtest_get_link_rec_by_lid( p_osmt, test_lid, 0, &context ); + if ( status != IB_SUCCESS ) + goto Exit; + + /* ToLID */ + memset( &context, 0, sizeof( context ) ); + status = osmtest_get_link_rec_by_lid( p_osmt, 0, test_lid, &context ); + if ( status != IB_SUCCESS ) + goto Exit; + + /* Another NodeRecord test */ + memset( &context, 0, sizeof( context ) ); + status = osmtest_get_node_rec_by_lid( p_osmt, test_lid, &context ); + if ( status != IB_SUCCESS ) + goto Exit; + } + + /* PathRecords */ if (! p_osmt->opt.ignore_path_records) + { + status = osmtest_validate_all_path_recs( p_osmt ); + if( status != IB_SUCCESS ) + goto Exit; + + if (lmc != 0) { - status = osmtest_validate_all_path_recs( p_osmt ); + memset( &context, 0, sizeof( context ) ); + status = osmtest_get_path_rec_by_lid_pair( p_osmt, test_lid, + test_lid, &context ); + if (status != IB_SUCCESS ) + goto Exit; + + memset( &context, 0, sizeof( context ) ); + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_path_rec_by_lid_pair: " EXPECTING_ERRORS_START "\n" ); + status = osmtest_get_path_rec_by_lid_pair( p_osmt, 0xffff, + 0xffff, &context ); + if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_path_rec_by_lid_pair: " + "Got error %s\n", ib_get_err_str(status) ); + } + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_path_rec_by_lid_pair: " EXPECTING_ERRORS_END "\n" ); + + if( status == IB_SUCCESS ) + { + status = IB_ERROR; + goto Exit; + } + + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_path_rec_by_lid_pair: " EXPECTING_ERRORS_START "\n" ); + + status = osmtest_get_path_rec_by_lid_pair( p_osmt, test_lid, + 0xffff, &context ); if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_path_rec_by_lid_pair: " + "Got error %s\n", ib_get_err_str(status) ); + } + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_get_path_rec_by_lid_pair: " EXPECTING_ERRORS_END "\n" ); + + if( status == IB_SUCCESS ) + { + status = IB_ERROR; goto Exit; + } } + } #endif status = osmtest_validate_single_port_recs( p_osmt ); @@ -4682,11 +5795,11 @@ osmtest_validate_against_db( IN osmtest_t * const p_osmt ) goto Exit; if (! p_osmt->opt.ignore_path_records) - { - status = osmtest_validate_single_path_recs( p_osmt ); - if( status != IB_SUCCESS ) - goto Exit; - } + { + status = osmtest_validate_single_path_recs( p_osmt ); + if( status != IB_SUCCESS ) + goto Exit; + } Exit: OSM_LOG_EXIT( &p_osmt->log ); @@ -4724,9 +5837,9 @@ str_skip_white( IN char line[], while( ( ( line[*p_offset] == '\t' ) || ( line[*p_offset] == ' ' ) ) && ( line[*p_offset] != '\n' ) && ( line[*p_offset] != '\0' ) ) - { - ++*p_offset; - } + { + ++*p_offset; + } if( ( line[*p_offset] == '\n' ) || ( line[*p_offset] == '\0' ) ) return ( FALSE ); @@ -4743,9 +5856,9 @@ str_skip_token( IN char line[], { while( ( line[*p_offset] != '\t' ) && ( line[*p_offset] != ' ' ) && ( line[*p_offset] != '\0' ) ) - { - ++*p_offset; - } + { + ++*p_offset; + } } /********************************************************************** @@ -4772,255 +5885,250 @@ osmtest_parse_node( IN osmtest_t * const p_osmt, * Parse the inventory file and create the database. */ while( !done ) + { + if( fgets( line, OSMTEST_MAX_LINE_LEN, fh ) == NULL ) { - if( fgets( line, OSMTEST_MAX_LINE_LEN, fh ) == NULL ) - { - /* - * End of file in the middle of a definition. - */ - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_parse_node: ERR 00119: " - "Unexpected end of file\n" ); - status = IB_ERROR; - goto Exit; - } - - ++*p_line_num; - /* - * Skip whitespace + * End of file in the middle of a definition. */ - offset = 0; - if( !str_skip_white( line, &offset ) ) - continue; /* whole line was whitespace */ + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_parse_node: ERR 0119: " + "Unexpected end of file\n" ); + status = IB_ERROR; + goto Exit; + } + + ++*p_line_num; + + /* + * Skip whitespace + */ + offset = 0; + if( !str_skip_white( line, &offset ) ) + continue; /* whole line was whitespace */ + + p_tok = str_get_token( &line[offset] ); + if( p_tok == NULL ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_parse_node: ERR 0120: " + "Ignoring line %u with unknown token: %s\n", + *p_line_num, &line[offset] ); + continue; + } + + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) + { + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_parse_node: " + "Found '%s' (line %u)\n", p_tok->str, *p_line_num ); + } + + str_skip_token( line, &offset ); - p_tok = str_get_token( &line[offset] ); - if( p_tok == NULL ) + switch ( p_tok->val ) + { + case OSMTEST_TOKEN_COMMENT: + break; + + case OSMTEST_TOKEN_LID: + p_node->comp.lid = 0xFFFF; + p_node->rec.lid = + cl_hton16( ( uint16_t ) strtoul( &line[offset], NULL, 0 ) ); + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_parse_node: ERR 00120: " - "Ignoring line %u with unknown token: %s\n", - *p_line_num, &line[offset] ); - continue; + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_parse_node: " + "lid = 0x%X\n", cl_ntoh16( p_node->rec.lid ) ); } + break; - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) + case OSMTEST_TOKEN_BASE_VERSION: + p_node->comp.node_info.base_version = 0xFF; + p_node->rec.node_info.base_version = + ( uint8_t ) strtoul( &line[offset], NULL, 0 ); + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) { osm_log( &p_osmt->log, OSM_LOG_DEBUG, "osmtest_parse_node: " - "Found '%s' (line %u)\n", p_tok->str, *p_line_num ); + "base_version = 0x%X\n", + p_node->rec.node_info.base_version ); } + break; - str_skip_token( line, &offset ); - - switch ( p_tok->val ) + case OSMTEST_TOKEN_CLASS_VERSION: + p_node->comp.node_info.class_version = 0xFF; + p_node->rec.node_info.class_version = + ( uint8_t ) strtoul( &line[offset], NULL, 0 ); + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) { - case OSMTEST_TOKEN_COMMENT: - break; - - case OSMTEST_TOKEN_LID: - p_node->comp.lid = 0xFFFF; - p_node->rec.lid = - cl_hton16( ( uint16_t ) strtoul( &line[offset], NULL, 0 ) ); - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_parse_node: " - "lid = 0x%X\n", cl_ntoh16( p_node->rec.lid ) ); - } - break; - - case OSMTEST_TOKEN_BASE_VERSION: - p_node->comp.node_info.base_version = 0xFF; - p_node->rec.node_info.base_version = - ( uint8_t ) strtoul( &line[offset], NULL, 0 ); - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_parse_node: " - "base_version = 0x%X\n", - p_node->rec.node_info.base_version ); - } - break; - - case OSMTEST_TOKEN_CLASS_VERSION: - p_node->comp.node_info.class_version = 0xFF; - p_node->rec.node_info.class_version = - ( uint8_t ) strtoul( &line[offset], NULL, 0 ); - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_parse_node: " - "class_version = 0x%X\n", - p_node->rec.node_info.class_version ); - } - break; - - case OSMTEST_TOKEN_NODE_TYPE: - p_node->comp.node_info.node_type = 0xFF; - p_node->rec.node_info.node_type = - ( uint8_t ) strtoul( &line[offset], NULL, 0 ); - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_parse_node: " - "node_type = 0x%X\n", - p_node->rec.node_info.node_type ); - } - break; - - case OSMTEST_TOKEN_NUM_PORTS: - p_node->comp.node_info.num_ports = 0xFF; - p_node->rec.node_info.num_ports = - ( uint8_t ) strtoul( &line[offset], NULL, 0 ); - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_parse_node: " - "num_ports = 0x%X\n", - p_node->rec.node_info.num_ports ); - } - break; - - case OSMTEST_TOKEN_SYS_GUID: - p_node->comp.node_info.sys_guid = 0xFFFFFFFFFFFFFFFFULL; - p_node->rec.node_info.sys_guid = - cl_hton64( strtoull( &line[offset], NULL, 0 ) ); - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_parse_node: " - "sys_guid = 0x%016" PRIx64 "\n", - cl_ntoh64( p_node->rec.node_info.sys_guid ) ); - } - break; - - case OSMTEST_TOKEN_NODE_GUID: - p_node->comp.node_info.node_guid = 0xFFFFFFFFFFFFFFFFULL; - p_node->rec.node_info.node_guid = - cl_hton64( strtoull( &line[offset], NULL, 0 ) ); - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_parse_node: " - "node_guid = 0x%016" PRIx64 "\n", - cl_ntoh64( p_node->rec.node_info.node_guid ) ); - } - break; - - case OSMTEST_TOKEN_PORT_GUID: - p_node->comp.node_info.port_guid = 0xFFFFFFFFFFFFFFFFULL; - p_node->rec.node_info.port_guid = - cl_hton64( strtoull( &line[offset], NULL, 0 ) ); - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_parse_node: " - "port_guid = 0x%016" PRIx64 "\n", - cl_ntoh64( p_node->rec.node_info.port_guid ) ); - } - break; - - case OSMTEST_TOKEN_PARTITION_CAP: - p_node->comp.node_info.partition_cap = 0xFFFF; - p_node->rec.node_info.partition_cap = cl_hton16( ( uint16_t ) - strtoul( &line - [offset], - NULL, - 0 ) ); - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_parse_node: " - "partition_cap = 0x%X\n", - cl_ntoh16( p_node->rec.node_info.partition_cap ) ); - } - break; - - case OSMTEST_TOKEN_DEVICE_ID: - p_node->comp.node_info.device_id = 0xFFFF; - p_node->rec.node_info.device_id = cl_hton16( ( uint16_t ) - strtoul( &line - [offset], - NULL, 0 ) ); - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_parse_node: " - "device_id = 0x%X\n", - cl_ntoh16( p_node->rec.node_info.device_id ) ); - } - break; - - case OSMTEST_TOKEN_REVISION: - p_node->comp.node_info.revision = 0xFFFFFFFF; - p_node->rec.node_info.revision = - cl_hton32( strtoul( &line[offset], NULL, 0 ) ); - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_parse_node: " - "revision = 0x%X\n", - cl_ntoh32( p_node->rec.node_info.revision ) ); - } - break; + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_parse_node: " + "class_version = 0x%X\n", + p_node->rec.node_info.class_version ); + } + break; - case OSMTEST_TOKEN_PORT_NUM: - p_node->comp.node_info.port_num_vendor_id |= - IB_NODE_INFO_PORT_NUM_MASK; - p_node->rec.node_info.port_num_vendor_id |= - ( uint8_t ) strtoul( &line[offset], NULL, 0 ); - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_parse_node: " - "local_port_num = 0x%X\n", - ib_node_info_get_local_port_num( &p_node->rec. - node_info ) ); - } - break; + case OSMTEST_TOKEN_NODE_TYPE: + p_node->comp.node_info.node_type = 0xFF; + p_node->rec.node_info.node_type = + ( uint8_t ) strtoul( &line[offset], NULL, 0 ); + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) + { + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_parse_node: " + "node_type = 0x%X\n", + p_node->rec.node_info.node_type ); + } + break; - case OSMTEST_TOKEN_VENDOR_ID: - p_node->comp.node_info.port_num_vendor_id |= - IB_NODE_INFO_VEND_ID_MASK; - p_node->rec.node_info.port_num_vendor_id |= - cl_hton32( strtoul( &line[offset], NULL, 0 ) ); - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_parse_node: " - "vendor_id = 0x%X\n", - cl_ntoh32( ib_node_info_get_vendor_id - ( &p_node->rec.node_info ) ) ); - } - break; + case OSMTEST_TOKEN_NUM_PORTS: + p_node->comp.node_info.num_ports = 0xFF; + p_node->rec.node_info.num_ports = + ( uint8_t ) strtoul( &line[offset], NULL, 0 ); + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) + { + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_parse_node: " + "num_ports = 0x%X\n", + p_node->rec.node_info.num_ports ); + } + break; - case OSMTEST_TOKEN_END: - done = TRUE; - break; + case OSMTEST_TOKEN_SYS_GUID: + p_node->comp.node_info.sys_guid = 0xFFFFFFFFFFFFFFFFULL; + p_node->rec.node_info.sys_guid = + cl_hton64( strtoull( &line[offset], NULL, 0 ) ); + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) + { + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_parse_node: " + "sys_guid = 0x%016" PRIx64 "\n", + cl_ntoh64( p_node->rec.node_info.sys_guid ) ); + } + break; - default: - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_parse_node: ERR 00121: " - "Ignoring line %u with unknown token: %s\n", - *p_line_num, &line[offset] ); + case OSMTEST_TOKEN_NODE_GUID: + p_node->comp.node_info.node_guid = 0xFFFFFFFFFFFFFFFFULL; + p_node->rec.node_info.node_guid = + cl_hton64( strtoull( &line[offset], NULL, 0 ) ); + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) + { + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_parse_node: " + "node_guid = 0x%016" PRIx64 "\n", + cl_ntoh64( p_node->rec.node_info.node_guid ) ); + } + break; - break; + case OSMTEST_TOKEN_PORT_GUID: + p_node->comp.node_info.port_guid = 0xFFFFFFFFFFFFFFFFULL; + p_node->rec.node_info.port_guid = + cl_hton64( strtoull( &line[offset], NULL, 0 ) ); + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) + { + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_parse_node: " + "port_guid = 0x%016" PRIx64 "\n", + cl_ntoh64( p_node->rec.node_info.port_guid ) ); } - } + break; + + case OSMTEST_TOKEN_PARTITION_CAP: + p_node->comp.node_info.partition_cap = 0xFFFF; + p_node->rec.node_info.partition_cap = cl_hton16( ( uint16_t ) + strtoul( &line[offset], + NULL, 0 ) ); + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) + { + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_parse_node: " + "partition_cap = 0x%X\n", + cl_ntoh16( p_node->rec.node_info.partition_cap ) ); + } + break; + + case OSMTEST_TOKEN_DEVICE_ID: + p_node->comp.node_info.device_id = 0xFFFF; + p_node->rec.node_info.device_id = cl_hton16( ( uint16_t ) + strtoul( &line[offset], + NULL, 0 ) ); + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) + { + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_parse_node: " + "device_id = 0x%X\n", + cl_ntoh16( p_node->rec.node_info.device_id ) ); + } + break; + + case OSMTEST_TOKEN_REVISION: + p_node->comp.node_info.revision = 0xFFFFFFFF; + p_node->rec.node_info.revision = + cl_hton32( strtoul( &line[offset], NULL, 0 ) ); + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) + { + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_parse_node: " + "revision = 0x%X\n", + cl_ntoh32( p_node->rec.node_info.revision ) ); + } + break; + + case OSMTEST_TOKEN_PORT_NUM: + p_node->comp.node_info.port_num_vendor_id |= IB_NODE_INFO_PORT_NUM_MASK; + p_node->rec.node_info.port_num_vendor_id |= + ( uint8_t ) strtoul( &line[offset], NULL, 0 ); + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) + { + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_parse_node: " + "local_port_num = 0x%X\n", + ib_node_info_get_local_port_num( &p_node->rec. + node_info ) ); + } + break; + + case OSMTEST_TOKEN_VENDOR_ID: + p_node->comp.node_info.port_num_vendor_id |= IB_NODE_INFO_VEND_ID_MASK; + p_node->rec.node_info.port_num_vendor_id |= + cl_hton32( strtoul( &line[offset], NULL, 0 ) ); + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) + { + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_parse_node: " + "vendor_id = 0x%X\n", + cl_ntoh32( ib_node_info_get_vendor_id + ( &p_node->rec.node_info ) ) ); + } + break; + + case OSMTEST_TOKEN_END: + done = TRUE; + break; + + default: + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_parse_node: ERR 0121: " + "Ignoring line %u with unknown token: %s\n", + *p_line_num, &line[offset] ); + + break; + } + } /* * Make sure the user specified enough information, then * add this object to the database. */ if( p_node->comp.lid == 0 ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_parse_node: ERR 00122: " - "LID must be specified for defined nodes\n" ); - node_delete( p_node ); - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_parse_node: ERR 0122: " + "LID must be specified for defined nodes\n" ); + node_delete( p_node ); + goto Exit; + } cl_qmap_insert( &p_osmt->exp_subn.node_lid_tbl, p_node->rec.lid, &p_node->map_item ); @@ -5062,523 +6170,521 @@ osmtest_parse_port( IN osmtest_t * const p_osmt, * Parse the inventory file and create the database. */ while( !done ) + { + if( fgets( line, OSMTEST_MAX_LINE_LEN, fh ) == NULL ) { - if( fgets( line, OSMTEST_MAX_LINE_LEN, fh ) == NULL ) - { - /* - * End of file in the middle of a definition. - */ - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_parse_port: ERR 00123: " - "Unexpected end of file\n" ); - status = IB_ERROR; - goto Exit; - } - - ++*p_line_num; - /* - * Skip whitespace + * End of file in the middle of a definition. */ - offset = 0; - if( !str_skip_white( line, &offset ) ) - continue; /* whole line was whitespace */ + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_parse_port: ERR 0123: " + "Unexpected end of file\n" ); + status = IB_ERROR; + goto Exit; + } + + ++*p_line_num; + + /* + * Skip whitespace + */ + offset = 0; + if( !str_skip_white( line, &offset ) ) + continue; /* whole line was whitespace */ + + p_tok = str_get_token( &line[offset] ); + if( p_tok == NULL ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_parse_port: ERR 0124: " + "Ignoring line %u with unknown token: %s\n", + *p_line_num, &line[offset] ); + continue; + } + + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) + { + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_parse_port: " + "Found '%s' (line %u)\n", p_tok->str, *p_line_num ); + } + + str_skip_token( line, &offset ); + + switch ( p_tok->val ) + { + case OSMTEST_TOKEN_COMMENT: + break; - p_tok = str_get_token( &line[offset] ); - if( p_tok == NULL ) + case OSMTEST_TOKEN_LID: + p_port->comp.lid = 0xFFFF; + p_port->rec.lid = + cl_hton16( ( uint16_t ) strtoul( &line[offset], NULL, 0 ) ); + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_parse_port: ERR 00124: " - "Ignoring line %u with unknown token: %s\n", - *p_line_num, &line[offset] ); - continue; + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_parse_port: " + "lid = 0x%X\n", cl_ntoh16( p_port->rec.lid ) ); } + break; - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) + case OSMTEST_TOKEN_PORT_NUM: + p_port->comp.port_num = 0xFF; + p_port->rec.port_num = + ( uint8_t ) strtoul( &line[offset], NULL, 0 ); + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) { osm_log( &p_osmt->log, OSM_LOG_DEBUG, "osmtest_parse_port: " - "Found '%s' (line %u)\n", p_tok->str, *p_line_num ); + "port_num = 0x%u\n", + p_port->rec.port_num ); } + break; - str_skip_token( line, &offset ); - - switch ( p_tok->val ) + case OSMTEST_TOKEN_MKEY: + p_port->comp.port_info.m_key = 0xFFFFFFFFFFFFFFFFULL; + p_port->rec.port_info.m_key = + cl_hton64( strtoull( &line[offset], NULL, 0 ) ); + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) { - case OSMTEST_TOKEN_COMMENT: - break; - - case OSMTEST_TOKEN_LID: - p_port->comp.lid = 0xFFFF; - p_port->rec.lid = - cl_hton16( ( uint16_t ) strtoul( &line[offset], NULL, 0 ) ); - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_parse_port: " - "lid = 0x%X\n", cl_ntoh16( p_port->rec.lid ) ); - } - break; - - case OSMTEST_TOKEN_PORT_NUM: - p_port->comp.port_num = 0xFF; - p_port->rec.port_num = - ( uint8_t ) strtoul( &line[offset], NULL, 0 ); - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_parse_port: " - "port_num = 0x%u\n", - p_port->rec.port_num ); - } - break; - - case OSMTEST_TOKEN_MKEY: - p_port->comp.port_info.m_key = 0xFFFFFFFFFFFFFFFFULL; - p_port->rec.port_info.m_key = - cl_hton64( strtoull( &line[offset], NULL, 0 ) ); - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_parse_port: " - "m_key = 0x%016" PRIx64 "\n", - cl_ntoh64( p_port->rec.port_info.m_key ) ); - } - break; - - case OSMTEST_TOKEN_SUBN_PREF: - p_port->comp.port_info.subnet_prefix = 0xFFFFFFFFFFFFFFFFULL; - p_port->rec.port_info.subnet_prefix = - cl_hton64( strtoull( &line[offset], NULL, 0 ) ); - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_parse_port: " - "subnet_prefix = 0x%016" PRIx64 "\n", - cl_ntoh64( p_port->rec.port_info.subnet_prefix ) ); - } - break; - - case OSMTEST_TOKEN_BASE_LID: - p_port->comp.port_info.base_lid = 0xFFFF; - p_port->rec.port_info.base_lid = - cl_hton16( ( uint16_t ) strtoul( &line[offset], NULL, 0 ) ); - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_parse_port: " - "base_lid = 0x%X\n", cl_ntoh16( p_port->rec.port_info.base_lid ) ); - } - break; - - case OSMTEST_TOKEN_SM_BASE_LID: - p_port->comp.port_info.master_sm_base_lid = 0xFFFF; - p_port->rec.port_info.master_sm_base_lid = - cl_hton16( ( uint16_t ) strtoul( &line[offset], NULL, 0 ) ); - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_parse_port: " - "master_sm_base_lid = 0x%X\n", - cl_ntoh16( p_port->rec.port_info.master_sm_base_lid ) ); - } - break; - - case OSMTEST_TOKEN_CAP_MASK: - p_port->comp.port_info.capability_mask = 0xFFFFFFFF; - p_port->rec.port_info.capability_mask = - cl_hton32( ( uint32_t ) strtoul( &line[offset], NULL, 0 ) ); - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_parse_port: " - "capability_mask = 0x%X\n", - cl_ntoh32( p_port->rec.port_info.capability_mask ) ); - } - break; - - case OSMTEST_TOKEN_DIAG_CODE: - p_port->comp.port_info.diag_code = 0xFFFF; - p_port->rec.port_info.diag_code = - cl_hton16( ( uint16_t ) strtoul( &line[offset], NULL, 0 ) ); - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_parse_port: " - "diag_code = 0x%X\n", - cl_ntoh16( p_port->rec.port_info.diag_code ) ); - } - break; + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_parse_port: " + "m_key = 0x%016" PRIx64 "\n", + cl_ntoh64( p_port->rec.port_info.m_key ) ); + } + break; - case OSMTEST_TOKEN_MKEY_LEASE_PER: - p_port->comp.port_info.m_key_lease_period = 0xFFFF; - p_port->rec.port_info.m_key_lease_period = - cl_hton16( ( uint16_t ) strtoul( &line[offset], NULL, 0 ) ); - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_parse_port: " - "m_key_lease_period = 0x%X\n", - cl_ntoh16( p_port->rec.port_info.m_key_lease_period ) ); - } - break; + case OSMTEST_TOKEN_SUBN_PREF: + p_port->comp.port_info.subnet_prefix = 0xFFFFFFFFFFFFFFFFULL; + p_port->rec.port_info.subnet_prefix = + cl_hton64( strtoull( &line[offset], NULL, 0 ) ); + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) + { + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_parse_port: " + "subnet_prefix = 0x%016" PRIx64 "\n", + cl_ntoh64( p_port->rec.port_info.subnet_prefix ) ); + } + break; - case OSMTEST_TOKEN_LOC_PORT_NUM: - p_port->comp.port_info.local_port_num = 0xFF; - p_port->rec.port_info.local_port_num = - ( uint8_t ) strtoul( &line[offset], NULL, 0 ); - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_parse_port: " - "local_port_num = 0x%u\n", - p_port->rec.port_info.local_port_num ); - } - break; + case OSMTEST_TOKEN_BASE_LID: + p_port->comp.port_info.base_lid = 0xFFFF; + p_port->rec.port_info.base_lid = + cl_hton16( ( uint16_t ) strtoul( &line[offset], NULL, 0 ) ); + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) + { + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_parse_port: " + "base_lid = 0x%X\n", cl_ntoh16( p_port->rec.port_info.base_lid ) ); + } + break; - case OSMTEST_TOKEN_LINK_WID_EN: - p_port->comp.port_info.link_width_enabled = 0xFF; - p_port->rec.port_info.link_width_enabled = - ( uint8_t ) strtoul( &line[offset], NULL, 0 ); - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_parse_port: " - "link_width_enabled = 0x%u\n", - p_port->rec.port_info.link_width_enabled ); - } - break; + case OSMTEST_TOKEN_SM_BASE_LID: + p_port->comp.port_info.master_sm_base_lid = 0xFFFF; + p_port->rec.port_info.master_sm_base_lid = + cl_hton16( ( uint16_t ) strtoul( &line[offset], NULL, 0 ) ); + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) + { + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_parse_port: " + "master_sm_base_lid = 0x%X\n", + cl_ntoh16( p_port->rec.port_info.master_sm_base_lid ) ); + } + break; - case OSMTEST_TOKEN_LINK_WID_SUP: - p_port->comp.port_info.link_width_supported = 0xFF; - p_port->rec.port_info.link_width_supported = - ( uint8_t ) strtoul( &line[offset], NULL, 0 ); - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_parse_port: " - "link_width_supported = 0x%u\n", - p_port->rec.port_info.link_width_supported ); - } - break; + case OSMTEST_TOKEN_CAP_MASK: + p_port->comp.port_info.capability_mask = 0xFFFFFFFF; + p_port->rec.port_info.capability_mask = + cl_hton32( ( uint32_t ) strtoul( &line[offset], NULL, 0 ) ); + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) + { + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_parse_port: " + "capability_mask = 0x%X\n", + cl_ntoh32( p_port->rec.port_info.capability_mask ) ); + } + break; - case OSMTEST_TOKEN_LINK_WID_ACT: - p_port->comp.port_info.link_width_active = 0xFF; - p_port->rec.port_info.link_width_active = - ( uint8_t ) strtoul( &line[offset], NULL, 0 ); - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_parse_port: " - "link_width_active = 0x%u\n", - p_port->rec.port_info.link_width_active ); - } - break; + case OSMTEST_TOKEN_DIAG_CODE: + p_port->comp.port_info.diag_code = 0xFFFF; + p_port->rec.port_info.diag_code = + cl_hton16( ( uint16_t ) strtoul( &line[offset], NULL, 0 ) ); + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) + { + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_parse_port: " + "diag_code = 0x%X\n", + cl_ntoh16( p_port->rec.port_info.diag_code ) ); + } + break; - case OSMTEST_TOKEN_LINK_SPEED_SUP: - p_port->comp.port_info.state_info1 = 0xFF; - ib_port_info_set_link_speed_sup( - ( uint8_t ) strtoul( &line[offset], NULL, 0 ), - &p_port->rec.port_info); - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_parse_port: " - "link_speed_supported = 0x%u\n", - ib_port_info_get_link_speed_sup(&p_port->rec.port_info)); - } - break; + case OSMTEST_TOKEN_MKEY_LEASE_PER: + p_port->comp.port_info.m_key_lease_period = 0xFFFF; + p_port->rec.port_info.m_key_lease_period = + cl_hton16( ( uint16_t ) strtoul( &line[offset], NULL, 0 ) ); + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) + { + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_parse_port: " + "m_key_lease_period = 0x%X\n", + cl_ntoh16( p_port->rec.port_info.m_key_lease_period ) ); + } + break; - case OSMTEST_TOKEN_PORT_STATE: - str_skip_white( line, &offset ); - p_port->comp.port_info.state_info1 = 0xFF; - ib_port_info_set_port_state(&p_port->rec.port_info, - ib_get_port_state_from_str(&line[offset])); - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_parse_port: " - "port_state = 0x%u\n", - ib_port_info_get_port_state(&p_port->rec.port_info)); - } - break; + case OSMTEST_TOKEN_LOC_PORT_NUM: + p_port->comp.port_info.local_port_num = 0xFF; + p_port->rec.port_info.local_port_num = + ( uint8_t ) strtoul( &line[offset], NULL, 0 ); + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) + { + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_parse_port: " + "local_port_num = 0x%u\n", + p_port->rec.port_info.local_port_num ); + } + break; - case OSMTEST_TOKEN_STATE_INFO2: - p_port->comp.port_info.state_info2 = 0xFF; - p_port->rec.port_info.state_info2 = - ( uint8_t ) strtoul( &line[offset], NULL, 0 ); - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_parse_port: " - "state_info2 = 0x%u\n", - p_port->rec.port_info.state_info2 ); - } - break; + case OSMTEST_TOKEN_LINK_WID_EN: + p_port->comp.port_info.link_width_enabled = 0xFF; + p_port->rec.port_info.link_width_enabled = + ( uint8_t ) strtoul( &line[offset], NULL, 0 ); + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) + { + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_parse_port: " + "link_width_enabled = 0x%u\n", + p_port->rec.port_info.link_width_enabled ); + } + break; - case OSMTEST_TOKEN_MKEY_PROT_BITS: - p_port->comp.port_info.mkey_lmc = 0xFF; - ib_port_info_set_mpb( - &p_port->rec.port_info, - ( uint8_t ) strtoul( &line[offset], NULL, 0 )); - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_parse_port: " - "mpb = 0x%u\n", - ib_port_info_get_mpb(&p_port->rec.port_info) ); - } - break; + case OSMTEST_TOKEN_LINK_WID_SUP: + p_port->comp.port_info.link_width_supported = 0xFF; + p_port->rec.port_info.link_width_supported = + ( uint8_t ) strtoul( &line[offset], NULL, 0 ); + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) + { + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_parse_port: " + "link_width_supported = 0x%u\n", + p_port->rec.port_info.link_width_supported ); + } + break; - case OSMTEST_TOKEN_LMC: - p_port->comp.port_info.mkey_lmc = 0xFF; - ib_port_info_set_lmc( - &p_port->rec.port_info, - ( uint8_t ) strtoul( &line[offset], NULL, 0 ) ); + case OSMTEST_TOKEN_LINK_WID_ACT: + p_port->comp.port_info.link_width_active = 0xFF; + p_port->rec.port_info.link_width_active = + ( uint8_t ) strtoul( &line[offset], NULL, 0 ); + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) + { + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_parse_port: " + "link_width_active = 0x%u\n", + p_port->rec.port_info.link_width_active ); + } + break; + + case OSMTEST_TOKEN_LINK_SPEED_SUP: + p_port->comp.port_info.state_info1 = 0xFF; + ib_port_info_set_link_speed_sup( ( uint8_t ) strtoul( &line[offset], + NULL, 0 ), + &p_port->rec.port_info); + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) + { + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_parse_port: " + "link_speed_supported = 0x%u\n", + ib_port_info_get_link_speed_sup(&p_port->rec.port_info)); + } + break; + + case OSMTEST_TOKEN_PORT_STATE: + str_skip_white( line, &offset ); + p_port->comp.port_info.state_info1 = 0xFF; + ib_port_info_set_port_state(&p_port->rec.port_info, + ib_get_port_state_from_str(&line[offset])); + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) + { + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_parse_port: " + "port_state = 0x%u\n", + ib_port_info_get_port_state(&p_port->rec.port_info)); + } + break; - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_parse_port: " - "lmc = 0x%u\n", - ib_port_info_get_lmc(&p_port->rec.port_info) ); - } - break; + case OSMTEST_TOKEN_STATE_INFO2: + p_port->comp.port_info.state_info2 = 0xFF; + p_port->rec.port_info.state_info2 = + ( uint8_t ) strtoul( &line[offset], NULL, 0 ); + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) + { + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_parse_port: " + "state_info2 = 0x%u\n", + p_port->rec.port_info.state_info2 ); + } + break; - case OSMTEST_TOKEN_LINK_SPEED: - p_port->comp.port_info.link_speed = 0xFF; - p_port->rec.port_info.link_speed = - ( uint8_t ) strtoul( &line[offset], NULL, 0 ); - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_parse_port: " - "link_speed = 0x%u\n", - p_port->rec.port_info.link_speed ); - } - break; + case OSMTEST_TOKEN_MKEY_PROT_BITS: + p_port->comp.port_info.mkey_lmc = 0xFF; + ib_port_info_set_mpb( &p_port->rec.port_info, + ( uint8_t ) strtoul( &line[offset], NULL, 0 ) ); + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) + { + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_parse_port: " + "mpb = 0x%u\n", + ib_port_info_get_mpb(&p_port->rec.port_info) ); + } + break; - case OSMTEST_TOKEN_MTU_SMSL: - p_port->comp.port_info.mtu_smsl = 0xFF; - p_port->rec.port_info.mtu_smsl = - ( uint8_t ) strtoul( &line[offset], NULL, 0 ); - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_parse_port: " - "mtu_smsl = 0x%u\n", - p_port->rec.port_info.mtu_smsl ); - } - break; + case OSMTEST_TOKEN_LMC: + p_port->comp.port_info.mkey_lmc = 0xFF; + ib_port_info_set_lmc( &p_port->rec.port_info, + ( uint8_t ) strtoul( &line[offset], NULL, 0 ) ); - case OSMTEST_TOKEN_VL_CAP: - p_port->comp.port_info.vl_cap = 0xFF; - p_port->rec.port_info.vl_cap = - ( uint8_t ) strtoul( &line[offset], NULL, 0 ); - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_parse_port: " - "vl_cap = 0x%u\n", - p_port->rec.port_info.vl_cap ); - } - break; + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) + { + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_parse_port: " + "lmc = 0x%u\n", + ib_port_info_get_lmc(&p_port->rec.port_info) ); + } + break; - case OSMTEST_TOKEN_VL_HIGH_LIMIT: - p_port->comp.port_info.vl_high_limit = 0xFF; - p_port->rec.port_info.vl_high_limit = - ( uint8_t ) strtoul( &line[offset], NULL, 0 ); - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_parse_port: " - "vl_high_limit = 0x%u\n", - p_port->rec.port_info.vl_high_limit ); - } - break; + case OSMTEST_TOKEN_LINK_SPEED: + p_port->comp.port_info.link_speed = 0xFF; + p_port->rec.port_info.link_speed = + ( uint8_t ) strtoul( &line[offset], NULL, 0 ); + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) + { + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_parse_port: " + "link_speed = 0x%u\n", + p_port->rec.port_info.link_speed ); + } + break; - case OSMTEST_TOKEN_VL_ARB_HIGH_CAP: - p_port->comp.port_info.vl_arb_high_cap = 0xFF; - p_port->rec.port_info.vl_arb_high_cap = - ( uint8_t ) strtoul( &line[offset], NULL, 0 ); - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_parse_port: " - "vl_arb_high_cap = 0x%u\n", - p_port->rec.port_info.vl_arb_high_cap ); - } - break; + case OSMTEST_TOKEN_MTU_SMSL: + p_port->comp.port_info.mtu_smsl = 0xFF; + p_port->rec.port_info.mtu_smsl = + ( uint8_t ) strtoul( &line[offset], NULL, 0 ); + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) + { + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_parse_port: " + "mtu_smsl = 0x%u\n", + p_port->rec.port_info.mtu_smsl ); + } + break; - case OSMTEST_TOKEN_VL_ARB_LOW_CAP: - p_port->comp.port_info.vl_arb_low_cap = 0xFF; - p_port->rec.port_info.vl_arb_low_cap = - ( uint8_t ) strtoul( &line[offset], NULL, 0 ); - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_parse_port: " - "vl_arb_low_cap = 0x%u\n", - p_port->rec.port_info.vl_arb_low_cap ); - } - break; + case OSMTEST_TOKEN_VL_CAP: + p_port->comp.port_info.vl_cap = 0xFF; + p_port->rec.port_info.vl_cap = + ( uint8_t ) strtoul( &line[offset], NULL, 0 ); + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) + { + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_parse_port: " + "vl_cap = 0x%u\n", + p_port->rec.port_info.vl_cap ); + } + break; - case OSMTEST_TOKEN_MTU_CAP: - p_port->comp.port_info.mtu_cap = 0xFF; - p_port->rec.port_info.mtu_cap = - ( uint8_t ) strtoul( &line[offset], NULL, 0 ); - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_parse_port: " - "mtu_cap = 0x%u\n", - p_port->rec.port_info.mtu_cap ); - } - break; + case OSMTEST_TOKEN_VL_HIGH_LIMIT: + p_port->comp.port_info.vl_high_limit = 0xFF; + p_port->rec.port_info.vl_high_limit = + ( uint8_t ) strtoul( &line[offset], NULL, 0 ); + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) + { + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_parse_port: " + "vl_high_limit = 0x%u\n", + p_port->rec.port_info.vl_high_limit ); + } + break; - case OSMTEST_TOKEN_VL_STALL_LIFE: - p_port->comp.port_info.vl_stall_life = 0xFF; - p_port->rec.port_info.vl_stall_life = - ( uint8_t ) strtoul( &line[offset], NULL, 0 ); - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_parse_port: " - "vl_stall_life = 0x%u\n", - p_port->rec.port_info.vl_stall_life ); - } - break; + case OSMTEST_TOKEN_VL_ARB_HIGH_CAP: + p_port->comp.port_info.vl_arb_high_cap = 0xFF; + p_port->rec.port_info.vl_arb_high_cap = + ( uint8_t ) strtoul( &line[offset], NULL, 0 ); + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) + { + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_parse_port: " + "vl_arb_high_cap = 0x%u\n", + p_port->rec.port_info.vl_arb_high_cap ); + } + break; - case OSMTEST_TOKEN_VL_ENFORCE: - p_port->comp.port_info.vl_enforce = 0xFF; - p_port->rec.port_info.vl_enforce = - ( uint8_t ) strtoul( &line[offset], NULL, 0 ); - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_parse_port: " - "vl_enforce = 0x%u\n", - p_port->rec.port_info.vl_enforce ); - } - break; + case OSMTEST_TOKEN_VL_ARB_LOW_CAP: + p_port->comp.port_info.vl_arb_low_cap = 0xFF; + p_port->rec.port_info.vl_arb_low_cap = + ( uint8_t ) strtoul( &line[offset], NULL, 0 ); + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) + { + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_parse_port: " + "vl_arb_low_cap = 0x%u\n", + p_port->rec.port_info.vl_arb_low_cap ); + } + break; - case OSMTEST_TOKEN_MKEY_VIOL: - p_port->comp.port_info.m_key_violations = 0xFFFF; - p_port->rec.port_info.m_key_violations = - cl_hton16( ( uint16_t ) strtoul( &line[offset], NULL, 0 ) ); - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_parse_port: " - "m_key_violations = 0x%X\n", - cl_ntoh16( p_port->rec.port_info.m_key_violations ) ); - } - break; + case OSMTEST_TOKEN_MTU_CAP: + p_port->comp.port_info.mtu_cap = 0xFF; + p_port->rec.port_info.mtu_cap = + ( uint8_t ) strtoul( &line[offset], NULL, 0 ); + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) + { + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_parse_port: " + "mtu_cap = 0x%u\n", + p_port->rec.port_info.mtu_cap ); + } + break; - case OSMTEST_TOKEN_PKEY_VIOL: - p_port->comp.port_info.p_key_violations = 0xFFFF; - p_port->rec.port_info.p_key_violations = - cl_hton16( ( uint16_t ) strtoul( &line[offset], NULL, 0 ) ); - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_parse_port: " - "p_key_violations = 0x%X\n", - cl_ntoh16( p_port->rec.port_info.p_key_violations ) ); - } - break; + case OSMTEST_TOKEN_VL_STALL_LIFE: + p_port->comp.port_info.vl_stall_life = 0xFF; + p_port->rec.port_info.vl_stall_life = + ( uint8_t ) strtoul( &line[offset], NULL, 0 ); + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) + { + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_parse_port: " + "vl_stall_life = 0x%u\n", + p_port->rec.port_info.vl_stall_life ); + } + break; - case OSMTEST_TOKEN_QKEY_VIOL: - p_port->comp.port_info.q_key_violations = 0xFFFF; - p_port->rec.port_info.q_key_violations = - cl_hton16( ( uint16_t ) strtoul( &line[offset], NULL, 0 ) ); - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_parse_port: " - "q_key_violations = 0x%X\n", - cl_ntoh16( p_port->rec.port_info.q_key_violations ) ); - } - break; + case OSMTEST_TOKEN_VL_ENFORCE: + p_port->comp.port_info.vl_enforce = 0xFF; + p_port->rec.port_info.vl_enforce = + ( uint8_t ) strtoul( &line[offset], NULL, 0 ); + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) + { + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_parse_port: " + "vl_enforce = 0x%u\n", + p_port->rec.port_info.vl_enforce ); + } + break; - case OSMTEST_TOKEN_GUID_CAP: - p_port->comp.port_info.guid_cap = 0xFF; - p_port->rec.port_info.guid_cap = - ( uint8_t ) strtoul( &line[offset], NULL, 0 ); - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_parse_port: " - "guid_cap = 0x%u\n", - p_port->rec.port_info.guid_cap ); - } - break; + case OSMTEST_TOKEN_MKEY_VIOL: + p_port->comp.port_info.m_key_violations = 0xFFFF; + p_port->rec.port_info.m_key_violations = + cl_hton16( ( uint16_t ) strtoul( &line[offset], NULL, 0 ) ); + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) + { + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_parse_port: " + "m_key_violations = 0x%X\n", + cl_ntoh16( p_port->rec.port_info.m_key_violations ) ); + } + break; - case OSMTEST_TOKEN_SUBN_TIMEOUT: - p_port->comp.port_info.subnet_timeout = 0x1F; - p_port->rec.port_info.subnet_timeout = - ( uint8_t ) strtoul( &line[offset], NULL, 0 ); - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_parse_port: " - "subnet_timeout = 0x%u\n", - ib_port_info_get_timeout(&p_port->rec.port_info) ); - } - break; + case OSMTEST_TOKEN_PKEY_VIOL: + p_port->comp.port_info.p_key_violations = 0xFFFF; + p_port->rec.port_info.p_key_violations = + cl_hton16( ( uint16_t ) strtoul( &line[offset], NULL, 0 ) ); + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) + { + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_parse_port: " + "p_key_violations = 0x%X\n", + cl_ntoh16( p_port->rec.port_info.p_key_violations ) ); + } + break; - case OSMTEST_TOKEN_RESP_TIME_VAL: - p_port->comp.port_info.resp_time_value = 0xFF; - p_port->rec.port_info.resp_time_value = - ( uint8_t ) strtoul( &line[offset], NULL, 0 ); - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_parse_port: " - "resp_time_value = 0x%u\n", - p_port->rec.port_info.resp_time_value ); - } - break; + case OSMTEST_TOKEN_QKEY_VIOL: + p_port->comp.port_info.q_key_violations = 0xFFFF; + p_port->rec.port_info.q_key_violations = + cl_hton16( ( uint16_t ) strtoul( &line[offset], NULL, 0 ) ); + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) + { + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_parse_port: " + "q_key_violations = 0x%X\n", + cl_ntoh16( p_port->rec.port_info.q_key_violations ) ); + } + break; - case OSMTEST_TOKEN_ERR_THRESHOLD: - p_port->comp.port_info.error_threshold = 0xFF; - p_port->rec.port_info.error_threshold = - ( uint8_t ) strtoul( &line[offset], NULL, 0 ); - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_parse_port: " - "error_threshold = 0x%u\n", - p_port->rec.port_info.error_threshold ); - } - break; + case OSMTEST_TOKEN_GUID_CAP: + p_port->comp.port_info.guid_cap = 0xFF; + p_port->rec.port_info.guid_cap = + ( uint8_t ) strtoul( &line[offset], NULL, 0 ); + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) + { + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_parse_port: " + "guid_cap = 0x%u\n", + p_port->rec.port_info.guid_cap ); + } + break; - case OSMTEST_TOKEN_END: - done = TRUE; - break; + case OSMTEST_TOKEN_SUBN_TIMEOUT: + p_port->comp.port_info.subnet_timeout = 0x1F; + p_port->rec.port_info.subnet_timeout = + ( uint8_t ) strtoul( &line[offset], NULL, 0 ); + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) + { + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_parse_port: " + "subnet_timeout = 0x%u\n", + ib_port_info_get_timeout(&p_port->rec.port_info) ); + } + break; - default: - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_parse_port: ERR 00125: " - "Ignoring line %u with unknown token: %s\n", - *p_line_num, &line[offset] ); + case OSMTEST_TOKEN_RESP_TIME_VAL: + p_port->comp.port_info.resp_time_value = 0xFF; + p_port->rec.port_info.resp_time_value = + ( uint8_t ) strtoul( &line[offset], NULL, 0 ); + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) + { + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_parse_port: " + "resp_time_value = 0x%u\n", + p_port->rec.port_info.resp_time_value ); + } + break; - break; + case OSMTEST_TOKEN_ERR_THRESHOLD: + p_port->comp.port_info.error_threshold = 0xFF; + p_port->rec.port_info.error_threshold = + ( uint8_t ) strtoul( &line[offset], NULL, 0 ); + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) + { + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_parse_port: " + "error_threshold = 0x%u\n", + p_port->rec.port_info.error_threshold ); } + break; + + case OSMTEST_TOKEN_END: + done = TRUE; + break; + + default: + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_parse_port: ERR 0125: " + "Ignoring line %u with unknown token: %s\n", + *p_line_num, &line[offset] ); + break; } + } /* * Make sure the user specified enough information, then * add this object to the database. */ if( p_port->comp.lid == 0 ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_parse_port: ERR 00126: " - "LID must be specified for defined ports\n" ); - port_delete( p_port ); - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_parse_port: ERR 0126: " + "LID must be specified for defined ports\n" ); + port_delete( p_port ); + status = IB_ERROR; + goto Exit; + } cl_qmap_insert( &p_osmt->exp_subn.port_key_tbl, port_gen_id(p_port->rec.lid, p_port->rec.port_num), @@ -5589,7 +6695,6 @@ osmtest_parse_port( IN osmtest_t * const p_osmt, return ( status ); } - /********************************************************************** **********************************************************************/ static ib_api_status_t @@ -5603,174 +6708,274 @@ osmtest_parse_path( IN osmtest_t * const p_osmt, boolean_t done = FALSE; path_t *p_path; const osmtest_token_t *p_tok; + boolean_t got_error = FALSE; OSM_LOG_ENTER( &p_osmt->log, osmtest_parse_path ); - p_path = path_new( ); + p_path = path_new( ); CL_ASSERT( p_path != NULL ); /* * Parse the inventory file and create the database. */ while( !done ) + { + if( fgets( line, OSMTEST_MAX_LINE_LEN, fh ) == NULL ) + { + /* + * End of file in the middle of a definition. + */ + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_parse_path: ERR 0127: " + "Unexpected end of file\n" ); + status = IB_ERROR; + goto Exit; + } + + ++*p_line_num; + + /* + * Skip whitespace + */ + offset = 0; + if( !str_skip_white( line, &offset ) ) + continue; /* whole line was whitespace */ + + p_tok = str_get_token( &line[offset] ); + if( p_tok == NULL ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_parse_path: ERR 0128: " + "Ignoring line %u with unknown token: %s\n", + *p_line_num, &line[offset] ); + got_error = TRUE; + continue; + } + + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) + { + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_parse_path: " + "Found '%s' (line %u)\n", p_tok->str, *p_line_num ); + } + + str_skip_token( line, &offset ); + + switch ( p_tok->val ) { - if( fgets( line, OSMTEST_MAX_LINE_LEN, fh ) == NULL ) + case OSMTEST_TOKEN_COMMENT: + break; + + case OSMTEST_TOKEN_DGID: + p_path->comp.dgid.unicast.prefix = 0xFFFFFFFFFFFFFFFFULL; + p_path->comp.dgid.unicast.interface_id = 0xFFFFFFFFFFFFFFFFULL; + + str_skip_white( line, &offset ); + p_path->rec.dgid.unicast.prefix = + cl_hton64( strtoull( &line[offset], NULL, 0 ) ); + str_skip_token( line, &offset ); + p_path->rec.dgid.unicast.interface_id = + cl_hton64( strtoull( &line[offset], NULL, 0 ) ); + + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) { - /* - * End of file in the middle of a definition. - */ - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_parse_path: ERR 00127: " - "Unexpected end of file\n" ); - status = IB_ERROR; - goto Exit; + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_parse_path: " + "dgid = 0x%016" PRIx64 " 0x%016" PRIx64 "\n", + cl_ntoh64( p_path->rec.dgid.unicast.prefix ), + cl_ntoh64( p_path->rec.dgid.unicast.interface_id ) ); } + break; - ++*p_line_num; + case OSMTEST_TOKEN_SGID: + p_path->comp.sgid.unicast.prefix = 0xFFFFFFFFFFFFFFFFULL; + p_path->comp.sgid.unicast.interface_id = 0xFFFFFFFFFFFFFFFFULL; - /* - * Skip whitespace - */ - offset = 0; - if( !str_skip_white( line, &offset ) ) - continue; /* whole line was whitespace */ + str_skip_white( line, &offset ); + p_path->rec.sgid.unicast.prefix = + cl_hton64( strtoull( &line[offset], NULL, 0 ) ); + str_skip_token( line, &offset ); + p_path->rec.sgid.unicast.interface_id = + cl_hton64( strtoull( &line[offset], NULL, 0 ) ); - p_tok = str_get_token( &line[offset] ); - if( p_tok == NULL ) + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_parse_path: ERR 00128: " - "Ignoring line %u with unknown token: %s\n", - *p_line_num, &line[offset] ); - continue; + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_parse_path: " + "sgid = 0x%016" PRIx64 " 0x%016" PRIx64 "\n", + cl_ntoh64( p_path->rec.sgid.unicast.prefix ), + cl_ntoh64( p_path->rec.sgid.unicast.interface_id ) ); } + break; - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) + case OSMTEST_TOKEN_DLID: + p_path->comp.dlid = 0xFFFF; + p_path->rec.dlid = + cl_hton16( ( uint16_t ) strtoul( &line[offset], NULL, 0 ) ); + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) { osm_log( &p_osmt->log, OSM_LOG_DEBUG, "osmtest_parse_path: " - "Found '%s' (line %u)\n", p_tok->str, *p_line_num ); + "dlid = 0x%X\n", cl_ntoh16( p_path->rec.dlid ) ); } + break; - str_skip_token( line, &offset ); + case OSMTEST_TOKEN_SLID: + p_path->comp.slid = 0xFFFF; + p_path->rec.slid = + cl_hton16( ( uint16_t ) strtoul( &line[offset], NULL, 0 ) ); + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) + { + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_parse_path: " + "slid = 0x%X\n", cl_ntoh16( p_path->rec.slid ) ); + } + break; - switch ( p_tok->val ) + case OSMTEST_TOKEN_PKEY: + p_path->comp.pkey = 0xFFFF; + p_path->rec.pkey = + cl_hton16( ( uint16_t ) strtoul( &line[offset], NULL, 0 ) ); + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) { - case OSMTEST_TOKEN_COMMENT: - break; + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_parse_path: " + "pkey = 0x%X\n", cl_ntoh16( p_path->rec.pkey ) ); + } + break; - case OSMTEST_TOKEN_DGID: - p_path->comp.dgid.unicast.prefix = 0xFFFFFFFFFFFFFFFFULL; - p_path->comp.dgid.unicast.interface_id = 0xFFFFFFFFFFFFFFFFULL; + case OSMTEST_TOKEN_END: + done = TRUE; + break; - str_skip_white( line, &offset ); - p_path->rec.dgid.unicast.prefix = - cl_hton64( strtoull( &line[offset], NULL, 0 ) ); - str_skip_token( line, &offset ); - p_path->rec.dgid.unicast.interface_id = - cl_hton64( strtoull( &line[offset], NULL, 0 ) ); + default: + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_parse_path: ERR 0129: " + "Ignoring line %u with unknown token: %s\n", + *p_line_num, &line[offset] ); + got_error = TRUE; + break; + } + } - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_parse_path: " - "dgid = 0x%016" PRIx64 " 0x%016" PRIx64 "\n", - cl_ntoh64( p_path->rec.dgid.unicast.prefix ), - cl_ntoh64( p_path->rec.dgid.unicast.interface_id ) ); - } - break; + if( got_error ) + { + status = IB_ERROR; + goto Exit; + } + /* + * Make sure the user specified enough information, then + * add this object to the database. + */ + if( osmtest_path_rec_kay_is_valid( p_osmt, p_path ) == FALSE ) + { + path_delete( p_path ); + status = IB_ERROR; + goto Exit; + } + + cl_qmap_insert( &p_osmt->exp_subn.path_tbl, + osmtest_path_rec_key_get( &p_path->rec ), + &p_path->map_item ); + + Exit: + OSM_LOG_EXIT( &p_osmt->log ); + return ( status ); +} + +/********************************************************************** + **********************************************************************/ +static ib_api_status_t +osmtest_parse_link( IN osmtest_t * const p_osmt, + IN FILE * const fh, + IN OUT uint32_t * const p_line_num ) +{ + ib_api_status_t status = IB_SUCCESS; + uint32_t offset; + char line[OSMTEST_MAX_LINE_LEN]; + boolean_t done = FALSE; + const osmtest_token_t *p_tok; + boolean_t got_error = FALSE; - case OSMTEST_TOKEN_SGID: - p_path->comp.sgid.unicast.prefix = 0xFFFFFFFFFFFFFFFFULL; - p_path->comp.sgid.unicast.interface_id = 0xFFFFFFFFFFFFFFFFULL; + OSM_LOG_ENTER( &p_osmt->log, osmtest_parse_link); - str_skip_white( line, &offset ); - p_path->rec.sgid.unicast.prefix = - cl_hton64( strtoull( &line[offset], NULL, 0 ) ); - str_skip_token( line, &offset ); - p_path->rec.sgid.unicast.interface_id = - cl_hton64( strtoull( &line[offset], NULL, 0 ) ); + /* + * Parse the inventory file and create the database. + */ + while( !done ) + { + if( fgets( line, OSMTEST_MAX_LINE_LEN, fh ) == NULL ) + { + /* + * End of file in the middle of a definition. + */ + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_parse_link: ERR 012A: " + "Unexpected end of file\n" ); + status = IB_ERROR; + goto Exit; + } - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_parse_path: " - "sgid = 0x%016" PRIx64 " 0x%016" PRIx64 "\n", - cl_ntoh64( p_path->rec.sgid.unicast.prefix ), - cl_ntoh64( p_path->rec.sgid.unicast.interface_id ) ); - } - break; + ++*p_line_num; - case OSMTEST_TOKEN_DLID: - p_path->comp.dlid = 0xFFFF; - p_path->rec.dlid = - cl_hton16( ( uint16_t ) strtoul( &line[offset], NULL, 0 ) ); - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_parse_path: " - "dlid = 0x%X\n", cl_ntoh16( p_path->rec.dlid ) ); - } - break; + /* + * Skip whitespace + */ + offset = 0; + if( !str_skip_white( line, &offset ) ) + continue; /* whole line was whitespace */ - case OSMTEST_TOKEN_SLID: - p_path->comp.slid = 0xFFFF; - p_path->rec.slid = - cl_hton16( ( uint16_t ) strtoul( &line[offset], NULL, 0 ) ); - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_parse_path: " - "slid = 0x%X\n", cl_ntoh16( p_path->rec.slid ) ); - } - break; + p_tok = str_get_token( &line[offset] ); + if( p_tok == NULL ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_parse_link: ERR 012B: " + "Ignoring line %u with unknown token: %s\n", + *p_line_num, &line[offset] ); + got_error = TRUE; + continue; + } - case OSMTEST_TOKEN_PKEY: - p_path->comp.pkey = 0xFFFF; - p_path->rec.pkey = - cl_hton16( ( uint16_t ) strtoul( &line[offset], NULL, 0 ) ); - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_parse_path: " - "pkey = 0x%X\n", cl_ntoh16( p_path->rec.pkey ) ); - } - break; + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) + { + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_parse_link: " + "Found '%s' (line %u)\n", p_tok->str, *p_line_num ); + } - case OSMTEST_TOKEN_END: - done = TRUE; - break; + str_skip_token( line, &offset ); - default: - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_parse_path: ERR 00129: " - "Ignoring line %u with unknown token: %s\n", - *p_line_num, &line[offset] ); + switch ( p_tok->val ) + { + case OSMTEST_TOKEN_FROMLID: + case OSMTEST_TOKEN_FROMPORTNUM: + case OSMTEST_TOKEN_TOPORTNUM: + case OSMTEST_TOKEN_TOLID: + /* For now */ + break; - break; - } - } + case OSMTEST_TOKEN_END: + done = TRUE; + break; - /* - * Make sure the user specified enough information, then - * add this object to the database. - */ - if( osmtest_path_rec_kay_is_valid( p_osmt, p_path ) == FALSE ) - { - path_delete( p_path ); - goto Exit; + default: + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_parse_link: ERR 012C: " + "Ignoring line %u with unknown token: %s\n", + *p_line_num, &line[offset] ); + got_error = TRUE; + break; } + } - cl_qmap_insert( &p_osmt->exp_subn.path_tbl, - osmtest_path_rec_key_get( &p_path->rec ), - &p_path->map_item ); + if( got_error ) + status = IB_ERROR; Exit: OSM_LOG_EXIT( &p_osmt->log ); return ( status ); } - /********************************************************************** **********************************************************************/ static ib_api_status_t @@ -5782,83 +6987,93 @@ osmtest_create_db( IN osmtest_t * const p_osmt ) char line[OSMTEST_MAX_LINE_LEN]; uint32_t line_num = 0; const osmtest_token_t *p_tok; + boolean_t got_error = FALSE; OSM_LOG_ENTER( &p_osmt->log, osmtest_create_db ); fh = fopen( p_osmt->opt.file_name, "r" ); if( fh == NULL ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_create_db: ERR 00130: " - "Unable to open inventory file (%s)\n", p_osmt->opt.file_name); - status = IB_ERROR; - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_create_db: ERR 0130: " + "Unable to open inventory file (%s)\n", p_osmt->opt.file_name); + status = IB_ERROR; + goto Exit; + } /* * Parse the inventory file and create the database. */ while( fgets( line, OSMTEST_MAX_LINE_LEN, fh ) != NULL ) + { + line_num++; + + /* + * Skip whitespace + */ + offset = 0; + if( !str_skip_white( line, &offset ) ) + continue; /* whole line was whitespace */ + + p_tok = str_get_token( &line[offset] ); + if( p_tok == NULL ) { - line_num++; + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_create_db: ERR 0131: " + "Ignoring line %u: %s\n", line_num, &line[offset] ); + got_error = TRUE; + continue; + } - /* - * Skip whitespace - */ - offset = 0; - if( !str_skip_white( line, &offset ) ) - continue; /* whole line was whitespace */ + if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) + { + osm_log( &p_osmt->log, OSM_LOG_DEBUG, + "osmtest_create_db: " + "Found '%s' (line %u)\n", p_tok->str, line_num ); + } - p_tok = str_get_token( &line[offset] ); - if( p_tok == NULL ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_create_db: ERR 00131: " - "Ignoring line %u: %s\n", line_num, &line[offset] ); - continue; - } + switch ( p_tok->val ) + { + case OSMTEST_TOKEN_COMMENT: + break; - if( osm_log_is_active( &p_osmt->log, OSM_LOG_DEBUG ) ) - { - osm_log( &p_osmt->log, OSM_LOG_DEBUG, - "osmtest_create_db: " - "Found '%s' (line %u)\n", p_tok->str, line_num ); - } + case OSMTEST_TOKEN_DEFINE_NODE: + status = osmtest_parse_node( p_osmt, fh, &line_num ); + break; - switch ( p_tok->val ) - { - case OSMTEST_TOKEN_COMMENT: - break; + case OSMTEST_TOKEN_DEFINE_PORT: + status = osmtest_parse_port( p_osmt, fh, &line_num ); + break; - case OSMTEST_TOKEN_DEFINE_NODE: - status = osmtest_parse_node( p_osmt, fh, &line_num ); - break; + case OSMTEST_TOKEN_DEFINE_PATH: + status = osmtest_parse_path( p_osmt, fh, &line_num ); + break; - case OSMTEST_TOKEN_DEFINE_PORT: - status = osmtest_parse_port( p_osmt, fh, &line_num ); - break; + case OSMTEST_TOKEN_DEFINE_LINK: + status = osmtest_parse_link( p_osmt, fh, &line_num ); + break; - case OSMTEST_TOKEN_DEFINE_PATH: - status = osmtest_parse_path( p_osmt, fh, &line_num ); - break; + default: + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_create_db: ERR 0132: " + "Ignoring line %u: %s\n", line_num, &line[offset] ); + got_error = TRUE; + break; + } - default: - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_create_db: ERR 00132: " - "Ignoring line %u: %s\n", line_num, &line[offset] ); - break; - } + if( got_error ) + status = IB_ERROR; - if( status != IB_SUCCESS ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_create_db: ERR 00133: " - "Bad status received during parsing (%s)\n", - ib_get_err_str( status ) ); - fclose( fh ); - goto Exit; - } + if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_create_db: ERR 0133: " + "Bad status received during parsing (%s)\n", + ib_get_err_str( status ) ); + fclose( fh ); + goto Exit; } + } fclose( fh ); @@ -5888,29 +7103,29 @@ osmtest_get_user_port( IN osmtest_t * const p_osmt, */ while( done_flag == FALSE ) + { + printf( "\nChoose a local port number with which to bind:\n\n" ); + for( i = 0; i < num_ports; i++ ) { - printf( "\nChoose a local port number with which to bind:\n\n" ); - for( i = 0; i < num_ports; i++ ) - { - /* - * Print the index + 1 since by convention, port numbers - * start with 1 on host channel adapters. - */ + /* + * Print the index + 1 since by convention, port numbers + * start with 1 on host channel adapters. + */ - printf( "\t%u: GUID = 0x%8" PRIx64 ", lid = 0x%04X, state = %s\n", - i + 1, cl_ntoh64( p_attr_array[i].port_guid ), - p_attr_array[i].lid, - ib_get_port_state_str( p_attr_array[i].link_state ) ); - } + printf( "\t%u: GUID = 0x%8" PRIx64 ", lid = 0x%04X, state = %s\n", + i + 1, cl_ntoh64( p_attr_array[i].port_guid ), + p_attr_array[i].lid, + ib_get_port_state_str( p_attr_array[i].link_state ) ); + } - printf( "\nEnter choice (1-%u): ", i ); - scanf( "%u", &choice ); - if( choice > num_ports ) - printf( "\nError: Lame choice!\n" ); - else - done_flag = TRUE; + printf( "\nEnter choice (1-%u): ", i ); + scanf( "%u", &choice ); + if( choice > num_ports ) + printf( "\nError: Lame choice!\n" ); + else + done_flag = TRUE; - } + } printf("\n"); OSM_LOG_EXIT( &p_osmt->log ); return ( choice - 1 ); @@ -5937,75 +7152,73 @@ osmtest_bind( IN osmtest_t * p_osmt, status = osm_vendor_get_all_port_attr( p_osmt->p_vendor, attr_array, &num_ports ); if( status != IB_SUCCESS ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_bind: ERR 00134: " - "Failure getting local port attributes (%s)\n", - ib_get_err_str( status ) ); - goto Exit; - } + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_bind: ERR 0134: " + "Failure getting local port attributes (%s)\n", + ib_get_err_str( status ) ); + goto Exit; + } if( guid == 0 ) - { - /* - * User needs prompting for the local port GUID with which - * to bind. - */ - port_index = osmtest_get_user_port( p_osmt, attr_array, num_ports ); + { + /* + * User needs prompting for the local port GUID with which + * to bind. + */ + port_index = osmtest_get_user_port( p_osmt, attr_array, num_ports ); - if( num_ports == 0 ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_bind: ERR 00135: " - "No local ports. Unable to proceed\n", - ib_get_err_str( status ) ); - goto Exit; - } - guid = attr_array[port_index].port_guid; + if( num_ports == 0 ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_bind: ERR 0135: " + "No local ports. Unable to proceed\n" ); + goto Exit; } + guid = attr_array[port_index].port_guid; + } else + { + for( port_index = 0; port_index < num_ports; port_index++ ) { - for( port_index = 0; port_index < num_ports; port_index++ ) - { - if( attr_array[port_index].port_guid == guid ) - break; - } + if( attr_array[port_index].port_guid == guid ) + break; + } - if( port_index == num_ports ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_bind: ERR 00136: " - "No local port with guid 0x%016" PRIx64 "\n", - cl_ntoh64( guid ) ); - status = IB_NOT_FOUND; - goto Exit; - } + if( port_index == num_ports ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_bind: ERR 0136: " + "No local port with guid 0x%016" PRIx64 "\n", + cl_ntoh64( guid ) ); + status = IB_NOT_FOUND; + goto Exit; } + } /* * Copy the port info for the selected port. */ - cl_memcpy( &p_osmt->local_port, &attr_array[port_index], - sizeof( p_osmt->local_port ) ); + memcpy( &p_osmt->local_port, &attr_array[port_index], + sizeof( p_osmt->local_port ) ); /* bind to the SA */ osm_log( &p_osmt->log, OSM_LOG_DEBUG, "osmtest_bind: " - "Using port SM_LID:0x%04X\n", + "Using port with SM LID:0x%04X\n", p_osmt->local_port.sm_lid); p_osmt->max_lid = max_lid; - p_osmt->h_bind = - osmv_bind_sa(p_osmt->p_vendor, &p_osmt->mad_pool, guid); + p_osmt->h_bind = osmv_bind_sa(p_osmt->p_vendor, &p_osmt->mad_pool, guid); - if( p_osmt->h_bind == OSM_BIND_INVALID_HANDLE ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_bind: ERR 00137: " - "Unable to bind to SA\n" ); - status = IB_ERROR; - goto Exit; - } + if( p_osmt->h_bind == OSM_BIND_INVALID_HANDLE ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_bind: ERR 0137: " + "Unable to bind to SA\n" ); + status = IB_ERROR; + goto Exit; + } Exit: OSM_LOG_EXIT( &p_osmt->log ); @@ -6023,220 +7236,253 @@ osmtest_run( IN osmtest_t * const p_osmt ) status = osmtest_validate_sa_class_port_info(p_osmt); if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_run: ERR 0138: " + "Could not obtain SA ClassPortInfo (%s)\n", + ib_get_err_str( status ) ); + goto Exit; + } + + if( p_osmt->opt.flow == 1 ) + { + /* + * Creating an inventory file with all nodes, ports and paths + */ + status = osmtest_create_inventory_file( p_osmt ); + if( status != IB_SUCCESS ) { osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_run: ERR 00138: " - "Could not obtain SA ClassPortInfo (%s)\n", + "osmtest_run: ERR 0139: " + "Inventory file create failed (%s)\n", ib_get_err_str( status ) ); goto Exit; } - - if( p_osmt->opt.flow == 1 ) + } + else + { + if( p_osmt->opt.flow == 5 ) { - status = osmtest_create_inventory_file( p_osmt ); - if( status != IB_SUCCESS ) - { + /* + * Stress SA - flood the it with queries + */ + switch ( p_osmt->opt.stress ) + { + case 0: + case 1: /* small response SA query stress */ + status = osmtest_stress_small_rmpp( p_osmt ); + if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_run: ERR 0140: " + "Small RMPP stress test failed (%s)\n", + ib_get_err_str( status ) ); + goto Exit; + } + break; + case 2: /* large response SA query stress */ + status = osmtest_stress_large_rmpp( p_osmt ); + if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_run: ERR 0141: " + "Large RMPP stress test failed (%s)\n", + ib_get_err_str( status ) ); + goto Exit; + } + break; + case 3: /* large response Path Record SA query stress */ + status = osmtest_create_db( p_osmt ); + if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_run: ERR 0142: " + "Database creation failed (%s)\n", + ib_get_err_str( status ) ); + goto Exit; + } + + status = osmtest_stress_large_rmpp_pr( p_osmt ); + if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_run: ERR 0143: " + "Large RMPP stress test failed (%s)\n", + ib_get_err_str( status ) ); + goto Exit; + } + break; + default: osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_run: ERR 00139: " - "Inventory file create failed (%s)\n", - ib_get_err_str( status ) ); - goto Exit; - } + "osmtest_run: ERR 0144: " + "Unknown stress test value %u\n", + p_osmt->opt.stress ); + break; + } } - else + else { - if( p_osmt->opt.flow == 5 ) - { - switch ( p_osmt->opt.stress ) - { - case 0: - case 1: /* small response SA query stress */ - status = osmtest_stress_small_rmpp( p_osmt ); - if( status != IB_SUCCESS ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_run: ERR 00140: " - "Small RMPP stress test failed (%s)\n", - ib_get_err_str( status ) ); - goto Exit; - } - break; - case 2: /* large response SA query stress */ - status = osmtest_stress_large_rmpp( p_osmt ); - if( status != IB_SUCCESS ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_run: ERR 00141: " - "Large RMPP stress test failed (%s)\n", - ib_get_err_str( status ) ); - goto Exit; - } - break; - case 3: /* large response Path Record SA query stress */ - status = osmtest_create_db( p_osmt ); - if( status != IB_SUCCESS ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_run: ERR 00142: " - "Database creation failed (%s)\n", - ib_get_err_str( status ) ); - goto Exit; - } - - status = osmtest_stress_large_rmpp_pr( p_osmt ); - if( status != IB_SUCCESS ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_run: ERR 00143: " - "Large RMPP stress test failed (%s)\n", - ib_get_err_str( status ) ); - goto Exit; - } - break; - default: - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_run: ERR 00144: " - "Unknown stress test value %u\n", - p_osmt->opt.stress ); - break; - } - } - else - { - /* - * Run normal validition tests. + /* + * Run normal validition tests. + */ + if (p_osmt->opt.flow == 0 || p_osmt->opt.flow == 2) + { + /* + * Only validate the given inventory file + */ + status = osmtest_create_db( p_osmt ); + if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_run: ERR 0145: " + "Database creation failed (%s)\n", + ib_get_err_str( status ) ); + goto Exit; + } + + status = osmtest_validate_against_db( p_osmt ); + if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_run: ERR 0146: " + "SA validation database failure (%s)\n", + ib_get_err_str( status ) ); + goto Exit; + } + } + + if (p_osmt->opt.flow == 0) + { + status = osmtest_wrong_sm_key_ignored( p_osmt ); + if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_run: ERR 0147: " + "Try wrong SM_Key failed (%s)\n", + ib_get_err_str( status ) ); + goto Exit; + } + } + + if (p_osmt->opt.flow == 0 || p_osmt->opt.flow == 3) + { + /* + * run service registration, deregistration, and lease test + */ + status = osmt_run_service_records_flow( p_osmt ); + if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_run: ERR 0148: " + "Service Flow failed (%s)\n", + ib_get_err_str( status ) ); + goto Exit; + } + } + + if (p_osmt->opt.flow == 0 || p_osmt->opt.flow == 4) + { + /* + * Run event forwarding test */ - if (!p_osmt->opt.flow || p_osmt->opt.flow == 2) - { - status = osmtest_create_db( p_osmt ); - if( status != IB_SUCCESS ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_run: ERR 00145: " - "Database creation failed (%s)\n", - ib_get_err_str( status ) ); - goto Exit; - } - - status = osmtest_validate_against_db( p_osmt ); - if( status != IB_SUCCESS ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_run: ERR 00146: " - "SA validation database failure again (%s)\n", - ib_get_err_str( status ) ); - goto Exit; - } - } - - if (!p_osmt->opt.flow) - { - status = osmtest_wrong_sm_key_ignored( p_osmt ); - if( status != IB_SUCCESS ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_run: ERR 00147: " - "Try wrong SM_Key failed (%s)\n", - ib_get_err_str( status ) ); - goto Exit; - } - } - - if (!p_osmt->opt.flow || p_osmt->opt.flow == 3) - { - status = osmt_run_service_records_flow( p_osmt ); - if( status != IB_SUCCESS ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_run: ERR 00148: " - "Service Flow failed (%s)\n", - ib_get_err_str( status ) ); - goto Exit; - } - } - - if (!p_osmt->opt.flow || p_osmt->opt.flow == 4) - { #ifdef OSM_VENDOR_INTF_MTL - status = osmt_run_inform_info_flow( p_osmt ); - - if( status != IB_SUCCESS ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_run: ERR 00149: " - "Inform Info Flow failed: (%s)\n", - ib_get_err_str( status ) ); - goto Exit; - } + status = osmt_run_inform_info_flow( p_osmt ); + + if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_run: ERR 0149: " + "Inform Info Flow failed: (%s)\n", + ib_get_err_str( status ) ); + goto Exit; + } #else - osm_log (&p_osmt->log, OSM_LOG_INFO, - "osmtest_run: The event forwarding flow " - "is not implemented yet!\n"); - status = IB_SUCCESS; - goto Exit; + osm_log (&p_osmt->log, OSM_LOG_INFO, + "osmtest_run: The event forwarding flow " + "is not implemented yet!\n"); + status = IB_SUCCESS; + goto Exit; #endif - } + } - /* - * since it generate a huge file - we run it only + if (p_osmt->opt.flow == 7) + { + /* + * QoS info: dump VLArb and SLtoVL tables. + * Since it generates a huge file, we run it only * if explicitly required to */ - if (p_osmt->opt.flow == 7) - { - status = osmt_run_slvl_and_vlarb_records_flow(p_osmt); - if( status != IB_SUCCESS ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_run: ERR 00150: " - "Failed to get SLtoVL and VL Arbitration Tables (%s)\n", - ib_get_err_str( status ) ); - goto Exit; - } - } + status = osmtest_create_db( p_osmt ); + if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_run: ERR 014A: " + "Database creation failed (%s)\n", + ib_get_err_str( status ) ); + goto Exit; + } - if (p_osmt->opt.flow == 8) - { + status = osmt_run_slvl_and_vlarb_records_flow(p_osmt); + if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_run: ERR 0150: " + "Failed to get SLtoVL and VL Arbitration Tables (%s)\n", + ib_get_err_str( status ) ); + goto Exit; + } + } + + if (p_osmt->opt.flow == 8) + { + /* + * Run trap 64/65 flow (this flow requires running of external tool) + */ #ifdef OSM_VENDOR_INTF_MTL - status = osmt_run_trap64_65_flow( p_osmt ); - if( status != IB_SUCCESS ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_run: ERR 00151: " - "Trap 64/65 Flow failed: (%s)\n", - ib_get_err_str( status ) ); - goto Exit; - } + status = osmt_run_trap64_65_flow( p_osmt ); + if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_run: ERR 0151: " + "Trap 64/65 Flow failed: (%s)\n", + ib_get_err_str( status ) ); + goto Exit; + } #else - osm_log (&p_osmt->log, OSM_LOG_INFO, - "osmtest_run: The event forwarding flow " - "is not implemented yet!\n"); - status = IB_SUCCESS; - goto Exit; + osm_log (&p_osmt->log, OSM_LOG_INFO, + "osmtest_run: The event forwarding flow " + "is not implemented yet!\n"); + status = IB_SUCCESS; + goto Exit; #endif - } + } - if (!p_osmt->opt.flow || p_osmt->opt.flow == 6) - { - status = osmt_run_mcast_flow( p_osmt ); - if( status != IB_SUCCESS ) - { - osm_log( &p_osmt->log, OSM_LOG_ERROR, - "osmtest_run: ERR 00152: " - "Multicast Flow failed: (%s)\n", - ib_get_err_str( status ) ); - goto Exit; - } - } + if (p_osmt->opt.flow == 0 || p_osmt->opt.flow == 6) + { + /* + * Multicast flow + */ + status = osmt_run_mcast_flow( p_osmt ); + if( status != IB_SUCCESS ) + { + osm_log( &p_osmt->log, OSM_LOG_ERROR, + "osmtest_run: ERR 0152: " + "Multicast Flow failed: (%s)\n", + ib_get_err_str( status ) ); + goto Exit; + } + } - osm_log( &p_osmt->log, OSM_LOG_INFO, - "osmtest_run: " - "\n\n***************** ALL TESTS PASS *****************\n\n" ); + osm_log( &p_osmt->log, OSM_LOG_INFO, + "osmtest_run: " + "\n\n***************** ALL TESTS PASS *****************\n\n" ); - } - } + } + } Exit: OSM_LOG_EXIT( &p_osmt->log ); return ( status ); } + -- 2.41.0