xref: /trueos/contrib/ofed/management/libibmad/src/register.c (revision 8fe640108653f13042f1b15213769e338aa524f6)
1 /*
2  * Copyright (c) 2004,2005 Voltaire Inc.  All rights reserved.
3  *
4  * This software is available to you under a choice of one of two
5  * licenses.  You may choose to be licensed under the terms of the GNU
6  * General Public License (GPL) Version 2, available from the file
7  * COPYING in the main directory of this source tree, or the
8  * OpenIB.org BSD license below:
9  *
10  *     Redistribution and use in source and binary forms, with or
11  *     without modification, are permitted provided that the following
12  *     conditions are met:
13  *
14  *      - Redistributions of source code must retain the above
15  *        copyright notice, this list of conditions and the following
16  *        disclaimer.
17  *
18  *      - Redistributions in binary form must reproduce the above
19  *        copyright notice, this list of conditions and the following
20  *        disclaimer in the documentation and/or other materials
21  *        provided with the distribution.
22  *
23  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
24  * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
25  * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
26  * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
27  * BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
28  * ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
29  * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
30  * SOFTWARE.
31  *
32  */
33 
34 #if HAVE_CONFIG_H
35 #  include <config.h>
36 #endif /* HAVE_CONFIG_H */
37 
38 #include <stdio.h>
39 #include <stdlib.h>
40 #include <unistd.h>
41 #include <pthread.h>
42 #include <sys/time.h>
43 #include <string.h>
44 #include <errno.h>
45 
46 #include <infiniband/umad.h>
47 #include "mad.h"
48 
49 #undef DEBUG
50 #define DEBUG	if (ibdebug)	IBWARN
51 
52 #define MAX_CLASS	256
53 #define MAX_AGENTS	256
54 
55 static int class_agent[MAX_CLASS];
56 static int agent_class[MAX_AGENTS];
57 
58 static int
register_agent(int agent,int mclass)59 register_agent(int agent, int mclass)
60 {
61 	static int initialized;
62 
63 	if (!initialized) {
64 		initialized++;
65 		memset(class_agent, 0xff, sizeof class_agent);
66 		memset(agent_class, 0xff, sizeof agent_class);
67 	}
68 
69 	if (mclass < 0 || mclass >= MAX_CLASS ||
70 	    agent < 0 || agent >= MAX_AGENTS) {
71 		DEBUG("bad mgmt class %d or agent %d", mclass, agent);
72 		return -1;
73 	}
74 
75 	class_agent[mclass] = agent;
76 	agent_class[agent] = mclass;
77 
78 	return 0;
79 }
80 
81 static int
mgmt_class_vers(int mgmt_class)82 mgmt_class_vers(int mgmt_class)
83 {
84 	if ((mgmt_class >= IB_VENDOR_RANGE1_START_CLASS &&
85 	     mgmt_class <= IB_VENDOR_RANGE1_END_CLASS) ||
86 	    (mgmt_class >= IB_VENDOR_RANGE2_START_CLASS &&
87 	     mgmt_class <= IB_VENDOR_RANGE2_END_CLASS))
88 		return 1;
89 
90 	switch(mgmt_class) {
91 		case IB_SMI_CLASS:
92 		case IB_SMI_DIRECT_CLASS:
93 			return 1;
94 		case IB_SA_CLASS:
95 			return 2;
96 		case IB_PERFORMANCE_CLASS:
97 			return 1;
98 		case IB_DEVICE_MGMT_CLASS:
99 			return 1;
100 		case IB_CC_CLASS:
101 			return 2;
102 	}
103 
104 	return 0;
105 }
106 
107 int
mad_class_agent(int mgmt)108 mad_class_agent(int mgmt)
109 {
110 	if (mgmt < 1 || mgmt > MAX_CLASS)
111 		return -1;
112 	return class_agent[mgmt];
113 }
114 
115 int
mad_agent_class(int agent)116 mad_agent_class(int agent)
117 {
118 	if (agent < 1 || agent > MAX_AGENTS)
119 		return -1;
120 	return agent_class[agent];
121 }
122 
123 int
mad_register_port_client(int port_id,int mgmt,uint8_t rmpp_version)124 mad_register_port_client(int port_id, int mgmt, uint8_t rmpp_version)
125 {
126 	int vers, agent;
127 
128 	if ((vers = mgmt_class_vers(mgmt)) <= 0) {
129 		DEBUG("Unknown class %d mgmt_class", mgmt);
130 		return -1;
131 	}
132 	if ((agent = umad_register(port_id, mgmt,
133 				   vers, rmpp_version, 0)) < 0) {
134 		DEBUG("Can't register agent for class %d", mgmt);
135 		return -1;
136 	}
137 
138 	if (mgmt < 0 || mgmt >= MAX_CLASS || agent >= MAX_AGENTS) {
139 		DEBUG("bad mgmt class %d or agent %d", mgmt, agent);
140 		return -1;
141 	}
142 
143 	return agent;
144 }
145 
146 int
mad_register_client(int mgmt,uint8_t rmpp_version)147 mad_register_client(int mgmt, uint8_t rmpp_version)
148 {
149 	int agent;
150 
151 	agent = mad_register_port_client(madrpc_portid(), mgmt, rmpp_version);
152 	if (agent < 0)
153 		return agent;
154 
155 	return register_agent(agent, mgmt);
156 }
157 
158 int
mad_register_server(int mgmt,uint8_t rmpp_version,long method_mask[],uint32_t class_oui)159 mad_register_server(int mgmt, uint8_t rmpp_version,
160 		    long method_mask[], uint32_t class_oui)
161 {
162 	long class_method_mask[16/sizeof(long)];
163 	uint8_t oui[3];
164 	int agent, vers, mad_portid;
165 
166 	if (method_mask)
167 		memcpy(class_method_mask, method_mask, sizeof class_method_mask);
168 	else
169 		memset(class_method_mask, 0xff, sizeof(class_method_mask));
170 
171 	if ((mad_portid = madrpc_portid()) < 0)
172 		return -1;
173 
174 	if (class_agent[mgmt] >= 0) {
175 		DEBUG("Class 0x%x already registered", mgmt);
176 		return -1;
177 	}
178 	if ((vers = mgmt_class_vers(mgmt)) <= 0) {
179 		DEBUG("Unknown class 0x%x mgmt_class", mgmt);
180 		return -1;
181 	}
182 	if (mgmt >= IB_VENDOR_RANGE2_START_CLASS &&
183 	    mgmt <= IB_VENDOR_RANGE2_END_CLASS) {
184 		oui[0] = (class_oui >> 16) & 0xff;
185 		oui[1] = (class_oui >> 8) & 0xff;
186 		oui[2] = class_oui & 0xff;
187 		if ((agent = umad_register_oui(mad_portid, mgmt, rmpp_version,
188 					       oui, class_method_mask)) < 0) {
189 			DEBUG("Can't register agent for class %d", mgmt);
190 			return -1;
191 		}
192 	} else if ((agent = umad_register(mad_portid, mgmt, vers, rmpp_version,
193 					  class_method_mask)) < 0) {
194 		DEBUG("Can't register agent for class %d", mgmt);
195 		return -1;
196 	}
197 
198 	if (register_agent(agent, mgmt) < 0)
199 		return -1;
200 
201 	return agent;
202 }
203