[openib-general] [PATCH] Update to new process_mad API

Roland Dreier roland at topspin.com
Mon Sep 13 20:22:57 PDT 2004


This updates my branch to the new API for process_mad.  I still need
to fix up the definition of struct ib_mad in ts_ib_mad_types.h (will
be done shortly).

 - R.

Index: infiniband/include/ib_verbs.h
===================================================================
--- infiniband/include/ib_verbs.h	(revision 803)
+++ infiniband/include/ib_verbs.h	(working copy)
@@ -636,6 +636,19 @@
 	u32			rkey;
 };
 
+struct ib_mad;
+
+enum ib_process_mad_flags {
+	IB_MAD_IGNORE_MKEY	= 1
+};
+
+enum ib_mad_result {
+	IB_MAD_RESULT_FAILURE  = 0,      /* (!SUCCESS is the important flag) */
+	IB_MAD_RESULT_SUCCESS  = 1 << 0, /* MAD was successfully processed   */
+	IB_MAD_RESULT_REPLY    = 1 << 1, /* Reply packet needs to be sent    */
+	IB_MAD_RESULT_CONSUMED = 1 << 2  /* Packet consumed: stop processing */
+};
+
 #define IB_DEVICE_NAME_MAX 64
 
 struct ib_device {
@@ -743,7 +756,12 @@
 	int                        (*detach_mcast)(struct ib_qp *qp,
 						   union ib_gid *gid,
 						   u16 lid);
-	ib_mad_process_func          mad_process;
+	int                        (*process_mad)(struct ib_device *device,
+						  int process_mad_flags,
+						  u8 port_num,
+						  u16 source_lid,
+						  struct ib_mad *in_mad,
+						  struct ib_mad *out_mad);
 
 	struct class_device          class_dev;
 	struct kobject               ports_parent;
Index: infiniband/include/ib_mad.h
===================================================================
--- infiniband/include/ib_mad.h	(revision 0)
+++ infiniband/include/ib_mad.h	(revision 0)
@@ -0,0 +1,293 @@
+/*
+ * This software is available to you under a choice of one of two
+ * licenses.  You may choose to be licensed under the terms of the GNU
+ * General Public License (GPL) Version 2, available at
+ * <http://www.fsf.org/copyleft/gpl.html>, or the OpenIB.org BSD
+ * license, available in the LICENSE.TXT file accompanying this
+ * software.  These details are also available at
+ * <http://openib.org/license.html>.
+ *
+ * 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.
+ *
+ * Copyright (c) 2004 Mellanox Technologies Ltd.  All rights reserved.
+ * Copyright (c) 2004 Infinicon Corporation.  All rights reserved.
+ * Copyright (c) 2004 Intel Corporation.  All rights reserved.
+ * Copyright (c) 2004 Topspin Corporation.  All rights reserved.
+ * Copyright (c) 2004 Voltaire Corporation.  All rights reserved.
+ *
+ * $Id$
+ */
+
+#if !defined( IB_MAD_H )
+#define IB_MAD_H
+
+#include <ib_verbs.h>
+
+/* Management classes */
+#define IB_MGMT_CLASS_SUBN_LID_ROUTED		0x01
+#define IB_MGMT_CLASS_SUBN_DIRECTED_ROUTE	0x81
+#define IB_MGMT_CLASS_SUBN_ADM			0x03
+#define IB_MGMT_CLASS_PERF_MGMT			0x04
+#define IB_MGMT_CLASS_BM			0x05
+#define IB_MGMT_CLASS_DEVICE_MGMT		0x06
+#define IB_MGMT_CLASS_CM			0x07
+#define IB_MGMT_CLASS_SNMP			0x08
+
+/* Management methods */
+#define IB_MGMT_METHOD_GET			0x01
+#define IB_MGMT_METHOD_SET			0x02
+#define IB_MGMT_METHOD_GET_RESP			0x81
+#define IB_MGMT_METHOD_SEND			0x03
+#define IB_MGMT_METHOD_TRAP			0x05
+#define IB_MGMT_METHOD_REPORT			0x06
+#define IB_MGMT_METHOD_REPORT_RESP		0x86
+#define IB_MGMT_METHOD_TRAP_REPRESS		0x07
+
+#define IB_MGMT_METHOD_RESP			0x80
+
+
+#define IB_MGMT_MAX_METHODS			128
+
+#define IB_QP0		0
+#define IB_QP1		cpu_to_be32(1)
+#define IB_QP1_QKEY	cpu_to_be32(0x80010000)
+
+struct ib_grh {
+	u32		version_tclass_flow;
+	u16		paylen;
+	u8		next_hdr;
+	u8		hop_limit;
+	union ib_gid	sgid;
+	union ib_gid	dgid;
+} __attribute__ ((packed));
+
+struct ib_mad_hdr {
+	u8	base_version;
+	u8	mgmt_class;
+	u8	class_version;
+	u8	method;
+	u16	status;
+	u16	class_specific;
+	u64	tid;
+	u16	attr_id;
+	u16	resv;
+	u32	attr_mod;
+};
+
+struct ib_rmpp_hdr {
+	u8	rmpp_version;
+	u8	rmpp_type;
+	u8	rmpp_rtime_flags;
+	u8	rmpp_status;
+	u32	seg_num;
+	u32	paylen_newwin;
+};
+
+struct ib_mad {
+	struct ib_mad_hdr	mad_hdr;
+	u8			data[232];
+};
+
+struct ib_rmpp_mad {
+	struct ib_mad_hdr	mad_hdr;
+	struct ib_rmpp_hdr	rmpp_hdr;
+	u8			data[220];
+};
+
+struct ib_mad_agent;
+struct ib_mad_send_wc;
+struct ib_mad_recv_wc;
+
+/**
+ * ib_mad_send_handler - callback handler for a sent MAD.
+ * @mad_agent - MAD agent that sent the MAD.
+ * @mad_send_wc - Send work completion information on the sent MAD.
+ */
+typedef void (*ib_mad_send_handler)(struct ib_mad_agent *mad_agent,
+				    struct ib_mad_send_wc *mad_send_wc);
+
+/**
+ * ib_mad_recv_handler - callback handler for a received MAD.
+ * @mad_agent - MAD agent requesting the received MAD.
+ * @mad_recv_wc - Received work completion information on the received MAD.
+ *
+ * MADs received in response to a send request operation will be handed to
+ * the user after the send operation completes.  All data buffers given
+ * to the user through this routine are owned by the receiving client.
+ */
+typedef void (*ib_mad_recv_handler)(struct ib_mad_agent *mad_agent,
+				    struct ib_mad_recv_wc *mad_recv_wc);
+
+/**
+ * ib_mad_agent - Used to track MAD registration with the access layer.
+ * @device - Reference to device registration is on.
+ * @qp - Reference to QP used for sending and receiving MADs.
+ * @recv_handler - Callback handler for a received MAD.
+ * @send_handler - Callback handler for a sent MAD.
+ * @context - User-specified context associated with this registration.
+ * @hi_tid - Access layer assigned transaction ID for this client.
+ *   Unsolicited MADs sent by this client will have the upper 32-bits
+ *   of their TID set to this value.
+ */
+struct ib_mad_agent {
+	struct ib_device	*device;
+	struct ib_qp		*qp;
+	ib_mad_recv_handler	recv_handler;
+	ib_mad_send_handler	send_handler;
+	void			*context;
+	u32			hi_tid;
+};
+
+/**
+ * ib_mad_send_wc - MAD send completion information.
+ * @wr_id - Work request identifier associated with the send MAD request.
+ * @status - Completion status.
+ * @vendor_err - Optional vendor error information returned with a failed
+ *   request.
+ */
+struct ib_mad_send_wc {
+	u64			wr_id;
+	enum ib_wc_status	status;
+	u32			vendor_err;
+};
+
+/**
+ * ib_mad_recv_buf - received MAD buffer information.
+ * @list - Reference to next data buffer for a received RMPP MAD.
+ * @grh - References a data buffer containing the global route header.
+ *   The data refereced by this buffer is only valid if the GRH is
+ *   valid.
+ * @mad - References the start of the received MAD.
+ */
+struct ib_mad_recv_buf {
+	struct list_head	list;
+	struct ib_grh		*grh;
+	struct ib_mad		*mad;
+};
+
+/**
+ * ib_mad_recv_wc - received MAD information.
+ * @wc - Completion information for the received data.
+ * @recv_buf - Specifies the location of the received data buffer(s).
+ * @mad_len - The length of the received MAD, without duplicated headers.
+ *
+ * For received response, the wr_id field of the wc is set to the wr_id
+ *   for the corresponding send request.
+ */
+struct ib_mad_recv_wc {
+	struct ib_wc		*wc;
+	struct ib_mad_recv_buf	*recv_buf;
+	int			mad_len;
+};
+
+/**
+ * ib_mad_reg_req - MAD registration request
+ * @mgmt_class - Indicates which management class of MADs should be receive
+ *   by the caller.  This field is only required if the user wishes to
+ *   receive unsolicited MADs, otherwise it should be 0.
+ * @mgmt_class_version - Indicates which version of MADs for the given
+ *   management class to receive.
+ * @method_mask - The caller will receive unsolicited MADs for any method
+ *   where @method_mask = 1.
+ */
+struct ib_mad_reg_req {
+	u8	mgmt_class;
+	u8	mgmt_class_version;
+	DECLARE_BITMAP(method_mask, IB_MGMT_MAX_METHODS);
+};
+
+/**
+ * ib_register_mad_agent - Register to send/receive MADs.
+ * @device - The device to register with.
+ * @port - The port on the specified device to use.
+ * @qp_type - Specifies which QP to access.  Must be either
+ *   IB_QPT_SMI or IB_QPT_GSI.
+ * @mad_reg_req - Specifies which unsolicited MADs should be received
+ *   by the caller.  This parameter may be NULL if the caller only
+ *   wishes to receive solicited responses.
+ * @rmpp_version - If set, indicates that the client will send
+ *   and receive MADs that contain the RMPP header for the given version.
+ *   If set to 0, indicates that RMPP is not used by this client.
+ * @send_handler - The completion callback routine invoked after a send
+ *   request has completed.
+ * @recv_handler - The completion callback routine invoked for a received
+ *   MAD.
+ * @context - User specified context associated with the registration.
+ */
+struct ib_mad_agent *ib_register_mad_agent(struct ib_device *device,
+					   u8 port,
+					   enum ib_qp_type qp_type,
+					   struct ib_mad_reg_req *mad_reg_req,
+					   u8 rmpp_version,
+					   ib_mad_send_handler send_handler,
+					   ib_mad_recv_handler recv_handler,
+					   void *context);
+
+/**
+ * ib_unregister_mad_agent - Unregisters a client from using MAD services.
+ * @mad_agent - Corresponding MAD registration request to deregister.
+ *
+ * After invoking this routine, MAD services are no longer usable by the
+ * client on the associated QP.
+ */
+int ib_unregister_mad_agent(struct ib_mad_agent *mad_agent);
+
+/**
+ * ib_post_send_mad - Posts MAD(s) to the send queue of the QP associated
+ *   with the registered client.
+ * @mad_agent - Specifies the associated registration to post the send to.
+ * @send_wr - Specifies the information needed to send the MAD(s).
+ * @bad_send_wr - Specifies the MAD on which an error was encountered.
+ */
+int ib_post_send_mad(struct ib_mad_agent *mad_agent,
+		     struct ib_send_wr *send_wr,
+		     struct ib_send_wr **bad_send_wr);
+
+/**
+ * ib_redirect_mad_qp - Registers a QP for MAD services.
+ * @qp - Reference to a QP that requires MAD services.
+ * @rmpp_version - If set, indicates that the client will send
+ *   and receive MADs that contain the RMPP header for the given version.
+ *   If set to 0, indicates that RMPP is not used by this client.
+ * @send_handler - The completion callback routine invoked after a send
+ *   request has completed.
+ * @recv_handler - The completion callback routine invoked for a received
+ *   MAD.
+ * @context - User specified context associated with the registration.
+ *
+ * Use of this call allows clients to use MAD services, such as RMPP,
+ * on user-owned QPs.  After calling this routine, users may send
+ * MADs on the specified QP by calling ib_mad_post_send.
+ */
+struct ib_mad_agent *ib_redirect_mad_qp(struct ib_qp *qp,
+					u8 rmpp_version,
+					ib_mad_send_handler send_handler,
+					ib_mad_recv_handler recv_handler,
+					void *context);
+
+/**
+ * ib_process_mad_wc - Processes a work completion associated with a
+ *   MAD sent or received on a redirected QP.
+ * @mad_agent - Specifies the registered MAD service using the redirected QP.
+ * @wc - References a work completion associated with a sent or received
+ *   MAD segment.
+ *
+ * This routine is used to complete or continue processing on a MAD request.
+ * If the work completion is associated with a send operation, calling
+ * this routine is required to continue an RMPP transfer or to wait for a
+ * corresponding response, if it is a request.  If the work completion is
+ * associated with a receive operation, calling this routine is required to
+ * process an inbound or outbound RMPP transfer, or to match a response MAD
+ * with its corresponding request.
+ */
+int ib_process_mad_wc(struct ib_mad_agent *mad_agent,
+		      struct ib_wc *wc);
+
+#endif /* IB_MAD_H */
Index: infiniband/include/ts_ib_core_types.h
===================================================================
--- infiniband/include/ts_ib_core_types.h	(revision 803)
+++ infiniband/include/ts_ib_core_types.h	(working copy)
@@ -90,20 +90,6 @@
 	u8         lmc;
 };
 
