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 <string.h> 42#include <pthread.h> 43#include <sys/time.h> 44 45#include <mad.h> 46#include <infiniband/common.h> 47 48#undef DEBUG 49#define DEBUG if (ibdebug) IBWARN 50 51static inline int 52response_expected(int method) 53{ 54 return method == IB_MAD_METHOD_GET || 55 method == IB_MAD_METHOD_SET || 56 method == IB_MAD_METHOD_TRAP; 57} 58 59uint8_t * 60ib_vendor_call(void *data, ib_portid_t *portid, ib_vendor_call_t *call) 61{ 62 ib_rpc_t rpc = {0}; 63 int range1 = 0, resp_expected; 64 65 DEBUG("route %s data %p", portid2str(portid), data); 66 if (portid->lid <= 0) 67 return 0; /* no direct SMI */ 68 69 if (!(range1 = mad_is_vendor_range1(call->mgmt_class)) && 70 !(mad_is_vendor_range2(call->mgmt_class))) 71 return 0; 72 73 resp_expected = response_expected(call->method); 74 75 rpc.mgtclass = call->mgmt_class; 76 77 rpc.method = call->method; 78 rpc.attr.id = call->attrid; 79 rpc.attr.mod = call->mod; 80 rpc.timeout = resp_expected ? call->timeout : 0; 81 rpc.datasz = range1 ? IB_VENDOR_RANGE1_DATA_SIZE : IB_VENDOR_RANGE2_DATA_SIZE; 82 rpc.dataoffs = range1 ? IB_VENDOR_RANGE1_DATA_OFFS : IB_VENDOR_RANGE2_DATA_OFFS; 83 84 if (!range1) 85 rpc.oui = call->oui; 86 87 DEBUG("class 0x%x method 0x%x attr 0x%x mod 0x%x datasz %d off %d res_ex %d", 88 rpc.mgtclass, rpc.method, rpc.attr.id, rpc.attr.mod, 89 rpc.datasz, rpc.dataoffs, resp_expected); 90 91 portid->qp = 1; 92 if (!portid->qkey) 93 portid->qkey = IB_DEFAULT_QP1_QKEY; 94 95 if (resp_expected) 96 return madrpc_rmpp(&rpc, portid, 0, data); /* FIXME: no RMPP for now */ 97 98 return mad_send(&rpc, portid, 0, data) < 0 ? 0 : data; /* FIXME: no RMPP for now */ 99} 100