1 /*
2 *
3 * Copyright (c) 2003 The Regents of the University of California. All
4 * rights reserved.
5 *
6 * Redistribution and use in source and binary forms, with or without
7 * modification, are permitted provided that the following conditions
8 * are met:
9 *
10 * - Redistributions of source code must retain the above copyright
11 * notice, this list of conditions and the following disclaimer.
12 *
13 * - Neither the name of the University nor the names of its
14 * contributors may be used to endorse or promote products derived
15 * from this software without specific prior written permission.
16 *
17 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS''
18 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
19 * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
20 * PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR
21 * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
22 * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
23 * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
24 * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
25 * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
26 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
27 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
28 *
29 */
30
31
32 #include <stdlib.h>
33 #include <stdio.h>
34 #include <ctype.h>
35 #include <assert.h>
36
37 #include <sys/types.h>
38 #include <sys/socket.h>
39 #include <arpa/inet.h>
40 #include <netinet/in.h>
41
42 #include <emrun/emrun.h>
43
44 #include <glib.h>
45 #include <libmisc/local_types.h>
46 #include "libmisc/misc.h"
47
48 #include "common.h"
49 #include "hash.h"
50
51 #define MY_LOG_LEVEL LOG_DEBUG(4)
52
53
54 /* callback, invoked when walking the neighborlist (in order to construct a
55 * linked list of neighbors)
56 *
57 * key is pointer id of the neighbor,
58 * value is pointer to neighbor structure
59 * user_data is our pointer to the head of the list
60 */
61 static void
62 prepend_neighbor_to_list(gpointer key, gpointer value, gpointer user_data)
63 {
64 gls_neighbor_t *n;
65
66 assert(value);
67 assert(* (GSList **)user_data);
68
69 /* g_malloc0 aborts program on error */
70 n = g_malloc0(sizeof(gls_neighbor_t));
71
72 /* make a copy of the neighbor element */
73 *n = * (gls_neighbor_t *)value;
74
75 * (GSList **)user_data = g_slist_prepend(* (GSList **)user_data,
76 (gpointer)n);
77 }
78
79
80 /* see explanation in the header file (on declaration) */
81 GSList *
82 alloc_neighbor_list_from_table(GHashTable *neighbor_table)
83 {
84 GSList *neighborlist = NULL;
85
86 assert(neighbor_table);
87
88 /* NOTE: because we PREpend elements to the list, after we're done we'll end
89 * up with a pointer to the first element in the list stored in the
90 * u->neighbors. That's just the way glib's lists work... */
91 g_hash_table_foreach(neighbor_table, prepend_neighbor_to_list,
92 (gpointer)&(neighborlist));
93
94 return neighborlist;
95 }
96
97 /* typedef struct nbr_pf { */
98 /* gls_neighbor_t *n; */
99 /* buf_t *b; */
100 /* } nbr_pf_t; */
101
102 /* prints a single neighbor */
103 static void
104 neighbor_print_func(gpointer key, gpointer value, gpointer user_data)
105 {
106 /* we're not concerned with keys here */
107 gls_neighbor_t *n = value;
108 buf_t *b = (buf_t *)user_data;
109
110 assert(n);
111 bufprintf(b,"%lu,", n->id);
112 }
113
114 void
115 print_neighborlist(struct nodeconf *cfg, buf_t *bf)
116 {
117 /* nbr_pf_t npf = { */
118 /* n: cfg->neighbor_list, */
119 /* b: bf, */
120 /* }; */
121
122 assert(cfg);
123
124 bufprintf(bf,"NBR: ");
125 if (cfg->neighbor_list)
126 {
127 // g_hash_table_foreach((gpointer)npf, neighbor_print_func, NULL);
128 g_hash_table_foreach(cfg->neighbor_list, neighbor_print_func, (gpointer)bf);
129 }
130 }
131
132 void
133 print_geo(geo_t *geo, buf_t *bf)
134 {
135 assert(geo);
136 bufprintf(bf,"GEO:(%f, %f): ", loc_expand(geo->x), loc_expand(geo->y));
137 }
138
139 void
140 print_udp(struct udp_info *udp)
141 {
142 char buf[INET_ADDRSTRLEN];
143 assert(udp);
144 /* this should never fail, as we know AF_INET is supported by inet_ntop and
145 * size of the buffer is that recommended in the man page */
146 assert(inet_ntop(AF_INET, &(udp->ip), buf, sizeof buf));
147 /* inet_ntop null-terminates */
148 elog_g(MY_LOG_LEVEL,"UDP : %s:%u", buf, ntohs(udp->port));
149 }
150
151 void
152 print_nodeconf(struct nodeconf *cfg)
153 {
154 buf_t *bf = buf_new();
155
156 assert(cfg);
157 bufprintf(bf,"ID:%lu: ", (unsigned long int)cfg->id);
158 print_geo(&cfg->geo, bf);
159 // bufprintf(bf,"\n");
160 // print_udp(&cfg->udp);
161 // bufprintf(bf,"\n");
162 print_neighborlist(cfg,bf);
163 elog_g(MY_LOG_LEVEL, "%s",bf->buf);
164 buf_free(bf);
165
166 }
167
168 void
169 destroy_neighbor(gpointer data)
170 {
171 if (data)
172 {
173 g_free(data);
174 }
175 }
176
177 void
178 init_nodeconf(struct nodeconf *cfg)
179 {
180 assert(cfg);
181
182 cfg->id = UINT32_MAX;
183 cfg->udp.ip.s_addr = UINT32_MAX;
184 cfg->udp.port = UINT16_MAX;
185 cfg->geo.x = UINT16_MAX;
186 cfg->geo.y = UINT16_MAX;
187
188 /* create the neighborlist hashtable */
189 if (! (cfg->neighbor_list = g_hash_table_new_full(hash_u32,
190 hash_compare_u32,
191 NULL /* key destroy */,
192 destroy_neighbor)))
193 {
194 elog_g(LOG_NOTICE,"Error creating a neighbor table for %lu\n",
195 (unsigned long )cfg->id);
196 assert(0);
197 }
198
199 cfg->use_cartesian_symmetric_weights = FALSE;
200 }
201
202 void
203 destroy_nodeconf(struct nodeconf *cfg)
204 {
205 assert(cfg);
206 assert(cfg->neighbor_list);
207 /* individual nodes are destroyed through callbacks registered at the time
208 * the table was created */
209 g_hash_table_destroy(cfg->neighbor_list);
210 }
211
212 static void
213 global_table_entry_print_func(gpointer key, gpointer value, gpointer user_data)
214 {
215 /* we dont care to print the 'key's, only the values */
216 struct nodeconf *cfg = value;
217
218 assert(cfg);
219 print_nodeconf(cfg);
220 }
221
222 void
223 print_global_table(GHashTable *table)
224 {
225 assert(table);
226 g_hash_table_foreach(table, global_table_entry_print_func, NULL);
227 }
228
229
This page was automatically generated by the
LXR engine.
Visit the LXR main site for more
information.