-struct ib_mad;
-
-enum ib_mad_result {
-	IB_MAD_RESULT_FAILURE      = 0,        // (!SUCCESS is the important flag)
-	IB_MAD_RESULT_SUCCESS      = 1 << 0,   // MAD was successfully processed
-	IB_MAD_RESULT_REPLY        = 1 << 1,   // Reply packet needs to be sent
-	IB_MAD_RESULT_CONSUMED     = 1 << 2    // Packet consumed: stop processing
-};
-
-typedef enum ib_mad_result (*ib_mad_process_func)(struct ib_device *device,
-						  int               ignore_mkey,
-						  struct ib_mad    *in_mad,
-						  struct ib_mad    *response_mad);
-
 /* structures */
 
 enum {
Index: infiniband/core/mad_thread.c
===================================================================
--- infiniband/core/mad_thread.c	(revision 803)
+++ infiniband/core/mad_thread.c	(working copy)
@@ -58,7 +58,7 @@
 		/* If this is an outgoing 0-hop SMP, we have a
 		   mad_process method and the provider hasn't told use
 		   to use QP0 for this, just process the MAD directly. */
-		if (device->mad_process &&
+		if (device->process_mad &&
 		    !(device->flags & IB_MAD_LOCAL_USE_QP) &&
 		    !mad->route.directed.hop_count) {
 			void *response_buf = kmalloc(sizeof (struct ib_mad) +
@@ -85,7 +85,8 @@
 
 			work->type   = IB_MAD_WORK_SEND_DONE;
 			work->index  = -1;
-			result = device->mad_process(device, 0, mad, response);
+			result = device->process_mad(device, 0, mad->port, mad->slid,
+						     mad, response);
 
 			*reuse = 1;
 
Index: infiniband/core/useraccess_ioctl.c
===================================================================
--- infiniband/core/useraccess_ioctl.c	(revision 803)
+++ infiniband/core/useraccess_ioctl.c	(working copy)
@@ -26,14 +26,6 @@
 #include <ib_verbs.h>
 #include "ts_ib_mad.h"
 
-/*
-  We include ts_ib_provider_types.h so that we can access the
-  mad_process member of a device struct.  This is sort of an ugly
-  violation of our layering (since the useraccess module should
-  probably only use devices through device handles) but seems like the
-  least bad solution.
-*/
-
 #include "ts_kernel_trace.h"
 #include "ts_kernel_services.h"
 
@@ -206,9 +198,8 @@
 	/* Here's the ugly layering violation mentioned above: */
 	struct ib_device *device = priv->device->ib_device;
 
-	if (!device->mad_process) {
+	if (!device->process_mad)
 		return -ENOSYS;
-	}
 
 	mad = kmalloc(2 * sizeof *mad, GFP_KERNEL);
 	if (!mad) {
@@ -221,7 +212,7 @@
 	}
 	mad->device = priv->device->ib_device;
 
-	result = device->mad_process(device, 1, mad, mad + 1);
+	result = device->process_mad(device, 1, mad->port, mad->slid, mad, mad + 1);
 
 	if (copy_to_user
 	    ((void *)arg + TS_USER_MAD_SIZE, &result, sizeof result)) {
Index: infiniband/core/mad_filter.c
===================================================================
--- infiniband/core/mad_filter.c	(revision 803)
+++ infiniband/core/mad_filter.c	(working copy)
@@ -284,7 +284,8 @@
 	    !ib_mad_validate_dr_smp(mad, device))
 		ret = IB_MAD_RESULT_SUCCESS; // As if device ignored packet.
 	else
-		ret = device->mad_process(device, 0, mad, response);
+		ret = device->process_mad(device, 0, mad->port, mad->slid,
+					  mad, response);
 
 	if (!(ret & IB_MAD_RESULT_SUCCESS))
 		TS_REPORT_WARN(MOD_KERNEL_IB,
Index: infiniband/core/mad_static.c
===================================================================
--- infiniband/core/mad_static.c	(revision 803)
+++ infiniband/core/mad_static.c	(working copy)
@@ -104,13 +104,11 @@
 {
 	struct ib_mad *mad_in, *mad_out;
 
-	if (!device->mad_process) {
+	if (!device->process_mad)
 		return;
-	}
 
-	if (!lid_base) {
+	if (!lid_base)
 		ib_mad_static_compute_base();
-	}
 
 	mad_in = kmem_cache_alloc(mad_cache, GFP_KERNEL);
 	if (!mad_in) {
@@ -133,14 +131,12 @@
 	mad_in->class_version  = 1;
 	mad_in->r_method       = IB_MGMT_METHOD_GET;
 	mad_in->attribute_id   = cpu_to_be16(IB_SMP_ATTRIB_PORT_INFO);
-	mad_in->port           = port;
-	mad_in->slid           = 0xffff;
 
 	/* Request port info from the device */
-	if ((device->mad_process(device, 1, mad_in, mad_out) &
+	if ((device->process_mad(device, IB_MAD_IGNORE_MKEY, port, 0xffff, mad_in, mad_out) &
 	     (IB_MAD_RESULT_SUCCESS | IB_MAD_RESULT_REPLY)) !=
 	    (IB_MAD_RESULT_SUCCESS | IB_MAD_RESULT_REPLY)) {
-		TS_REPORT_FATAL(MOD_KERNEL_IB, "%s: mad_process failed for port %d",
+		TS_REPORT_FATAL(MOD_KERNEL_IB, "%s: process_mad failed for port %d",
 				device->name, port);
 		return;
 	}
@@ -149,13 +145,11 @@
 	ib_smp_port_info_lid_set(IB_MAD_TO_SMP_DATA(mad_out), lid_base);
 	++lid_base;
 	mad_out->r_method = IB_MGMT_METHOD_SET;
-	mad_out->port     = port;
-	mad_out->slid     = 0xffff;
 
 	/* Update the port info on the device */
-	if (!(device->mad_process(device, 1, mad_out, mad_in) &
+	if (!(device->process_mad(device, IB_MAD_IGNORE_MKEY, port, 0xffff, mad_out, mad_in) &
 	      IB_MAD_RESULT_SUCCESS)) {
-		TS_REPORT_FATAL(MOD_KERNEL_IB, "%s: mad_process failed for port %d",
+		TS_REPORT_FATAL(MOD_KERNEL_IB, "%s: process_mad failed for port %d",
 				device->name, port);
 		return;
 	}
Index: infiniband/hw/mthca/mthca_dev.h
===================================================================
--- infiniband/hw/mthca/mthca_dev.h	(revision 803)
+++ infiniband/hw/mthca/mthca_dev.h	(working copy)
@@ -346,10 +346,12 @@
 int mthca_multicast_attach(struct ib_qp *ibqp, union ib_gid *gid, u16 lid);
 int mthca_multicast_detach(struct ib_qp *ibqp, union ib_gid *gid, u16 lid);
 
-enum ib_mad_result mthca_process_mad(struct ib_device *ibdev,
-                                     int               ignore_mkey,
-                                     struct ib_mad    *in_mad,
-                                     struct ib_mad    *response_mad);
+int mthca_process_mad(struct ib_device *ibdev,
+		      int mad_flags,
+		      u8 port_num,
+		      u16 slid,
+		      struct ib_mad *in_mad,
+		      struct ib_mad *out_mad);
 
 static inline struct mthca_dev *to_mdev(struct ib_device *ibdev)
 {
Index: infiniband/hw/mthca/mthca_provider.c
===================================================================
--- infiniband/hw/mthca/mthca_provider.c	(revision 803)
+++ infiniband/hw/mthca/mthca_provider.c	(working copy)
@@ -582,7 +582,7 @@
 	dev->ib_dev.dereg_mr             = mthca_dereg_mr;
 	dev->ib_dev.attach_mcast         = mthca_multicast_attach;
 	dev->ib_dev.detach_mcast         = mthca_multicast_detach;
-	dev->ib_dev.mad_process          = mthca_process_mad;
+	dev->ib_dev.process_mad          = mthca_process_mad;
 
 	ret = ib_register_device(&dev->ib_dev);
 	if (ret)
Index: infiniband/hw/mthca/mthca_mad.c
===================================================================
--- infiniband/hw/mthca/mthca_mad.c	(revision 803)
+++ infiniband/hw/mthca/mthca_mad.c	(working copy)
@@ -44,7 +44,8 @@
  * synthesize LID change and P_Key change events.
  */
 static void smp_snoop(struct ib_device *ibdev,
-                      struct ib_mad *mad)
+                      struct ib_mad *mad,
+		      u8 port_num)
 {
 	struct ib_event event;
 
@@ -55,35 +56,36 @@
 		if (mad->attribute_id == cpu_to_be16(IB_SM_PORT_INFO)) {
 			event.device           = ibdev;
 			event.event            = IB_EVENT_LID_CHANGE;
-			event.element.port_num = mad->port;
+			event.element.port_num = port_num;
 			ib_dispatch_event(&event);
 		}
 
 		if (mad->attribute_id == cpu_to_be16(IB_SM_PKEY_TABLE)) {
 			event.device           = ibdev;
 			event.event            = IB_EVENT_PKEY_CHANGE;
-			event.element.port_num = mad->port;
+			event.element.port_num = port_num;
 			ib_dispatch_event(&event);
 		}
 	}
 }
 
-enum ib_mad_result mthca_process_mad(struct ib_device *ibdev,
-                                     int               ignore_mkey,
-                                     struct ib_mad    *in_mad,
-                                     struct ib_mad    *response_mad)
+int mthca_process_mad(struct ib_device *ibdev,
+		      int mad_flags,
+		      u8 port_num,
+		      u16 slid,
+		      struct ib_mad *in_mad,
+		      struct ib_mad *out_mad)
 {
 	int err;
 	u8 status;
 
 	/* Forward locally generated traps to the SM */
-	if (in_mad->dqpn       == 0                                &&
-	    in_mad->mgmt_class == IB_MGMT_CLASS_SUBN_LID_ROUTED &&
+	if (in_mad->mgmt_class == IB_MGMT_CLASS_SUBN_LID_ROUTED &&
 	    in_mad->r_method   == IB_MGMT_METHOD_TRAP           &&
-	    in_mad->slid       == 0) {
+	    slid               == 0) {
 		struct ib_sm_path sm_path;
 
-		ib_cached_sm_path_get(ibdev, in_mad->port, &sm_path);
+		ib_cached_sm_path_get(ibdev, port_num, &sm_path);
 		if (sm_path.sm_lid) {
 			in_mad->sqpn            = 0;
 			in_mad->dlid            = sm_path.sm_lid;
@@ -94,13 +96,17 @@
 		return IB_MAD_RESULT_SUCCESS | IB_MAD_RESULT_CONSUMED;
 	}
 
-	/* Only handle SM gets, sets and trap represses for QP0 */
-	if (in_mad->dqpn == 0) {
-		if ((in_mad->mgmt_class != IB_MGMT_CLASS_SUBN_LID_ROUTED &&
-		     in_mad->mgmt_class != IB_MGMT_CLASS_SUBN_DIRECTED_ROUTE) ||
-		    (in_mad->r_method   != IB_MGMT_METHOD_GET &&
-		     in_mad->r_method   != IB_MGMT_METHOD_SET &&
-		     in_mad->r_method   != IB_MGMT_METHOD_TRAP_REPRESS))
+	/*
+	 * Only handle SM gets, sets and trap represses for SM class
+	 *
+	 * Only handle PMA and Mellanox vendor-specific class gets and
+	 * sets for other classes.
+	 */
+	if (in_mad->mgmt_class == IB_MGMT_CLASS_SUBN_LID_ROUTED || 
+	    in_mad->mgmt_class == IB_MGMT_CLASS_SUBN_DIRECTED_ROUTE) {
+		if (in_mad->r_method   != IB_MGMT_METHOD_GET &&
+		    in_mad->r_method   != IB_MGMT_METHOD_SET &&
+		    in_mad->r_method   != IB_MGMT_METHOD_TRAP_REPRESS)
 			return IB_MAD_RESULT_SUCCESS;
 
 		/* 
@@ -110,22 +116,18 @@
 		if (be16_to_cpu(in_mad->attribute_id) == IB_SM_SM_INFO ||
 		    be16_to_cpu(in_mad->attribute_id) >= IB_SM_VENDOR_START)
 			return IB_MAD_RESULT_SUCCESS;
-	}
-
-	/* 
-	 * Only handle PMA and Mellanox vendor-specific class gets and
-	 * sets on QP1
-	 */
-	if (in_mad->dqpn == 1 &&
-	    ((in_mad->mgmt_class != IB_MGMT_CLASS_PERF &&
-	      in_mad->mgmt_class != MTHCA_VENDOR_CLASS1   &&
-	      in_mad->mgmt_class != MTHCA_VENDOR_CLASS2) ||
-	     (in_mad->r_method  != IB_MGMT_METHOD_GET &&
-	      in_mad->r_method  != IB_MGMT_METHOD_SET)))
+	} else if (in_mad->mgmt_class == IB_MGMT_CLASS_PERF  ||
+		   in_mad->mgmt_class == MTHCA_VENDOR_CLASS1 || 
+		   in_mad->mgmt_class == MTHCA_VENDOR_CLASS2) {
+		if (in_mad->r_method  != IB_MGMT_METHOD_GET &&
+		    in_mad->r_method  != IB_MGMT_METHOD_SET)
+			return IB_MAD_RESULT_SUCCESS;
+	} else
 		return IB_MAD_RESULT_SUCCESS;
 
-	err = mthca_MAD_IFC(to_mdev(ibdev), ignore_mkey,
-			    in_mad->port, in_mad, response_mad,
+	err = mthca_MAD_IFC(to_mdev(ibdev),
+			    !!(mad_flags & IB_MAD_IGNORE_MKEY),
+			    port_num, in_mad, out_mad,
 			    &status);
 	if (err) {
 		mthca_err(to_mdev(ibdev), "MAD_IFC failed\n");
@@ -139,11 +141,11 @@
 		return IB_MAD_RESULT_FAILURE;
 	}
 
-	smp_snoop(ibdev, in_mad);
+	smp_snoop(ibdev, in_mad, port_num);
 
 	/* set return bit in status of directed route responses */
 	if (in_mad->mgmt_class == IB_MGMT_CLASS_SUBN_DIRECTED_ROUTE)
-		response_mad->status |= cpu_to_be16(1 << 15);
+		out_mad->status |= cpu_to_be16(1 << 15);
 
 	if (in_mad->r_method == IB_MGMT_METHOD_TRAP_REPRESS)
 		/* no response for trap repress */



More information about the general mailing list