1 /*
2 * Copyright (c) 2005 MontaVista Software, Inc.
3 * Copyright (c) 2006-2007, 2009 Red Hat, Inc.
4 *
5 * All rights reserved.
6 *
7 * Author: Steven Dake (sdake@redhat.com)
8 *
9 * This software licensed under BSD license, the text of which follows:
10 *
11 * Redistribution and use in source and binary forms, with or without
12 * modification, are permitted provided that the following conditions are met:
13 *
14 * - Redistributions of source code must retain the above copyright notice,
15 * this list of conditions and the following disclaimer.
16 * - Redistributions in binary form must reproduce the above copyright notice,
17 * this list of conditions and the following disclaimer in the documentation
18 * and/or other materials provided with the distribution.
19 * - Neither the name of the MontaVista Software, Inc. nor the names of its
20 * contributors may be used to endorse or promote products derived from this
21 * software without specific prior written permission.
22 *
23 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
24 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
25 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
26 * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
27 * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
28 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
29 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
30 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
31 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
32 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
33 * THE POSSIBILITY OF SUCH DAMAGE.
34 */
35
36 #include <config.h>
37
38 #include <sys/mman.h>
39 #include <sys/types.h>
40 #include <sys/stat.h>
41 #include <sys/socket.h>
42 #include <netdb.h>
43 #include <sys/un.h>
44 #include <sys/ioctl.h>
45 #include <sys/param.h>
46 #include <netinet/in.h>
47 #include <arpa/inet.h>
48 #include <unistd.h>
49 #include <fcntl.h>
50 #include <stdlib.h>
51 #include <stdio.h>
52 #include <errno.h>
53 #include <sched.h>
54 #include <time.h>
55 #include <sys/time.h>
56 #include <sys/poll.h>
57
58 #include <corosync/totem/totem.h>
59 #include <qb/qbloop.h>
60
61 #include "totemmrp.h"
62 #include "totemsrp.h"
63
64 void *totemsrp_context;
65
66 void totemmrp_deliver_fn (
67 unsigned int nodeid,
68 const void *msg,
69 unsigned int msg_len,
70 int endian_conversion_required);
71
72 void totemmrp_confchg_fn (
73 enum totem_configuration_type configuration_type,
74 const unsigned int *member_list, size_t member_list_entries,
75 const unsigned int *left_list, size_t left_list_entries,
76 const unsigned int *joined_list, size_t joined_list_entries,
77 const struct memb_ring_id *ring_id);
78
79 void (*pg_deliver_fn) (
80 unsigned int nodeid,
81 const void *msg,
82 unsigned int msg_len,
83 int endian_conversion_required) = 0;
84
85 void (*pg_confchg_fn) (
86 enum totem_configuration_type configuration_type,
87 const unsigned int *member_list, size_t member_list_entries,
88 const unsigned int *left_list, size_t left_list_entries,
89 const unsigned int *joined_list, size_t joined_list_entries,
90 const struct memb_ring_id *ring_id) = 0;
91
totemmrp_deliver_fn(unsigned int nodeid,const void * msg,unsigned int msg_len,int endian_conversion_required)92 void totemmrp_deliver_fn (
93 unsigned int nodeid,
94 const void *msg,
95 unsigned int msg_len,
96 int endian_conversion_required)
97 {
98 pg_deliver_fn (nodeid, msg, msg_len, endian_conversion_required);
99 }
100
totemmrp_confchg_fn(enum totem_configuration_type configuration_type,const unsigned int * member_list,size_t member_list_entries,const unsigned int * left_list,size_t left_list_entries,const unsigned int * joined_list,size_t joined_list_entries,const struct memb_ring_id * ring_id)101 void totemmrp_confchg_fn (
102 enum totem_configuration_type configuration_type,
103 const unsigned int *member_list, size_t member_list_entries,
104 const unsigned int *left_list, size_t left_list_entries,
105 const unsigned int *joined_list, size_t joined_list_entries,
106 const struct memb_ring_id *ring_id)
107 {
108 pg_confchg_fn (configuration_type,
109 member_list, member_list_entries,
110 left_list, left_list_entries,
111 joined_list, joined_list_entries,
112 ring_id);
113 }
114
115 /*
116 * Initialize the totem multiple ring protocol
117 */
totemmrp_initialize(qb_loop_t * poll_handle,struct totem_config * totem_config,totempg_stats_t * stats,void (* deliver_fn)(unsigned int nodeid,const void * msg,unsigned int msg_len,int endian_conversion_required),void (* confchg_fn)(enum totem_configuration_type configuration_type,const unsigned int * member_list,size_t member_list_entries,const unsigned int * left_list,size_t left_list_entries,const unsigned int * joined_list,size_t joined_list_entries,const struct memb_ring_id * ring_id),void (* waiting_trans_ack_cb_fn)(int waiting_trans_ack))118 int totemmrp_initialize (
119 qb_loop_t *poll_handle,
120 struct totem_config *totem_config,
121 totempg_stats_t *stats,
122
123 void (*deliver_fn) (
124 unsigned int nodeid,
125 const void *msg,
126 unsigned int msg_len,
127 int endian_conversion_required),
128 void (*confchg_fn) (
129 enum totem_configuration_type configuration_type,
130 const unsigned int *member_list, size_t member_list_entries,
131 const unsigned int *left_list, size_t left_list_entries,
132 const unsigned int *joined_list, size_t joined_list_entries,
133 const struct memb_ring_id *ring_id),
134 void (*waiting_trans_ack_cb_fn) (
135 int waiting_trans_ack))
136 {
137 int result;
138 pg_deliver_fn = deliver_fn;
139 pg_confchg_fn = confchg_fn;
140
141 stats->mrp = calloc (sizeof(totemmrp_stats_t), 1);
142 result = totemsrp_initialize (
143 poll_handle,
144 &totemsrp_context,
145 totem_config,
146 stats->mrp,
147 totemmrp_deliver_fn,
148 totemmrp_confchg_fn,
149 waiting_trans_ack_cb_fn);
150
151 return (result);
152 }
153
totemmrp_finalize(void)154 void totemmrp_finalize (void)
155 {
156 totemsrp_finalize (totemsrp_context);
157 }
158
159 /*
160 * Multicast a message
161 */
totemmrp_mcast(struct iovec * iovec,unsigned int iov_len,int priority)162 int totemmrp_mcast (
163 struct iovec *iovec,
164 unsigned int iov_len,
165 int priority)
166 {
167 return totemsrp_mcast (totemsrp_context, iovec, iov_len, priority);
168 }
169
170 /*
171 * Return number of available messages that can be queued
172 */
totemmrp_avail(void)173 int totemmrp_avail (void)
174 {
175 return (totemsrp_avail (totemsrp_context));
176 }
177
totemmrp_callback_token_create(void ** handle_out,enum totem_callback_token_type type,int delete,int (* callback_fn)(enum totem_callback_token_type type,const void *),const void * data)178 int totemmrp_callback_token_create (
179 void **handle_out,
180 enum totem_callback_token_type type,
181 int delete,
182 int (*callback_fn) (enum totem_callback_token_type type, const void *),
183 const void *data)
184 {
185 return totemsrp_callback_token_create (totemsrp_context, handle_out, type, delete, callback_fn, data);
186 }
187
totemmrp_callback_token_destroy(void * handle_out)188 void totemmrp_callback_token_destroy (
189 void *handle_out)
190 {
191 totemsrp_callback_token_destroy (totemsrp_context, handle_out);
192 }
193
totemmrp_event_signal(enum totem_event_type type,int value)194 void totemmrp_event_signal (enum totem_event_type type, int value)
195 {
196 totemsrp_event_signal (totemsrp_context, type, value);
197 }
198
totemmrp_ifaces_get(unsigned int nodeid,struct totem_ip_address * interfaces,unsigned int interfaces_size,char *** status,unsigned int * iface_count)199 int totemmrp_ifaces_get (
200 unsigned int nodeid,
201 struct totem_ip_address *interfaces,
202 unsigned int interfaces_size,
203 char ***status,
204 unsigned int *iface_count)
205 {
206 int res;
207
208 res = totemsrp_ifaces_get (
209 totemsrp_context,
210 nodeid,
211 interfaces,
212 interfaces_size,
213 status,
214 iface_count);
215
216 return (res);
217 }
218
totemmrp_crypto_set(const char * cipher_type,const char * hash_type)219 int totemmrp_crypto_set (
220 const char *cipher_type,
221 const char *hash_type)
222 {
223 return totemsrp_crypto_set (totemsrp_context,
224 cipher_type,
225 hash_type);
226 }
227
totemmrp_my_nodeid_get(void)228 unsigned int totemmrp_my_nodeid_get (void)
229 {
230 return (totemsrp_my_nodeid_get (totemsrp_context));
231 }
232
totemmrp_my_family_get(void)233 int totemmrp_my_family_get (void)
234 {
235 return (totemsrp_my_family_get (totemsrp_context));
236 }
237
totemmrp_ring_reenable(void)238 extern int totemmrp_ring_reenable (void)
239 {
240 int res;
241
242 res = totemsrp_ring_reenable (
243 totemsrp_context);
244
245 return (res);
246 }
247
totemmrp_service_ready_register(void (* totem_service_ready)(void))248 extern void totemmrp_service_ready_register (
249 void (*totem_service_ready) (void))
250 {
251 totemsrp_service_ready_register (
252 totemsrp_context,
253 totem_service_ready);
254 }
255
totemmrp_member_add(const struct totem_ip_address * member,int ring_no)256 int totemmrp_member_add (
257 const struct totem_ip_address *member,
258 int ring_no)
259 {
260 int res;
261
262 res = totemsrp_member_add (totemsrp_context, member, ring_no);
263
264 return (res);
265 }
266
totemmrp_member_remove(const struct totem_ip_address * member,int ring_no)267 int totemmrp_member_remove (
268 const struct totem_ip_address *member,
269 int ring_no)
270 {
271 int res;
272
273 res = totemsrp_member_remove (totemsrp_context, member, ring_no);
274
275 return (res);
276 }
277
totemmrp_threaded_mode_enable(void)278 void totemmrp_threaded_mode_enable (void)
279 {
280 totemsrp_threaded_mode_enable (totemsrp_context);
281 }
282
totemmrp_trans_ack(void)283 void totemmrp_trans_ack (void)
284 {
285 totemsrp_trans_ack (totemsrp_context);
286 }
287