]> git.proxmox.com Git - mirror_frr.git/blob - qpb/qpb.h
Merge pull request #3535 from kareiva/master
[mirror_frr.git] / qpb / qpb.h
1 /*
2 * qpb.h
3 *
4 * @copyright Copyright (C) 2016 Sproute Networks, Inc.
5 *
6 * @author Avneesh Sachdev <avneesh@sproute.com>
7 *
8 * This file is part of Quagga.
9 *
10 * Quagga is free software; you can redistribute it and/or modify it
11 * under the terms of the GNU General Public License as published by the
12 * Free Software Foundation; either version 2, or (at your option) any
13 * later version.
14 *
15 * Quagga is distributed in the hope that it will be useful, but
16 * WITHOUT ANY WARRANTY; without even the implied warranty of
17 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
18 * General Public License for more details.
19 *
20 * You should have received a copy of the GNU General Public License along
21 * with this program; see the file COPYING; if not, write to the Free Software
22 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
23 */
24
25 /*
26 * Main public header file for the quagga protobuf library.
27 */
28
29 #ifndef _QPB_H
30 #define _QPB_H
31
32 #include "prefix.h"
33
34 #include "qpb/qpb.pb-c.h"
35
36 #include "qpb/qpb_allocator.h"
37
38 /*
39 * qpb__address_family__set
40 */
41 #define qpb_address_family_set qpb__address_family__set
42 static inline int qpb__address_family__set(Qpb__AddressFamily *pb_family,
43 uint8_t family)
44 {
45 switch (family) {
46 case AF_INET:
47 *pb_family = QPB__ADDRESS_FAMILY__IPV4;
48 return 1;
49
50 case AF_INET6:
51 *pb_family = QPB__ADDRESS_FAMILY__IPV6;
52 return 1;
53
54 default:
55 *pb_family = QPB__ADDRESS_FAMILY__UNKNOWN_AF;
56 }
57
58 return 0;
59 }
60
61 /*
62 * qpb__address_family__get
63 */
64 #define qpb_address_family_get qpb__address_family__get
65 static inline int qpb__address_family__get(Qpb__AddressFamily pb_family,
66 uint8_t *family)
67 {
68
69 switch (pb_family) {
70 case QPB__ADDRESS_FAMILY__IPV4:
71 *family = AF_INET;
72 return 1;
73
74 case QPB__ADDRESS_FAMILY__IPV6:
75 *family = AF_INET6;
76 return 1;
77
78 case QPB__ADDRESS_FAMILY__UNKNOWN_AF:
79 return 0;
80 default: /* protobuf "magic value" _QPB__ADDRESS_FAMILY_IS_INT_SIZE */
81 return 0;
82 }
83
84 return 0;
85 }
86
87 /*
88 * qpb__l3_prefix__create
89 */
90 #define qpb_l3_prefix_create qpb__l3_prefix__create
91 static inline Qpb__L3Prefix *qpb__l3_prefix__create(qpb_allocator_t *allocator,
92 struct prefix *p)
93 {
94 Qpb__L3Prefix *prefix;
95
96 prefix = QPB_ALLOC(allocator, typeof(*prefix));
97 if (!prefix) {
98 return NULL;
99 }
100 qpb__l3_prefix__init(prefix);
101 prefix->length = p->prefixlen;
102 prefix->bytes.len = (p->prefixlen + 7) / 8;
103 prefix->bytes.data = qpb_alloc(allocator, prefix->bytes.len);
104 if (!prefix->bytes.data) {
105 return NULL;
106 }
107
108 memcpy(prefix->bytes.data, &p->u.prefix, prefix->bytes.len);
109
110 return prefix;
111 }
112
113 /*
114 * qpb__l3_prefix__get
115 */
116 #define qpb_l3_prefix_get qpb__l3_prefix__get
117 static inline int qpb__l3_prefix__get(const Qpb__L3Prefix *pb_prefix,
118 uint8_t family, struct prefix *prefix)
119 {
120
121 switch (family) {
122
123 case AF_INET:
124 memset(prefix, 0, sizeof(struct prefix_ipv4));
125 break;
126
127 case AF_INET6:
128 memset(prefix, 0, sizeof(struct prefix_ipv6));
129 break;
130
131 default:
132 memset(prefix, 0, sizeof(*prefix));
133 }
134
135 prefix->prefixlen = pb_prefix->length;
136 prefix->family = family;
137 memcpy(&prefix->u.prefix, pb_prefix->bytes.data, pb_prefix->bytes.len);
138 return 1;
139 }
140
141 /*
142 * qpb__protocol__set
143 *
144 * Translate a quagga route type to a protobuf protocol.
145 */
146 #define qpb_protocol_set qpb__protocol__set
147 static inline int qpb__protocol__set(Qpb__Protocol *pb_proto, int route_type)
148 {
149 switch (route_type) {
150 case ZEBRA_ROUTE_KERNEL:
151 *pb_proto = QPB__PROTOCOL__KERNEL;
152 break;
153
154 case ZEBRA_ROUTE_CONNECT:
155 *pb_proto = QPB__PROTOCOL__CONNECTED;
156 break;
157
158 case ZEBRA_ROUTE_STATIC:
159 *pb_proto = QPB__PROTOCOL__STATIC;
160 break;
161
162 case ZEBRA_ROUTE_RIP:
163 *pb_proto = QPB__PROTOCOL__RIP;
164 break;
165
166 case ZEBRA_ROUTE_RIPNG:
167 *pb_proto = QPB__PROTOCOL__RIPNG;
168 break;
169
170 case ZEBRA_ROUTE_OSPF:
171 case ZEBRA_ROUTE_OSPF6:
172 *pb_proto = QPB__PROTOCOL__OSPF;
173 break;
174
175 case ZEBRA_ROUTE_ISIS:
176 *pb_proto = QPB__PROTOCOL__ISIS;
177 break;
178
179 case ZEBRA_ROUTE_BGP:
180 *pb_proto = QPB__PROTOCOL__BGP;
181 break;
182
183 case ZEBRA_ROUTE_HSLS:
184 case ZEBRA_ROUTE_OLSR:
185 case ZEBRA_ROUTE_MAX:
186 case ZEBRA_ROUTE_SYSTEM:
187 default:
188 *pb_proto = QPB__PROTOCOL__OTHER;
189 }
190
191 return 1;
192 }
193
194 /*
195 * qpb__ipv4_address__create
196 */
197 static inline Qpb__Ipv4Address *
198 qpb__ipv4_address__create(qpb_allocator_t *allocator, struct in_addr *addr)
199 {
200 Qpb__Ipv4Address *v4;
201
202 v4 = QPB_ALLOC(allocator, typeof(*v4));
203 if (!v4) {
204 return NULL;
205 }
206 qpb__ipv4_address__init(v4);
207
208 v4->value = ntohl(addr->s_addr);
209 return v4;
210 }
211
212 /*
213 * qpb__ipv4_address__get
214 */
215 static inline int qpb__ipv4_address__get(const Qpb__Ipv4Address *v4,
216 struct in_addr *addr)
217 {
218 addr->s_addr = htonl(v4->value);
219 return 1;
220 }
221
222 /*
223 * qpb__ipv6_address__create
224 */
225 static inline Qpb__Ipv6Address *
226 qpb__ipv6_address__create(qpb_allocator_t *allocator, struct in6_addr *addr)
227 {
228 Qpb__Ipv6Address *v6;
229
230 v6 = QPB_ALLOC(allocator, typeof(*v6));
231 if (!v6)
232 return NULL;
233
234 qpb__ipv6_address__init(v6);
235 v6->bytes.len = 16;
236 v6->bytes.data = qpb_alloc(allocator, 16);
237 if (!v6->bytes.data)
238 return NULL;
239
240 memcpy(v6->bytes.data, addr->s6_addr, v6->bytes.len);
241 return v6;
242 }
243
244 /*
245 * qpb__ipv6_address__get
246 *
247 * Read out information from a protobuf ipv6 address structure.
248 */
249 static inline int qpb__ipv6_address__get(const Qpb__Ipv6Address *v6,
250 struct in6_addr *addr)
251 {
252 if (v6->bytes.len != 16)
253 return 0;
254
255 memcpy(addr->s6_addr, v6->bytes.data, v6->bytes.len);
256 return 1;
257 }
258
259 /*
260 * qpb__l3_address__create
261 */
262 #define qpb_l3_address_create qpb__l3_address__create
263 static inline Qpb__L3Address *
264 qpb__l3_address__create(qpb_allocator_t *allocator, union g_addr *addr,
265 uint8_t family)
266 {
267 Qpb__L3Address *l3_addr;
268
269 l3_addr = QPB_ALLOC(allocator, typeof(*l3_addr));
270 if (!l3_addr)
271 return NULL;
272
273 qpb__l3_address__init(l3_addr);
274
275 switch (family) {
276
277 case AF_INET:
278 l3_addr->v4 = qpb__ipv4_address__create(allocator, &addr->ipv4);
279 if (!l3_addr->v4)
280 return NULL;
281
282 break;
283
284 case AF_INET6:
285 l3_addr->v6 = qpb__ipv6_address__create(allocator, &addr->ipv6);
286 if (!l3_addr->v6)
287 return NULL;
288
289 break;
290 }
291 return l3_addr;
292 }
293
294 /*
295 * qpb__l3_address__get
296 *
297 * Read out a gateway address from a protobuf l3 address.
298 */
299 #define qpb_l3_address_get qpb__l3_address__get
300 static inline int qpb__l3_address__get(const Qpb__L3Address *l3_addr,
301 uint8_t *family, union g_addr *addr)
302 {
303 if (l3_addr->v4) {
304 qpb__ipv4_address__get(l3_addr->v4, &addr->ipv4);
305 *family = AF_INET;
306 return 1;
307 }
308
309 if (l3_addr->v6) {
310 qpb__ipv6_address__get(l3_addr->v6, &addr->ipv6);
311 *family = AF_INET6;
312 return 1;
313 }
314
315 return 0;
316 }
317
318 /*
319 * qpb__if_identifier__create
320 */
321 #define qpb_if_identifier_create qpb__if_identifier__create
322 static inline Qpb__IfIdentifier *
323 qpb__if_identifier__create(qpb_allocator_t *allocator, uint if_index)
324 {
325 Qpb__IfIdentifier *if_id;
326
327 if_id = QPB_ALLOC(allocator, typeof(*if_id));
328 if (!if_id) {
329 return NULL;
330 }
331 qpb__if_identifier__init(if_id);
332 if_id->has_index = 1;
333 if_id->index = if_index;
334 return if_id;
335 }
336
337 /*
338 * qpb__if_identifier__get
339 *
340 * Get interface name and/or if_index from an if identifier.
341 */
342 #define qpb_if_identifier_get qpb__if_identifier__get
343 static inline int qpb__if_identifier__get(Qpb__IfIdentifier *if_id,
344 uint *if_index, char **name)
345 {
346 char *str;
347 uint ix;
348
349 if (!if_index)
350 if_index = &ix;
351
352 if (!name)
353 name = &str;
354
355 if (if_id->has_index)
356 *if_index = if_id->index;
357 else
358 *if_index = 0;
359
360 *name = if_id->name;
361 return 1;
362 }
363
364 #endif