]> CyberLeo.Net >> Repos - FreeBSD/releng/10.0.git/blob - contrib/ofed/management/opensm/opensm/osm_mad_pool.c
- Copy stable/10 (r259064) to releng/10.0 as part of the
[FreeBSD/releng/10.0.git] / contrib / ofed / management / opensm / opensm / osm_mad_pool.c
1 /*
2  * Copyright (c) 2004-2008 Voltaire, Inc. All rights reserved.
3  * Copyright (c) 2002-2005 Mellanox Technologies LTD. All rights reserved.
4  * Copyright (c) 1996-2003 Intel Corporation. All rights reserved.
5  *
6  * This software is available to you under a choice of one of two
7  * licenses.  You may choose to be licensed under the terms of the GNU
8  * General Public License (GPL) Version 2, available from the file
9  * COPYING in the main directory of this source tree, or the
10  * OpenIB.org BSD license below:
11  *
12  *     Redistribution and use in source and binary forms, with or
13  *     without modification, are permitted provided that the following
14  *     conditions are met:
15  *
16  *      - Redistributions of source code must retain the above
17  *        copyright notice, this list of conditions and the following
18  *        disclaimer.
19  *
20  *      - Redistributions in binary form must reproduce the above
21  *        copyright notice, this list of conditions and the following
22  *        disclaimer in the documentation and/or other materials
23  *        provided with the distribution.
24  *
25  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
26  * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
27  * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
28  * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
29  * BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
30  * ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
31  * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
32  * SOFTWARE.
33  *
34  */
35
36 /*
37  * Abstract:
38  *    Implementation of osm_mad_pool_t.
39  * This object represents a pool of management datagram (MAD) objects.
40  * This object is part of the opensm family of objects.
41  */
42
43 #if HAVE_CONFIG_H
44 #  include <config.h>
45 #endif                          /* HAVE_CONFIG_H */
46
47 #include <stdlib.h>
48 #include <string.h>
49 #include <opensm/osm_mad_pool.h>
50 #include <opensm/osm_madw.h>
51 #include <vendor/osm_vendor_api.h>
52
53 /**********************************************************************
54  **********************************************************************/
55 void osm_mad_pool_construct(IN osm_mad_pool_t * const p_pool)
56 {
57         CL_ASSERT(p_pool);
58
59         memset(p_pool, 0, sizeof(*p_pool));
60 }
61
62 /**********************************************************************
63  **********************************************************************/
64 void osm_mad_pool_destroy(IN osm_mad_pool_t * const p_pool)
65 {
66         CL_ASSERT(p_pool);
67 }
68
69 /**********************************************************************
70  **********************************************************************/
71 ib_api_status_t osm_mad_pool_init(IN osm_mad_pool_t * const p_pool)
72 {
73         p_pool->mads_out = 0;
74
75         return IB_SUCCESS;
76 }
77
78 /**********************************************************************
79  **********************************************************************/
80 osm_madw_t *osm_mad_pool_get(IN osm_mad_pool_t * const p_pool,
81                              IN osm_bind_handle_t h_bind,
82                              IN const uint32_t total_size,
83                              IN const osm_mad_addr_t * const p_mad_addr)
84 {
85         osm_madw_t *p_madw;
86         ib_mad_t *p_mad;
87
88         CL_ASSERT(h_bind != OSM_BIND_INVALID_HANDLE);
89         CL_ASSERT(total_size);
90
91         /*
92            First, acquire a mad wrapper from the mad wrapper pool.
93          */
94         p_madw = malloc(sizeof(*p_madw));
95         if (p_madw == NULL)
96                 goto Exit;
97
98         osm_madw_init(p_madw, h_bind, total_size, p_mad_addr);
99
100         /*
101            Next, acquire a wire mad of the specified size.
102          */
103         p_mad = osm_vendor_get(h_bind, total_size, &p_madw->vend_wrap);
104         if (p_mad == NULL) {
105                 /* Don't leak wrappers! */
106                 free(p_madw);
107                 p_madw = NULL;
108                 goto Exit;
109         }
110
111         cl_atomic_inc(&p_pool->mads_out);
112         /*
113            Finally, attach the wire MAD to this wrapper.
114          */
115         osm_madw_set_mad(p_madw, p_mad);
116
117 Exit:
118         return p_madw;
119 }
120
121 /**********************************************************************
122  **********************************************************************/
123 osm_madw_t *osm_mad_pool_get_wrapper(IN osm_mad_pool_t * const p_pool,
124                                      IN osm_bind_handle_t h_bind,
125                                      IN const uint32_t total_size,
126                                      IN const ib_mad_t * const p_mad,
127                                      IN const osm_mad_addr_t * const p_mad_addr)
128 {
129         osm_madw_t *p_madw;
130
131         CL_ASSERT(h_bind != OSM_BIND_INVALID_HANDLE);
132         CL_ASSERT(total_size);
133         CL_ASSERT(p_mad);
134
135         /*
136            First, acquire a mad wrapper from the mad wrapper pool.
137          */
138         p_madw = malloc(sizeof(*p_madw));
139         if (p_madw == NULL)
140                 goto Exit;
141
142         /*
143            Finally, initialize the wrapper object.
144          */
145         cl_atomic_inc(&p_pool->mads_out);
146         osm_madw_init(p_madw, h_bind, total_size, p_mad_addr);
147         osm_madw_set_mad(p_madw, p_mad);
148
149 Exit:
150         return (p_madw);
151 }
152
153 /**********************************************************************
154  **********************************************************************/
155 osm_madw_t *osm_mad_pool_get_wrapper_raw(IN osm_mad_pool_t * const p_pool)
156 {
157         osm_madw_t *p_madw;
158
159         p_madw = malloc(sizeof(*p_madw));
160         if (!p_madw)
161                 return NULL;
162
163         osm_madw_init(p_madw, 0, 0, 0);
164         osm_madw_set_mad(p_madw, 0);
165         cl_atomic_inc(&p_pool->mads_out);
166
167         return (p_madw);
168 }
169
170 /**********************************************************************
171  **********************************************************************/
172 void
173 osm_mad_pool_put(IN osm_mad_pool_t * const p_pool, IN osm_madw_t * const p_madw)
174 {
175         CL_ASSERT(p_madw);
176
177         /*
178            First, return the wire mad to the pool
179          */
180         if (p_madw->p_mad)
181                 osm_vendor_put(p_madw->h_bind, &p_madw->vend_wrap);
182
183         /*
184            Return the mad wrapper to the wrapper pool
185          */
186         free(p_madw);
187         cl_atomic_dec(&p_pool->mads_out);
188 }