1d6b92ffaSHans Petter Selasky /*
2d6b92ffaSHans Petter Selasky * Copyright (c) 2004-2009 Voltaire Inc. All rights reserved.
3d6b92ffaSHans Petter Selasky * Copyright (c) 2010,2011 Mellanox Technologies LTD. All rights reserved.
4d6b92ffaSHans Petter Selasky * Copyright (c) 2011,2016 Oracle and/or its affiliates. All rights reserved.
5d6b92ffaSHans Petter Selasky *
6d6b92ffaSHans Petter Selasky * This software is available to you under a choice of one of two
7d6b92ffaSHans Petter Selasky * licenses. You may choose to be licensed under the terms of the GNU
8d6b92ffaSHans Petter Selasky * General Public License (GPL) Version 2, available from the file
9d6b92ffaSHans Petter Selasky * COPYING in the main directory of this source tree, or the
10d6b92ffaSHans Petter Selasky * OpenIB.org BSD license below:
11d6b92ffaSHans Petter Selasky *
12d6b92ffaSHans Petter Selasky * Redistribution and use in source and binary forms, with or
13d6b92ffaSHans Petter Selasky * without modification, are permitted provided that the following
14d6b92ffaSHans Petter Selasky * conditions are met:
15d6b92ffaSHans Petter Selasky *
16d6b92ffaSHans Petter Selasky * - Redistributions of source code must retain the above
17d6b92ffaSHans Petter Selasky * copyright notice, this list of conditions and the following
18d6b92ffaSHans Petter Selasky * disclaimer.
19d6b92ffaSHans Petter Selasky *
20d6b92ffaSHans Petter Selasky * - Redistributions in binary form must reproduce the above
21d6b92ffaSHans Petter Selasky * copyright notice, this list of conditions and the following
22d6b92ffaSHans Petter Selasky * disclaimer in the documentation and/or other materials
23d6b92ffaSHans Petter Selasky * provided with the distribution.
24d6b92ffaSHans Petter Selasky *
25d6b92ffaSHans Petter Selasky * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
26d6b92ffaSHans Petter Selasky * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
27d6b92ffaSHans Petter Selasky * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
28d6b92ffaSHans Petter Selasky * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
29d6b92ffaSHans Petter Selasky * BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
30d6b92ffaSHans Petter Selasky * ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
31d6b92ffaSHans Petter Selasky * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
32d6b92ffaSHans Petter Selasky * SOFTWARE.
33d6b92ffaSHans Petter Selasky *
34d6b92ffaSHans Petter Selasky */
35d6b92ffaSHans Petter Selasky
36d6b92ffaSHans Petter Selasky #if HAVE_CONFIG_H
37d6b92ffaSHans Petter Selasky # include <config.h>
38d6b92ffaSHans Petter Selasky #endif /* HAVE_CONFIG_H */
39d6b92ffaSHans Petter Selasky
40d6b92ffaSHans Petter Selasky #include <stdio.h>
41d6b92ffaSHans Petter Selasky #include <stdlib.h>
42d6b92ffaSHans Petter Selasky #include <unistd.h>
43d6b92ffaSHans Petter Selasky #include <string.h>
44d6b92ffaSHans Petter Selasky #include <getopt.h>
45d6b92ffaSHans Petter Selasky #include <errno.h>
46d6b92ffaSHans Petter Selasky
47d6b92ffaSHans Petter Selasky #include <infiniband/umad.h>
48d6b92ffaSHans Petter Selasky #include <infiniband/mad.h>
49d6b92ffaSHans Petter Selasky
50d6b92ffaSHans Petter Selasky #include "ibdiag_common.h"
51d6b92ffaSHans Petter Selasky
52d6b92ffaSHans Petter Selasky enum port_ops {
53d6b92ffaSHans Petter Selasky QUERY,
54d6b92ffaSHans Petter Selasky ENABLE,
55d6b92ffaSHans Petter Selasky RESET,
56d6b92ffaSHans Petter Selasky DISABLE,
57d6b92ffaSHans Petter Selasky SPEED,
58d6b92ffaSHans Petter Selasky ESPEED,
59d6b92ffaSHans Petter Selasky FDR10SPEED,
60d6b92ffaSHans Petter Selasky WIDTH,
61d6b92ffaSHans Petter Selasky DOWN,
62d6b92ffaSHans Petter Selasky ARM,
63d6b92ffaSHans Petter Selasky ACTIVE,
64d6b92ffaSHans Petter Selasky VLS,
65d6b92ffaSHans Petter Selasky MTU,
66d6b92ffaSHans Petter Selasky LID,
67d6b92ffaSHans Petter Selasky SMLID,
68d6b92ffaSHans Petter Selasky LMC,
69d6b92ffaSHans Petter Selasky MKEY,
70d6b92ffaSHans Petter Selasky MKEYLEASE,
71d6b92ffaSHans Petter Selasky MKEYPROT,
72d6b92ffaSHans Petter Selasky ON,
73d6b92ffaSHans Petter Selasky OFF
74d6b92ffaSHans Petter Selasky };
75d6b92ffaSHans Petter Selasky
76d6b92ffaSHans Petter Selasky struct ibmad_port *srcport;
77d6b92ffaSHans Petter Selasky uint64_t speed = 0; /* no state change */
78d6b92ffaSHans Petter Selasky uint64_t espeed = 0; /* no state change */
79d6b92ffaSHans Petter Selasky uint64_t fdr10 = 0; /* no state change */
80d6b92ffaSHans Petter Selasky uint64_t width = 0; /* no state change */
81d6b92ffaSHans Petter Selasky uint64_t lid;
82d6b92ffaSHans Petter Selasky uint64_t smlid;
83d6b92ffaSHans Petter Selasky uint64_t lmc;
84d6b92ffaSHans Petter Selasky uint64_t mtu;
85d6b92ffaSHans Petter Selasky uint64_t vls = 0; /* no state change */
86d6b92ffaSHans Petter Selasky uint64_t mkey;
87d6b92ffaSHans Petter Selasky uint64_t mkeylease;
88d6b92ffaSHans Petter Selasky uint64_t mkeyprot;
89d6b92ffaSHans Petter Selasky
90d6b92ffaSHans Petter Selasky struct {
91d6b92ffaSHans Petter Selasky const char *name;
92d6b92ffaSHans Petter Selasky uint64_t *val;
93d6b92ffaSHans Petter Selasky int set;
94d6b92ffaSHans Petter Selasky } port_args[] = {
95d6b92ffaSHans Petter Selasky {"query", NULL, 0}, /* QUERY */
96d6b92ffaSHans Petter Selasky {"enable", NULL, 0}, /* ENABLE */
97d6b92ffaSHans Petter Selasky {"reset", NULL, 0}, /* RESET */
98d6b92ffaSHans Petter Selasky {"disable", NULL, 0}, /* DISABLE */
99d6b92ffaSHans Petter Selasky {"speed", &speed, 0}, /* SPEED */
100d6b92ffaSHans Petter Selasky {"espeed", &espeed, 0}, /* EXTENDED SPEED */
101d6b92ffaSHans Petter Selasky {"fdr10", &fdr10, 0}, /* FDR10 SPEED */
102d6b92ffaSHans Petter Selasky {"width", &width, 0}, /* WIDTH */
103d6b92ffaSHans Petter Selasky {"down", NULL, 0}, /* DOWN */
104d6b92ffaSHans Petter Selasky {"arm", NULL, 0}, /* ARM */
105d6b92ffaSHans Petter Selasky {"active", NULL, 0}, /* ACTIVE */
106d6b92ffaSHans Petter Selasky {"vls", &vls, 0}, /* VLS */
107d6b92ffaSHans Petter Selasky {"mtu", &mtu, 0}, /* MTU */
108d6b92ffaSHans Petter Selasky {"lid", &lid, 0}, /* LID */
109d6b92ffaSHans Petter Selasky {"smlid", &smlid, 0}, /* SMLID */
110d6b92ffaSHans Petter Selasky {"lmc", &lmc, 0}, /* LMC */
111d6b92ffaSHans Petter Selasky {"mkey", &mkey, 0}, /* MKEY */
112d6b92ffaSHans Petter Selasky {"mkeylease", &mkeylease, 0}, /* MKEY LEASE */
113d6b92ffaSHans Petter Selasky {"mkeyprot", &mkeyprot, 0}, /* MKEY PROTECT BITS */
114d6b92ffaSHans Petter Selasky {"on", NULL, 0}, /* ON */
115d6b92ffaSHans Petter Selasky {"off", NULL, 0}, /* OFF */
116d6b92ffaSHans Petter Selasky };
117d6b92ffaSHans Petter Selasky
118d6b92ffaSHans Petter Selasky #define NPORT_ARGS (sizeof(port_args) / sizeof(port_args[0]))
119d6b92ffaSHans Petter Selasky
120d6b92ffaSHans Petter Selasky /*******************************************/
121d6b92ffaSHans Petter Selasky
122d6b92ffaSHans Petter Selasky /*
123d6b92ffaSHans Petter Selasky * Return 1 if node is a switch, else zero.
124d6b92ffaSHans Petter Selasky */
get_node_info(ib_portid_t * dest,uint8_t * data)125d6b92ffaSHans Petter Selasky static int get_node_info(ib_portid_t * dest, uint8_t * data)
126d6b92ffaSHans Petter Selasky {
127d6b92ffaSHans Petter Selasky int node_type;
128d6b92ffaSHans Petter Selasky
129d6b92ffaSHans Petter Selasky if (!smp_query_via(data, dest, IB_ATTR_NODE_INFO, 0, 0, srcport))
130d6b92ffaSHans Petter Selasky IBEXIT("smp query nodeinfo failed");
131d6b92ffaSHans Petter Selasky
132d6b92ffaSHans Petter Selasky node_type = mad_get_field(data, 0, IB_NODE_TYPE_F);
133d6b92ffaSHans Petter Selasky if (node_type == IB_NODE_SWITCH) /* Switch NodeType ? */
134d6b92ffaSHans Petter Selasky return 1;
135d6b92ffaSHans Petter Selasky else
136d6b92ffaSHans Petter Selasky return 0;
137d6b92ffaSHans Petter Selasky }
138d6b92ffaSHans Petter Selasky
get_port_info(ib_portid_t * dest,uint8_t * data,int portnum,int is_switch)139d6b92ffaSHans Petter Selasky static int get_port_info(ib_portid_t * dest, uint8_t * data, int portnum,
140d6b92ffaSHans Petter Selasky int is_switch)
141d6b92ffaSHans Petter Selasky {
142d6b92ffaSHans Petter Selasky uint8_t smp[IB_SMP_DATA_SIZE];
143d6b92ffaSHans Petter Selasky uint8_t *info;
144d6b92ffaSHans Petter Selasky int cap_mask;
145d6b92ffaSHans Petter Selasky
146d6b92ffaSHans Petter Selasky if (is_switch) {
147d6b92ffaSHans Petter Selasky if (!smp_query_via(smp, dest, IB_ATTR_PORT_INFO, 0, 0, srcport))
148d6b92ffaSHans Petter Selasky IBEXIT("smp query port 0 portinfo failed");
149d6b92ffaSHans Petter Selasky info = smp;
150d6b92ffaSHans Petter Selasky } else
151d6b92ffaSHans Petter Selasky info = data;
152d6b92ffaSHans Petter Selasky
153d6b92ffaSHans Petter Selasky if (!smp_query_via(data, dest, IB_ATTR_PORT_INFO, portnum, 0, srcport))
154d6b92ffaSHans Petter Selasky IBEXIT("smp query portinfo failed");
155d6b92ffaSHans Petter Selasky cap_mask = mad_get_field(info, 0, IB_PORT_CAPMASK_F);
156d6b92ffaSHans Petter Selasky return (cap_mask & CL_NTOH32(IB_PORT_CAP_HAS_EXT_SPEEDS));
157d6b92ffaSHans Petter Selasky }
158d6b92ffaSHans Petter Selasky
show_port_info(ib_portid_t * dest,uint8_t * data,int portnum,int espeed_cap,int is_switch)159d6b92ffaSHans Petter Selasky static void show_port_info(ib_portid_t * dest, uint8_t * data, int portnum,
160d6b92ffaSHans Petter Selasky int espeed_cap, int is_switch)
161d6b92ffaSHans Petter Selasky {
162d6b92ffaSHans Petter Selasky char buf[2300];
163d6b92ffaSHans Petter Selasky char val[64];
164d6b92ffaSHans Petter Selasky
165d6b92ffaSHans Petter Selasky mad_dump_portstates(buf, sizeof buf, data, sizeof *data);
166d6b92ffaSHans Petter Selasky mad_decode_field(data, IB_PORT_LID_F, val);
167d6b92ffaSHans Petter Selasky mad_dump_field(IB_PORT_LID_F, buf + strlen(buf),
168d6b92ffaSHans Petter Selasky sizeof buf - strlen(buf), val);
169d6b92ffaSHans Petter Selasky sprintf(buf + strlen(buf), "%s", "\n");
170d6b92ffaSHans Petter Selasky mad_decode_field(data, IB_PORT_SMLID_F, val);
171d6b92ffaSHans Petter Selasky mad_dump_field(IB_PORT_SMLID_F, buf + strlen(buf),
172d6b92ffaSHans Petter Selasky sizeof buf - strlen(buf), val);
173d6b92ffaSHans Petter Selasky sprintf(buf + strlen(buf), "%s", "\n");
174d6b92ffaSHans Petter Selasky mad_decode_field(data, IB_PORT_LMC_F, val);
175d6b92ffaSHans Petter Selasky mad_dump_field(IB_PORT_LMC_F, buf + strlen(buf),
176d6b92ffaSHans Petter Selasky sizeof buf - strlen(buf), val);
177d6b92ffaSHans Petter Selasky sprintf(buf + strlen(buf), "%s", "\n");
178d6b92ffaSHans Petter Selasky mad_decode_field(data, IB_PORT_LINK_WIDTH_SUPPORTED_F, val);
179d6b92ffaSHans Petter Selasky mad_dump_field(IB_PORT_LINK_WIDTH_SUPPORTED_F, buf + strlen(buf),
180d6b92ffaSHans Petter Selasky sizeof buf - strlen(buf), val);
181d6b92ffaSHans Petter Selasky sprintf(buf + strlen(buf), "%s", "\n");
182d6b92ffaSHans Petter Selasky mad_decode_field(data, IB_PORT_LINK_WIDTH_ENABLED_F, val);
183d6b92ffaSHans Petter Selasky mad_dump_field(IB_PORT_LINK_WIDTH_ENABLED_F, buf + strlen(buf),
184d6b92ffaSHans Petter Selasky sizeof buf - strlen(buf), val);
185d6b92ffaSHans Petter Selasky sprintf(buf + strlen(buf), "%s", "\n");
186d6b92ffaSHans Petter Selasky mad_decode_field(data, IB_PORT_LINK_WIDTH_ACTIVE_F, val);
187d6b92ffaSHans Petter Selasky mad_dump_field(IB_PORT_LINK_WIDTH_ACTIVE_F, buf + strlen(buf),
188d6b92ffaSHans Petter Selasky sizeof buf - strlen(buf), val);
189d6b92ffaSHans Petter Selasky sprintf(buf + strlen(buf), "%s", "\n");
190d6b92ffaSHans Petter Selasky mad_decode_field(data, IB_PORT_LINK_SPEED_SUPPORTED_F, val);
191d6b92ffaSHans Petter Selasky mad_dump_field(IB_PORT_LINK_SPEED_SUPPORTED_F, buf + strlen(buf),
192d6b92ffaSHans Petter Selasky sizeof buf - strlen(buf), val);
193d6b92ffaSHans Petter Selasky sprintf(buf + strlen(buf), "%s", "\n");
194d6b92ffaSHans Petter Selasky mad_decode_field(data, IB_PORT_LINK_SPEED_ENABLED_F, val);
195d6b92ffaSHans Petter Selasky mad_dump_field(IB_PORT_LINK_SPEED_ENABLED_F, buf + strlen(buf),
196d6b92ffaSHans Petter Selasky sizeof buf - strlen(buf), val);
197d6b92ffaSHans Petter Selasky sprintf(buf + strlen(buf), "%s", "\n");
198d6b92ffaSHans Petter Selasky mad_decode_field(data, IB_PORT_LINK_SPEED_ACTIVE_F, val);
199d6b92ffaSHans Petter Selasky mad_dump_field(IB_PORT_LINK_SPEED_ACTIVE_F, buf + strlen(buf),
200d6b92ffaSHans Petter Selasky sizeof buf - strlen(buf), val);
201d6b92ffaSHans Petter Selasky sprintf(buf + strlen(buf), "%s", "\n");
202d6b92ffaSHans Petter Selasky if (espeed_cap) {
203d6b92ffaSHans Petter Selasky mad_decode_field(data, IB_PORT_LINK_SPEED_EXT_SUPPORTED_F, val);
204d6b92ffaSHans Petter Selasky mad_dump_field(IB_PORT_LINK_SPEED_EXT_SUPPORTED_F,
205d6b92ffaSHans Petter Selasky buf + strlen(buf), sizeof buf - strlen(buf),
206d6b92ffaSHans Petter Selasky val);
207d6b92ffaSHans Petter Selasky sprintf(buf + strlen(buf), "%s", "\n");
208d6b92ffaSHans Petter Selasky mad_decode_field(data, IB_PORT_LINK_SPEED_EXT_ENABLED_F, val);
209d6b92ffaSHans Petter Selasky mad_dump_field(IB_PORT_LINK_SPEED_EXT_ENABLED_F,
210d6b92ffaSHans Petter Selasky buf + strlen(buf), sizeof buf - strlen(buf),
211d6b92ffaSHans Petter Selasky val);
212d6b92ffaSHans Petter Selasky sprintf(buf + strlen(buf), "%s", "\n");
213d6b92ffaSHans Petter Selasky mad_decode_field(data, IB_PORT_LINK_SPEED_EXT_ACTIVE_F, val);
214d6b92ffaSHans Petter Selasky mad_dump_field(IB_PORT_LINK_SPEED_EXT_ACTIVE_F,
215d6b92ffaSHans Petter Selasky buf + strlen(buf), sizeof buf - strlen(buf),
216d6b92ffaSHans Petter Selasky val);
217d6b92ffaSHans Petter Selasky sprintf(buf + strlen(buf), "%s", "\n");
218d6b92ffaSHans Petter Selasky }
219d6b92ffaSHans Petter Selasky if (!is_switch || portnum == 0) {
220d6b92ffaSHans Petter Selasky if (show_keys) {
221d6b92ffaSHans Petter Selasky mad_decode_field(data, IB_PORT_MKEY_F, val);
222d6b92ffaSHans Petter Selasky mad_dump_field(IB_PORT_MKEY_F, buf + strlen(buf),
223d6b92ffaSHans Petter Selasky sizeof buf - strlen(buf), val);
224d6b92ffaSHans Petter Selasky } else
225d6b92ffaSHans Petter Selasky snprint_field(buf+strlen(buf), sizeof(buf)-strlen(buf),
226d6b92ffaSHans Petter Selasky IB_PORT_MKEY_F, 32, NOT_DISPLAYED_STR);
227d6b92ffaSHans Petter Selasky sprintf(buf+strlen(buf), "%s", "\n");
228d6b92ffaSHans Petter Selasky mad_decode_field(data, IB_PORT_MKEY_LEASE_F, val);
229d6b92ffaSHans Petter Selasky mad_dump_field(IB_PORT_MKEY_LEASE_F, buf + strlen(buf),
230d6b92ffaSHans Petter Selasky sizeof buf - strlen(buf), val);
231d6b92ffaSHans Petter Selasky sprintf(buf+strlen(buf), "%s", "\n");
232d6b92ffaSHans Petter Selasky mad_decode_field(data, IB_PORT_MKEY_PROT_BITS_F, val);
233d6b92ffaSHans Petter Selasky mad_dump_field(IB_PORT_MKEY_PROT_BITS_F, buf + strlen(buf),
234d6b92ffaSHans Petter Selasky sizeof buf - strlen(buf), val);
235d6b92ffaSHans Petter Selasky sprintf(buf+strlen(buf), "%s", "\n");
236d6b92ffaSHans Petter Selasky }
237d6b92ffaSHans Petter Selasky
238d6b92ffaSHans Petter Selasky printf("# Port info: %s port %d\n%s", portid2str(dest), portnum, buf);
239d6b92ffaSHans Petter Selasky }
240d6b92ffaSHans Petter Selasky
set_port_info(ib_portid_t * dest,uint8_t * data,int portnum,int espeed_cap,int is_switch)241d6b92ffaSHans Petter Selasky static void set_port_info(ib_portid_t * dest, uint8_t * data, int portnum,
242d6b92ffaSHans Petter Selasky int espeed_cap, int is_switch)
243d6b92ffaSHans Petter Selasky {
244d6b92ffaSHans Petter Selasky unsigned mod;
245d6b92ffaSHans Petter Selasky
246d6b92ffaSHans Petter Selasky mod = portnum;
247d6b92ffaSHans Petter Selasky if (espeed_cap)
248d6b92ffaSHans Petter Selasky mod |= 1<<31;
249d6b92ffaSHans Petter Selasky if (!smp_set_via(data, dest, IB_ATTR_PORT_INFO, mod, 0, srcport))
250d6b92ffaSHans Petter Selasky IBEXIT("smp set portinfo failed");
251d6b92ffaSHans Petter Selasky
252d6b92ffaSHans Petter Selasky printf("\nAfter PortInfo set:\n");
253d6b92ffaSHans Petter Selasky show_port_info(dest, data, portnum, espeed_cap, is_switch);
254d6b92ffaSHans Petter Selasky }
255d6b92ffaSHans Petter Selasky
get_mlnx_ext_port_info(ib_portid_t * dest,uint8_t * data,int portnum)256d6b92ffaSHans Petter Selasky static void get_mlnx_ext_port_info(ib_portid_t * dest, uint8_t * data, int portnum)
257d6b92ffaSHans Petter Selasky {
258d6b92ffaSHans Petter Selasky if (!smp_query_via(data, dest, IB_ATTR_MLNX_EXT_PORT_INFO,
259d6b92ffaSHans Petter Selasky portnum, 0, srcport))
260d6b92ffaSHans Petter Selasky IBEXIT("smp query ext portinfo failed");
261d6b92ffaSHans Petter Selasky }
262d6b92ffaSHans Petter Selasky
show_mlnx_ext_port_info(ib_portid_t * dest,uint8_t * data,int portnum)263d6b92ffaSHans Petter Selasky static void show_mlnx_ext_port_info(ib_portid_t * dest, uint8_t * data, int portnum)
264d6b92ffaSHans Petter Selasky {
265d6b92ffaSHans Petter Selasky char buf[256];
266d6b92ffaSHans Petter Selasky
267d6b92ffaSHans Petter Selasky mad_dump_mlnx_ext_port_info(buf, sizeof buf, data, IB_SMP_DATA_SIZE);
268d6b92ffaSHans Petter Selasky
269d6b92ffaSHans Petter Selasky printf("# MLNX ext Port info: %s port %d\n%s", portid2str(dest),
270d6b92ffaSHans Petter Selasky portnum, buf);
271d6b92ffaSHans Petter Selasky }
272d6b92ffaSHans Petter Selasky
set_mlnx_ext_port_info(ib_portid_t * dest,uint8_t * data,int portnum)273d6b92ffaSHans Petter Selasky static void set_mlnx_ext_port_info(ib_portid_t * dest, uint8_t * data, int portnum)
274d6b92ffaSHans Petter Selasky {
275d6b92ffaSHans Petter Selasky if (!smp_set_via(data, dest, IB_ATTR_MLNX_EXT_PORT_INFO,
276d6b92ffaSHans Petter Selasky portnum, 0, srcport))
277d6b92ffaSHans Petter Selasky IBEXIT("smp set MLNX ext portinfo failed");
278d6b92ffaSHans Petter Selasky
279d6b92ffaSHans Petter Selasky printf("\nAfter MLNXExtendedPortInfo set:\n");
280d6b92ffaSHans Petter Selasky show_mlnx_ext_port_info(dest, data, portnum);
281d6b92ffaSHans Petter Selasky }
282d6b92ffaSHans Petter Selasky
get_link_width(int lwe,int lws)283d6b92ffaSHans Petter Selasky static int get_link_width(int lwe, int lws)
284d6b92ffaSHans Petter Selasky {
285d6b92ffaSHans Petter Selasky if (lwe == 255)
286d6b92ffaSHans Petter Selasky return lws;
287d6b92ffaSHans Petter Selasky else
288d6b92ffaSHans Petter Selasky return lwe;
289d6b92ffaSHans Petter Selasky }
290d6b92ffaSHans Petter Selasky
get_link_speed(int lse,int lss)291d6b92ffaSHans Petter Selasky static int get_link_speed(int lse, int lss)
292d6b92ffaSHans Petter Selasky {
293d6b92ffaSHans Petter Selasky if (lse == 15)
294d6b92ffaSHans Petter Selasky return lss;
295d6b92ffaSHans Petter Selasky else
296d6b92ffaSHans Petter Selasky return lse;
297d6b92ffaSHans Petter Selasky }
298d6b92ffaSHans Petter Selasky
get_link_speed_ext(int lsee,int lses)299d6b92ffaSHans Petter Selasky static int get_link_speed_ext(int lsee, int lses)
300d6b92ffaSHans Petter Selasky {
301d6b92ffaSHans Petter Selasky if (lsee == 31)
302d6b92ffaSHans Petter Selasky return lses;
303d6b92ffaSHans Petter Selasky else
304d6b92ffaSHans Petter Selasky return lsee;
305d6b92ffaSHans Petter Selasky }
306d6b92ffaSHans Petter Selasky
validate_width(int width,int peerwidth,int lwa)307d6b92ffaSHans Petter Selasky static void validate_width(int width, int peerwidth, int lwa)
308d6b92ffaSHans Petter Selasky {
309d6b92ffaSHans Petter Selasky if ((width & peerwidth & 0x8)) {
310d6b92ffaSHans Petter Selasky if (lwa != 8)
311d6b92ffaSHans Petter Selasky IBWARN
312d6b92ffaSHans Petter Selasky ("Peer ports operating at active width %d rather than 8 (12x)",
313d6b92ffaSHans Petter Selasky lwa);
314d6b92ffaSHans Petter Selasky } else if ((width & peerwidth & 0x4)) {
315d6b92ffaSHans Petter Selasky if (lwa != 4)
316d6b92ffaSHans Petter Selasky IBWARN
317d6b92ffaSHans Petter Selasky ("Peer ports operating at active width %d rather than 4 (8x)",
318d6b92ffaSHans Petter Selasky lwa);
319d6b92ffaSHans Petter Selasky } else if ((width & peerwidth & 0x2)) {
320d6b92ffaSHans Petter Selasky if (lwa != 2)
321d6b92ffaSHans Petter Selasky IBWARN
322d6b92ffaSHans Petter Selasky ("Peer ports operating at active width %d rather than 2 (4x)",
323d6b92ffaSHans Petter Selasky lwa);
324d6b92ffaSHans Petter Selasky } else if ((width & peerwidth & 0x10)) {
325d6b92ffaSHans Petter Selasky if (lwa != 16)
326d6b92ffaSHans Petter Selasky IBWARN
327d6b92ffaSHans Petter Selasky ("Peer ports operating at active width %d rather than 16 (2x)",
328d6b92ffaSHans Petter Selasky lwa);
329d6b92ffaSHans Petter Selasky } else if ((width & peerwidth & 0x1)) {
330d6b92ffaSHans Petter Selasky if (lwa != 1)
331d6b92ffaSHans Petter Selasky IBWARN
332d6b92ffaSHans Petter Selasky ("Peer ports operating at active width %d rather than 1 (1x)",
333d6b92ffaSHans Petter Selasky lwa);
334d6b92ffaSHans Petter Selasky }
335d6b92ffaSHans Petter Selasky }
336d6b92ffaSHans Petter Selasky
validate_speed(int speed,int peerspeed,int lsa)337d6b92ffaSHans Petter Selasky static void validate_speed(int speed, int peerspeed, int lsa)
338d6b92ffaSHans Petter Selasky {
339d6b92ffaSHans Petter Selasky if ((speed & peerspeed & 0x4)) {
340d6b92ffaSHans Petter Selasky if (lsa != 4)
341d6b92ffaSHans Petter Selasky IBWARN
342d6b92ffaSHans Petter Selasky ("Peer ports operating at active speed %d rather than 4 (10.0 Gbps)",
343d6b92ffaSHans Petter Selasky lsa);
344d6b92ffaSHans Petter Selasky } else if ((speed & peerspeed & 0x2)) {
345d6b92ffaSHans Petter Selasky if (lsa != 2)
346d6b92ffaSHans Petter Selasky IBWARN
347d6b92ffaSHans Petter Selasky ("Peer ports operating at active speed %d rather than 2 (5.0 Gbps)",
348d6b92ffaSHans Petter Selasky lsa);
349d6b92ffaSHans Petter Selasky } else if ((speed & peerspeed & 0x1)) {
350d6b92ffaSHans Petter Selasky if (lsa != 1)
351d6b92ffaSHans Petter Selasky IBWARN
352d6b92ffaSHans Petter Selasky ("Peer ports operating at active speed %d rather than 1 (2.5 Gbps)",
353d6b92ffaSHans Petter Selasky lsa);
354d6b92ffaSHans Petter Selasky }
355d6b92ffaSHans Petter Selasky }
356d6b92ffaSHans Petter Selasky
validate_extended_speed(int espeed,int peerespeed,int lsea)357d6b92ffaSHans Petter Selasky static void validate_extended_speed(int espeed, int peerespeed, int lsea)
358d6b92ffaSHans Petter Selasky {
359d6b92ffaSHans Petter Selasky if ((espeed & peerespeed & 0x2)) {
360d6b92ffaSHans Petter Selasky if (lsea != 2)
361d6b92ffaSHans Petter Selasky IBWARN
362d6b92ffaSHans Petter Selasky ("Peer ports operating at active extended speed %d rather than 2 (25.78125 Gbps)",
363d6b92ffaSHans Petter Selasky lsea);
364d6b92ffaSHans Petter Selasky } else if ((espeed & peerespeed & 0x1)) {
365d6b92ffaSHans Petter Selasky if (lsea != 1)
366d6b92ffaSHans Petter Selasky IBWARN
367d6b92ffaSHans Petter Selasky ("Peer ports operating at active extended speed %d rather than 1 (14.0625 Gbps)",
368d6b92ffaSHans Petter Selasky lsea);
369d6b92ffaSHans Petter Selasky }
370d6b92ffaSHans Petter Selasky }
371d6b92ffaSHans Petter Selasky
main(int argc,char ** argv)372d6b92ffaSHans Petter Selasky int main(int argc, char **argv)
373d6b92ffaSHans Petter Selasky {
374d6b92ffaSHans Petter Selasky int mgmt_classes[3] =
375d6b92ffaSHans Petter Selasky { IB_SMI_CLASS, IB_SMI_DIRECT_CLASS, IB_SA_CLASS };
376d6b92ffaSHans Petter Selasky ib_portid_t portid = { 0 };
377d6b92ffaSHans Petter Selasky int port_op = -1;
378d6b92ffaSHans Petter Selasky int is_switch, is_peer_switch, espeed_cap, peer_espeed_cap;
379d6b92ffaSHans Petter Selasky int state, physstate, lwe, lws, lwa, lse, lss, lsa, lsee, lses, lsea,
380d6b92ffaSHans Petter Selasky fdr10s, fdr10e, fdr10a;
381d6b92ffaSHans Petter Selasky int peerlocalportnum, peerlwe, peerlws, peerlwa, peerlse, peerlss,
382d6b92ffaSHans Petter Selasky peerlsa, peerlsee, peerlses, peerlsea, peerfdr10s, peerfdr10e,
383d6b92ffaSHans Petter Selasky peerfdr10a;
384d6b92ffaSHans Petter Selasky int peerwidth, peerspeed, peerespeed;
385d6b92ffaSHans Petter Selasky uint8_t data[IB_SMP_DATA_SIZE] = { 0 };
386d6b92ffaSHans Petter Selasky uint8_t data2[IB_SMP_DATA_SIZE] = { 0 };
387d6b92ffaSHans Petter Selasky ib_portid_t peerportid = { 0 };
388d6b92ffaSHans Petter Selasky int portnum = 0;
389d6b92ffaSHans Petter Selasky ib_portid_t selfportid = { 0 };
390d6b92ffaSHans Petter Selasky int selfport = 0;
391d6b92ffaSHans Petter Selasky int changed = 0;
392d6b92ffaSHans Petter Selasky int i;
393d6b92ffaSHans Petter Selasky uint32_t vendorid, rem_vendorid;
394d6b92ffaSHans Petter Selasky uint16_t devid, rem_devid;
395d6b92ffaSHans Petter Selasky uint64_t val;
396d6b92ffaSHans Petter Selasky char *endp;
397d6b92ffaSHans Petter Selasky char usage_args[] = "<dest dr_path|lid|guid> <portnum> [<op>]\n"
398d6b92ffaSHans Petter Selasky "\nSupported ops: enable, disable, on, off, reset, speed, espeed, fdr10,\n"
399d6b92ffaSHans Petter Selasky "\twidth, query, down, arm, active, vls, mtu, lid, smlid, lmc,\n"
400d6b92ffaSHans Petter Selasky "\tmkey, mkeylease, mkeyprot\n";
401d6b92ffaSHans Petter Selasky const char *usage_examples[] = {
402d6b92ffaSHans Petter Selasky "3 1 disable\t\t\t# by lid",
403d6b92ffaSHans Petter Selasky "-G 0x2C9000100D051 1 enable\t# by guid",
404d6b92ffaSHans Petter Selasky "-D 0 1\t\t\t# (query) by direct route",
405d6b92ffaSHans Petter Selasky "3 1 reset\t\t\t# by lid",
406d6b92ffaSHans Petter Selasky "3 1 speed 1\t\t\t# by lid",
407d6b92ffaSHans Petter Selasky "3 1 width 1\t\t\t# by lid",
408d6b92ffaSHans Petter Selasky "-D 0 1 lid 0x1234 arm\t\t# by direct route",
409d6b92ffaSHans Petter Selasky NULL
410d6b92ffaSHans Petter Selasky };
411d6b92ffaSHans Petter Selasky
412d6b92ffaSHans Petter Selasky ibdiag_process_opts(argc, argv, NULL, NULL, NULL, NULL,
413d6b92ffaSHans Petter Selasky usage_args, usage_examples);
414d6b92ffaSHans Petter Selasky
415d6b92ffaSHans Petter Selasky argc -= optind;
416d6b92ffaSHans Petter Selasky argv += optind;
417d6b92ffaSHans Petter Selasky
418d6b92ffaSHans Petter Selasky if (argc < 2)
419d6b92ffaSHans Petter Selasky ibdiag_show_usage();
420d6b92ffaSHans Petter Selasky
421d6b92ffaSHans Petter Selasky srcport = mad_rpc_open_port(ibd_ca, ibd_ca_port, mgmt_classes, 3);
422d6b92ffaSHans Petter Selasky if (!srcport)
423d6b92ffaSHans Petter Selasky IBEXIT("Failed to open '%s' port '%d'", ibd_ca, ibd_ca_port);
424d6b92ffaSHans Petter Selasky
425d6b92ffaSHans Petter Selasky smp_mkey_set(srcport, ibd_mkey);
426d6b92ffaSHans Petter Selasky
427d6b92ffaSHans Petter Selasky if (resolve_portid_str(ibd_ca, ibd_ca_port, &portid, argv[0],
428d6b92ffaSHans Petter Selasky ibd_dest_type, ibd_sm_id, srcport) < 0)
429d6b92ffaSHans Petter Selasky IBEXIT("can't resolve destination port %s", argv[0]);
430d6b92ffaSHans Petter Selasky
431d6b92ffaSHans Petter Selasky if (argc > 1)
432d6b92ffaSHans Petter Selasky portnum = strtol(argv[1], 0, 0);
433d6b92ffaSHans Petter Selasky
434d6b92ffaSHans Petter Selasky for (i = 2; i < argc; i++) {
435d6b92ffaSHans Petter Selasky int j;
436d6b92ffaSHans Petter Selasky
437d6b92ffaSHans Petter Selasky for (j = 0; j < NPORT_ARGS; j++) {
438d6b92ffaSHans Petter Selasky if (strcmp(argv[i], port_args[j].name))
439d6b92ffaSHans Petter Selasky continue;
440d6b92ffaSHans Petter Selasky port_args[j].set = 1;
441d6b92ffaSHans Petter Selasky if (!port_args[j].val) {
442d6b92ffaSHans Petter Selasky if (port_op >= 0)
443d6b92ffaSHans Petter Selasky IBEXIT("%s only one of: ",
444d6b92ffaSHans Petter Selasky "query, enable, disable, "
445d6b92ffaSHans Petter Selasky "reset, down, arm, active, "
446d6b92ffaSHans Petter Selasky "can be specified",
447d6b92ffaSHans Petter Selasky port_args[j].name);
448d6b92ffaSHans Petter Selasky port_op = j;
449d6b92ffaSHans Petter Selasky break;
450d6b92ffaSHans Petter Selasky }
451d6b92ffaSHans Petter Selasky if (++i >= argc)
452d6b92ffaSHans Petter Selasky IBEXIT("%s requires an additional parameter",
453d6b92ffaSHans Petter Selasky port_args[j].name);
454d6b92ffaSHans Petter Selasky val = strtoull(argv[i], 0, 0);
455d6b92ffaSHans Petter Selasky switch (j) {
456d6b92ffaSHans Petter Selasky case SPEED:
457d6b92ffaSHans Petter Selasky if (val > 15)
458d6b92ffaSHans Petter Selasky IBEXIT("invalid speed value %ld", val);
459d6b92ffaSHans Petter Selasky break;
460d6b92ffaSHans Petter Selasky case ESPEED:
461d6b92ffaSHans Petter Selasky if (val > 31)
462d6b92ffaSHans Petter Selasky IBEXIT("invalid extended speed value %ld", val);
463d6b92ffaSHans Petter Selasky break;
464d6b92ffaSHans Petter Selasky case FDR10SPEED:
465d6b92ffaSHans Petter Selasky if (val > 1)
466d6b92ffaSHans Petter Selasky IBEXIT("invalid fdr10 speed value %ld", val);
467d6b92ffaSHans Petter Selasky break;
468d6b92ffaSHans Petter Selasky case WIDTH:
469d6b92ffaSHans Petter Selasky if ((val > 31 && val != 255))
470d6b92ffaSHans Petter Selasky IBEXIT("invalid width value %ld", val);
471d6b92ffaSHans Petter Selasky break;
472d6b92ffaSHans Petter Selasky case VLS:
473d6b92ffaSHans Petter Selasky if (val == 0 || val > 5)
474d6b92ffaSHans Petter Selasky IBEXIT("invalid vls value %ld", val);
475d6b92ffaSHans Petter Selasky break;
476d6b92ffaSHans Petter Selasky case MTU:
477d6b92ffaSHans Petter Selasky if (val == 0 || val > 5)
478d6b92ffaSHans Petter Selasky IBEXIT("invalid mtu value %ld", val);
479d6b92ffaSHans Petter Selasky break;
480d6b92ffaSHans Petter Selasky case LID:
481d6b92ffaSHans Petter Selasky if (val == 0 || val >= 0xC000)
482d6b92ffaSHans Petter Selasky IBEXIT("invalid lid value 0x%lx", val);
483d6b92ffaSHans Petter Selasky break;
484d6b92ffaSHans Petter Selasky case SMLID:
485d6b92ffaSHans Petter Selasky if (val == 0 || val >= 0xC000)
486d6b92ffaSHans Petter Selasky IBEXIT("invalid smlid value 0x%lx",
487d6b92ffaSHans Petter Selasky val);
488d6b92ffaSHans Petter Selasky break;
489d6b92ffaSHans Petter Selasky case LMC:
490d6b92ffaSHans Petter Selasky if (val > 7)
491d6b92ffaSHans Petter Selasky IBEXIT("invalid lmc value %ld", val);
492d6b92ffaSHans Petter Selasky break;
493d6b92ffaSHans Petter Selasky case MKEY:
494d6b92ffaSHans Petter Selasky errno = 0;
495d6b92ffaSHans Petter Selasky val = strtoull(argv[i], &endp, 0);
496d6b92ffaSHans Petter Selasky if (errno || *endp != '\0') {
497d6b92ffaSHans Petter Selasky errno = 0;
498d6b92ffaSHans Petter Selasky val = strtoull(getpass("New M_Key: "),
499d6b92ffaSHans Petter Selasky &endp, 0);
500d6b92ffaSHans Petter Selasky if (errno || *endp != '\0') {
501d6b92ffaSHans Petter Selasky IBEXIT("Bad new M_Key\n");
502d6b92ffaSHans Petter Selasky }
503d6b92ffaSHans Petter Selasky }
504d6b92ffaSHans Petter Selasky /* All 64-bit values are legal */
505d6b92ffaSHans Petter Selasky break;
506d6b92ffaSHans Petter Selasky case MKEYLEASE:
507d6b92ffaSHans Petter Selasky if (val > 0xFFFF)
508d6b92ffaSHans Petter Selasky IBEXIT("invalid mkey lease time %ld", val);
509d6b92ffaSHans Petter Selasky break;
510d6b92ffaSHans Petter Selasky case MKEYPROT:
511d6b92ffaSHans Petter Selasky if (val > 3)
512d6b92ffaSHans Petter Selasky IBEXIT("invalid mkey protection bit setting %ld", val);
513d6b92ffaSHans Petter Selasky }
514d6b92ffaSHans Petter Selasky *port_args[j].val = val;
515d6b92ffaSHans Petter Selasky changed = 1;
516d6b92ffaSHans Petter Selasky break;
517d6b92ffaSHans Petter Selasky }
518d6b92ffaSHans Petter Selasky if (j == NPORT_ARGS)
519d6b92ffaSHans Petter Selasky IBEXIT("invalid operation: %s", argv[i]);
520d6b92ffaSHans Petter Selasky }
521d6b92ffaSHans Petter Selasky if (port_op < 0)
522d6b92ffaSHans Petter Selasky port_op = QUERY;
523d6b92ffaSHans Petter Selasky
524d6b92ffaSHans Petter Selasky is_switch = get_node_info(&portid, data);
525d6b92ffaSHans Petter Selasky vendorid = (uint32_t) mad_get_field(data, 0, IB_NODE_VENDORID_F);
526d6b92ffaSHans Petter Selasky devid = (uint16_t) mad_get_field(data, 0, IB_NODE_DEVID_F);
527d6b92ffaSHans Petter Selasky
528d6b92ffaSHans Petter Selasky if ((port_args[MKEY].set || port_args[MKEYLEASE].set ||
529d6b92ffaSHans Petter Selasky port_args[MKEYPROT].set) && is_switch && portnum != 0)
530d6b92ffaSHans Petter Selasky IBEXIT("Can't set M_Key fields on switch port != 0");
531d6b92ffaSHans Petter Selasky
532d6b92ffaSHans Petter Selasky if (port_op != QUERY || changed)
533d6b92ffaSHans Petter Selasky printf("Initial %s PortInfo:\n", is_switch ? "Switch" : "CA/RT");
534d6b92ffaSHans Petter Selasky else
535d6b92ffaSHans Petter Selasky printf("%s PortInfo:\n", is_switch ? "Switch" : "CA/RT");
536d6b92ffaSHans Petter Selasky espeed_cap = get_port_info(&portid, data, portnum, is_switch);
537d6b92ffaSHans Petter Selasky show_port_info(&portid, data, portnum, espeed_cap, is_switch);
538d6b92ffaSHans Petter Selasky if (is_mlnx_ext_port_info_supported(vendorid, devid)) {
539d6b92ffaSHans Petter Selasky get_mlnx_ext_port_info(&portid, data2, portnum);
540d6b92ffaSHans Petter Selasky show_mlnx_ext_port_info(&portid, data2, portnum);
541d6b92ffaSHans Petter Selasky }
542d6b92ffaSHans Petter Selasky
543d6b92ffaSHans Petter Selasky if (port_op != QUERY || changed) {
544d6b92ffaSHans Petter Selasky /*
545d6b92ffaSHans Petter Selasky * If we aren't setting the LID and the LID is the default,
546d6b92ffaSHans Petter Selasky * the SMA command will fail due to an invalid LID.
547d6b92ffaSHans Petter Selasky * Set it to something unlikely but valid.
548d6b92ffaSHans Petter Selasky */
549d6b92ffaSHans Petter Selasky physstate = mad_get_field(data, 0, IB_PORT_PHYS_STATE_F);
550d6b92ffaSHans Petter Selasky
551d6b92ffaSHans Petter Selasky val = mad_get_field(data, 0, IB_PORT_LID_F);
552d6b92ffaSHans Petter Selasky if (!port_args[LID].set && (!val || val == 0xFFFF))
553d6b92ffaSHans Petter Selasky mad_set_field(data, 0, IB_PORT_LID_F, 0x1234);
554d6b92ffaSHans Petter Selasky val = mad_get_field(data, 0, IB_PORT_SMLID_F);
555d6b92ffaSHans Petter Selasky if (!port_args[SMLID].set && (!val || val == 0xFFFF))
556d6b92ffaSHans Petter Selasky mad_set_field(data, 0, IB_PORT_SMLID_F, 0x1234);
557d6b92ffaSHans Petter Selasky mad_set_field(data, 0, IB_PORT_STATE_F, 0); /* NOP */
558d6b92ffaSHans Petter Selasky mad_set_field(data, 0, IB_PORT_PHYS_STATE_F, 0); /* NOP */
559d6b92ffaSHans Petter Selasky
560d6b92ffaSHans Petter Selasky switch (port_op) {
561d6b92ffaSHans Petter Selasky case ON:
562d6b92ffaSHans Petter Selasky /* Enable only if state is Disable */
563d6b92ffaSHans Petter Selasky if(physstate != 3) {
564d6b92ffaSHans Petter Selasky printf("Port is already in enable state\n");
565d6b92ffaSHans Petter Selasky goto close_port;
566d6b92ffaSHans Petter Selasky }
567*d13def78SEric van Gyzen /* FALLTHROUGH */
568d6b92ffaSHans Petter Selasky case ENABLE:
569d6b92ffaSHans Petter Selasky case RESET:
570d6b92ffaSHans Petter Selasky /* Polling */
571d6b92ffaSHans Petter Selasky mad_set_field(data, 0, IB_PORT_PHYS_STATE_F, 2);
572d6b92ffaSHans Petter Selasky break;
573d6b92ffaSHans Petter Selasky case OFF:
574d6b92ffaSHans Petter Selasky case DISABLE:
575d6b92ffaSHans Petter Selasky printf("Disable may be irreversible\n");
576d6b92ffaSHans Petter Selasky mad_set_field(data, 0, IB_PORT_PHYS_STATE_F, 3);
577d6b92ffaSHans Petter Selasky break;
578d6b92ffaSHans Petter Selasky case DOWN:
579d6b92ffaSHans Petter Selasky mad_set_field(data, 0, IB_PORT_STATE_F, 1);
580d6b92ffaSHans Petter Selasky break;
581d6b92ffaSHans Petter Selasky case ARM:
582d6b92ffaSHans Petter Selasky mad_set_field(data, 0, IB_PORT_STATE_F, 3);
583d6b92ffaSHans Petter Selasky break;
584d6b92ffaSHans Petter Selasky case ACTIVE:
585d6b92ffaSHans Petter Selasky mad_set_field(data, 0, IB_PORT_STATE_F, 4);
586d6b92ffaSHans Petter Selasky break;
587d6b92ffaSHans Petter Selasky }
588d6b92ffaSHans Petter Selasky
589d6b92ffaSHans Petter Selasky /* always set enabled speeds/width - defaults to NOP */
590d6b92ffaSHans Petter Selasky mad_set_field(data, 0, IB_PORT_LINK_SPEED_ENABLED_F, speed);
591d6b92ffaSHans Petter Selasky mad_set_field(data, 0, IB_PORT_LINK_SPEED_EXT_ENABLED_F, espeed);
592d6b92ffaSHans Petter Selasky mad_set_field(data, 0, IB_PORT_LINK_WIDTH_ENABLED_F, width);
593d6b92ffaSHans Petter Selasky
594d6b92ffaSHans Petter Selasky if (port_args[VLS].set)
595d6b92ffaSHans Petter Selasky mad_set_field(data, 0, IB_PORT_OPER_VLS_F, vls);
596d6b92ffaSHans Petter Selasky if (port_args[MTU].set)
597d6b92ffaSHans Petter Selasky mad_set_field(data, 0, IB_PORT_NEIGHBOR_MTU_F, mtu);
598d6b92ffaSHans Petter Selasky if (port_args[LID].set)
599d6b92ffaSHans Petter Selasky mad_set_field(data, 0, IB_PORT_LID_F, lid);
600d6b92ffaSHans Petter Selasky if (port_args[SMLID].set)
601d6b92ffaSHans Petter Selasky mad_set_field(data, 0, IB_PORT_SMLID_F, smlid);
602d6b92ffaSHans Petter Selasky if (port_args[LMC].set)
603d6b92ffaSHans Petter Selasky mad_set_field(data, 0, IB_PORT_LMC_F, lmc);
604d6b92ffaSHans Petter Selasky
605d6b92ffaSHans Petter Selasky if (port_args[FDR10SPEED].set) {
606d6b92ffaSHans Petter Selasky mad_set_field(data2, 0,
607d6b92ffaSHans Petter Selasky IB_MLNX_EXT_PORT_STATE_CHG_ENABLE_F,
608d6b92ffaSHans Petter Selasky FDR10);
609d6b92ffaSHans Petter Selasky mad_set_field(data2, 0,
610d6b92ffaSHans Petter Selasky IB_MLNX_EXT_PORT_LINK_SPEED_ENABLED_F,
611d6b92ffaSHans Petter Selasky fdr10);
612d6b92ffaSHans Petter Selasky set_mlnx_ext_port_info(&portid, data2, portnum);
613d6b92ffaSHans Petter Selasky }
614d6b92ffaSHans Petter Selasky
615d6b92ffaSHans Petter Selasky if (port_args[MKEY].set)
616d6b92ffaSHans Petter Selasky mad_set_field64(data, 0, IB_PORT_MKEY_F, mkey);
617d6b92ffaSHans Petter Selasky if (port_args[MKEYLEASE].set)
618d6b92ffaSHans Petter Selasky mad_set_field(data, 0, IB_PORT_MKEY_LEASE_F,
619d6b92ffaSHans Petter Selasky mkeylease);
620d6b92ffaSHans Petter Selasky if (port_args[MKEYPROT].set)
621d6b92ffaSHans Petter Selasky mad_set_field(data, 0, IB_PORT_MKEY_PROT_BITS_F,
622d6b92ffaSHans Petter Selasky mkeyprot);
623d6b92ffaSHans Petter Selasky
624d6b92ffaSHans Petter Selasky set_port_info(&portid, data, portnum, espeed_cap, is_switch);
625d6b92ffaSHans Petter Selasky
626d6b92ffaSHans Petter Selasky } else if (is_switch && portnum) {
627d6b92ffaSHans Petter Selasky /* Now, make sure PortState is Active */
628d6b92ffaSHans Petter Selasky /* Or is PortPhysicalState LinkUp sufficient ? */
629d6b92ffaSHans Petter Selasky mad_decode_field(data, IB_PORT_STATE_F, &state);
630d6b92ffaSHans Petter Selasky mad_decode_field(data, IB_PORT_PHYS_STATE_F, &physstate);
631d6b92ffaSHans Petter Selasky if (state == 4) { /* Active */
632d6b92ffaSHans Petter Selasky mad_decode_field(data, IB_PORT_LINK_WIDTH_ENABLED_F,
633d6b92ffaSHans Petter Selasky &lwe);
634d6b92ffaSHans Petter Selasky mad_decode_field(data, IB_PORT_LINK_WIDTH_SUPPORTED_F,
635d6b92ffaSHans Petter Selasky &lws);
636d6b92ffaSHans Petter Selasky mad_decode_field(data, IB_PORT_LINK_WIDTH_ACTIVE_F,
637d6b92ffaSHans Petter Selasky &lwa);
638d6b92ffaSHans Petter Selasky mad_decode_field(data, IB_PORT_LINK_SPEED_SUPPORTED_F,
639d6b92ffaSHans Petter Selasky &lss);
640d6b92ffaSHans Petter Selasky mad_decode_field(data, IB_PORT_LINK_SPEED_ACTIVE_F,
641d6b92ffaSHans Petter Selasky &lsa);
642d6b92ffaSHans Petter Selasky mad_decode_field(data, IB_PORT_LINK_SPEED_ENABLED_F,
643d6b92ffaSHans Petter Selasky &lse);
644d6b92ffaSHans Petter Selasky mad_decode_field(data2,
645d6b92ffaSHans Petter Selasky IB_MLNX_EXT_PORT_LINK_SPEED_SUPPORTED_F,
646d6b92ffaSHans Petter Selasky &fdr10s);
647d6b92ffaSHans Petter Selasky mad_decode_field(data2,
648d6b92ffaSHans Petter Selasky IB_MLNX_EXT_PORT_LINK_SPEED_ENABLED_F,
649d6b92ffaSHans Petter Selasky &fdr10e);
650d6b92ffaSHans Petter Selasky mad_decode_field(data2,
651d6b92ffaSHans Petter Selasky IB_MLNX_EXT_PORT_LINK_SPEED_ACTIVE_F,
652d6b92ffaSHans Petter Selasky &fdr10a);
653d6b92ffaSHans Petter Selasky if (espeed_cap) {
654d6b92ffaSHans Petter Selasky mad_decode_field(data,
655d6b92ffaSHans Petter Selasky IB_PORT_LINK_SPEED_EXT_SUPPORTED_F,
656d6b92ffaSHans Petter Selasky &lses);
657d6b92ffaSHans Petter Selasky mad_decode_field(data,
658d6b92ffaSHans Petter Selasky IB_PORT_LINK_SPEED_EXT_ACTIVE_F,
659d6b92ffaSHans Petter Selasky &lsea);
660d6b92ffaSHans Petter Selasky mad_decode_field(data,
661d6b92ffaSHans Petter Selasky IB_PORT_LINK_SPEED_EXT_ENABLED_F,
662d6b92ffaSHans Petter Selasky &lsee);
663d6b92ffaSHans Petter Selasky }
664d6b92ffaSHans Petter Selasky
665d6b92ffaSHans Petter Selasky /* Setup portid for peer port */
666d6b92ffaSHans Petter Selasky memcpy(&peerportid, &portid, sizeof(peerportid));
667d6b92ffaSHans Petter Selasky if (portid.lid == 0) {
668d6b92ffaSHans Petter Selasky peerportid.drpath.cnt++;
669d6b92ffaSHans Petter Selasky if (peerportid.drpath.cnt == IB_SUBNET_PATH_HOPS_MAX) {
670d6b92ffaSHans Petter Selasky IBEXIT("Too many hops");
671d6b92ffaSHans Petter Selasky }
672d6b92ffaSHans Petter Selasky } else {
673d6b92ffaSHans Petter Selasky peerportid.drpath.cnt = 1;
674d6b92ffaSHans Petter Selasky
675d6b92ffaSHans Petter Selasky /* Set DrSLID to local lid */
676d6b92ffaSHans Petter Selasky if (resolve_self(ibd_ca, ibd_ca_port, &selfportid,
677d6b92ffaSHans Petter Selasky &selfport, 0) < 0)
678d6b92ffaSHans Petter Selasky IBEXIT("could not resolve self");
679d6b92ffaSHans Petter Selasky peerportid.drpath.drslid = (uint16_t) selfportid.lid;
680d6b92ffaSHans Petter Selasky peerportid.drpath.drdlid = 0xffff;
681d6b92ffaSHans Petter Selasky }
682d6b92ffaSHans Petter Selasky peerportid.drpath.p[peerportid.drpath.cnt] = (uint8_t) portnum;
683d6b92ffaSHans Petter Selasky
684d6b92ffaSHans Petter Selasky /* Get peer port NodeInfo to obtain peer port number */
685d6b92ffaSHans Petter Selasky is_peer_switch = get_node_info(&peerportid, data);
686d6b92ffaSHans Petter Selasky rem_vendorid = (uint32_t) mad_get_field(data, 0, IB_NODE_VENDORID_F);
687d6b92ffaSHans Petter Selasky rem_devid = (uint16_t) mad_get_field(data, 0, IB_NODE_DEVID_F);
688d6b92ffaSHans Petter Selasky
689d6b92ffaSHans Petter Selasky mad_decode_field(data, IB_NODE_LOCAL_PORT_F,
690d6b92ffaSHans Petter Selasky &peerlocalportnum);
691d6b92ffaSHans Petter Selasky
692d6b92ffaSHans Petter Selasky printf("Peer PortInfo:\n");
693d6b92ffaSHans Petter Selasky /* Get peer port characteristics */
694d6b92ffaSHans Petter Selasky peer_espeed_cap = get_port_info(&peerportid, data,
695d6b92ffaSHans Petter Selasky peerlocalportnum,
696d6b92ffaSHans Petter Selasky is_peer_switch);
697d6b92ffaSHans Petter Selasky if (is_mlnx_ext_port_info_supported(rem_vendorid, rem_devid))
698d6b92ffaSHans Petter Selasky get_mlnx_ext_port_info(&peerportid, data2,
699d6b92ffaSHans Petter Selasky peerlocalportnum);
700d6b92ffaSHans Petter Selasky show_port_info(&peerportid, data, peerlocalportnum,
701d6b92ffaSHans Petter Selasky peer_espeed_cap, is_peer_switch);
702d6b92ffaSHans Petter Selasky if (is_mlnx_ext_port_info_supported(rem_vendorid, rem_devid))
703d6b92ffaSHans Petter Selasky show_mlnx_ext_port_info(&peerportid, data2,
704d6b92ffaSHans Petter Selasky peerlocalportnum);
705d6b92ffaSHans Petter Selasky
706d6b92ffaSHans Petter Selasky mad_decode_field(data, IB_PORT_LINK_WIDTH_ENABLED_F,
707d6b92ffaSHans Petter Selasky &peerlwe);
708d6b92ffaSHans Petter Selasky mad_decode_field(data, IB_PORT_LINK_WIDTH_SUPPORTED_F,
709d6b92ffaSHans Petter Selasky &peerlws);
710d6b92ffaSHans Petter Selasky mad_decode_field(data, IB_PORT_LINK_WIDTH_ACTIVE_F,
711d6b92ffaSHans Petter Selasky &peerlwa);
712d6b92ffaSHans Petter Selasky mad_decode_field(data, IB_PORT_LINK_SPEED_SUPPORTED_F,
713d6b92ffaSHans Petter Selasky &peerlss);
714d6b92ffaSHans Petter Selasky mad_decode_field(data, IB_PORT_LINK_SPEED_ACTIVE_F,
715d6b92ffaSHans Petter Selasky &peerlsa);
716d6b92ffaSHans Petter Selasky mad_decode_field(data, IB_PORT_LINK_SPEED_ENABLED_F,
717d6b92ffaSHans Petter Selasky &peerlse);
718d6b92ffaSHans Petter Selasky mad_decode_field(data2,
719d6b92ffaSHans Petter Selasky IB_MLNX_EXT_PORT_LINK_SPEED_SUPPORTED_F,
720d6b92ffaSHans Petter Selasky &peerfdr10s);
721d6b92ffaSHans Petter Selasky mad_decode_field(data2,
722d6b92ffaSHans Petter Selasky IB_MLNX_EXT_PORT_LINK_SPEED_ENABLED_F,
723d6b92ffaSHans Petter Selasky &peerfdr10e);
724d6b92ffaSHans Petter Selasky mad_decode_field(data2,
725d6b92ffaSHans Petter Selasky IB_MLNX_EXT_PORT_LINK_SPEED_ACTIVE_F,
726d6b92ffaSHans Petter Selasky &peerfdr10a);
727d6b92ffaSHans Petter Selasky if (peer_espeed_cap) {
728d6b92ffaSHans Petter Selasky mad_decode_field(data,
729d6b92ffaSHans Petter Selasky IB_PORT_LINK_SPEED_EXT_SUPPORTED_F,
730d6b92ffaSHans Petter Selasky &peerlses);
731d6b92ffaSHans Petter Selasky mad_decode_field(data,
732d6b92ffaSHans Petter Selasky IB_PORT_LINK_SPEED_EXT_ACTIVE_F,
733d6b92ffaSHans Petter Selasky &peerlsea);
734d6b92ffaSHans Petter Selasky mad_decode_field(data,
735d6b92ffaSHans Petter Selasky IB_PORT_LINK_SPEED_EXT_ENABLED_F,
736d6b92ffaSHans Petter Selasky &peerlsee);
737d6b92ffaSHans Petter Selasky }
738d6b92ffaSHans Petter Selasky
739d6b92ffaSHans Petter Selasky /* Now validate peer port characteristics */
740d6b92ffaSHans Petter Selasky /* Examine Link Width */
741d6b92ffaSHans Petter Selasky width = get_link_width(lwe, lws);
742d6b92ffaSHans Petter Selasky peerwidth = get_link_width(peerlwe, peerlws);
743d6b92ffaSHans Petter Selasky validate_width(width, peerwidth, lwa);
744d6b92ffaSHans Petter Selasky
745d6b92ffaSHans Petter Selasky /* Examine Link Speeds */
746d6b92ffaSHans Petter Selasky speed = get_link_speed(lse, lss);
747d6b92ffaSHans Petter Selasky peerspeed = get_link_speed(peerlse, peerlss);
748d6b92ffaSHans Petter Selasky validate_speed(speed, peerspeed, lsa);
749d6b92ffaSHans Petter Selasky
750d6b92ffaSHans Petter Selasky if (espeed_cap && peer_espeed_cap) {
751d6b92ffaSHans Petter Selasky espeed = get_link_speed_ext(lsee, lses);
752d6b92ffaSHans Petter Selasky peerespeed = get_link_speed_ext(peerlsee,
753d6b92ffaSHans Petter Selasky peerlses);
754d6b92ffaSHans Petter Selasky validate_extended_speed(espeed, peerespeed,
755d6b92ffaSHans Petter Selasky lsea);
756d6b92ffaSHans Petter Selasky } else {
757d6b92ffaSHans Petter Selasky if (fdr10e & FDR10 && peerfdr10e & FDR10) {
758d6b92ffaSHans Petter Selasky if (!(fdr10a & FDR10))
759d6b92ffaSHans Petter Selasky IBWARN("Peer ports operating at active speed %d rather than FDR10", lsa);
760d6b92ffaSHans Petter Selasky }
761d6b92ffaSHans Petter Selasky }
762d6b92ffaSHans Petter Selasky }
763d6b92ffaSHans Petter Selasky }
764d6b92ffaSHans Petter Selasky
765d6b92ffaSHans Petter Selasky close_port:
766d6b92ffaSHans Petter Selasky mad_rpc_close_port(srcport);
767d6b92ffaSHans Petter Selasky exit(0);
768d6b92ffaSHans Petter Selasky }
769