blob: e7e66acb773ee0f851d9b29c3b150d34dea83009 [file] [log] [blame]
Neale Ranns0bfe5d82016-08-25 15:29:12 +01001/*
2 * Copyright (c) 2016 Cisco and/or its affiliates.
3 * Licensed under the Apache License, Version 2.0 (the "License");
4 * you may not use this file except in compliance with the License.
5 * You may obtain a copy of the License at:
6 *
7 * http://www.apache.org/licenses/LICENSE-2.0
8 *
9 * Unless required by applicable law or agreed to in writing, software
10 * distributed under the License is distributed on an "AS IS" BASIS,
11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 * See the License for the specific language governing permissions and
13 * limitations under the License.
14 */
15
16#ifndef __FIB_TABLE_H__
17#define __FIB_TABLE_H__
18
19#include <vnet/ip/ip.h>
20#include <vnet/adj/adj.h>
21#include <vnet/fib/fib_entry.h>
22#include <vnet/mpls/mpls.h>
23#include <vnet/mpls/packet.h>
24
25/**
26 * @brief
27 * A protocol Independent FIB table
28 */
29typedef struct fib_table_t_
30{
31 /**
32 * A union of the protocol specific FIBs that provide the
33 * underlying LPM mechanism.
34 * This element is first in the struct so that it is in the
35 * first cache line.
36 */
37 union {
38 ip4_fib_t v4;
39 ip6_fib_t v6;
40 mpls_fib_t mpls;
41 };
42
43 /**
44 * Which protocol this table serves. Used to switch on the union above.
45 */
46 fib_protocol_t ft_proto;
47
48 /**
49 * number of locks on the table
50 */
51 u16 ft_locks;
52
53 /**
54 * Table ID (hash key) for this FIB.
55 */
56 u32 ft_table_id;
57
58 /**
59 * Index into FIB vector.
60 */
61 fib_node_index_t ft_index;
62
63 /**
64 * flow hash configuration
65 */
66 u32 ft_flow_hash_config;
67
68 /**
69 * Per-source route counters
70 */
71 u32 ft_src_route_counts[FIB_SOURCE_MAX];
72
73 /**
74 * Total route counters
75 */
76 u32 ft_total_route_counts;
77
78 /**
79 * Table description
80 */
81 u8* ft_desc;
82} fib_table_t;
83
84/**
85 * @brief
86 * Format the description/name of the table
87 */
88extern u8* format_fib_table_name(u8* s, va_list ap);
89
90/**
91 * @brief
92 * Perfom a longest prefix match in the non-forwarding table
93 *
94 * @param fib_index
95 * The index of the FIB
96 *
97 * @param prefix
98 * The prefix to lookup
99 *
100 * @return
101 * The index of the fib_entry_t for the best match, which may be the default route
102 */
103extern fib_node_index_t fib_table_lookup(u32 fib_index,
104 const fib_prefix_t *prefix);
105
106/**
107 * @brief
108 * Perfom an exact match in the non-forwarding table
109 *
110 * @param fib_index
111 * The index of the FIB
112 *
113 * @param prefix
114 * The prefix to lookup
115 *
116 * @return
117 * The index of the fib_entry_t for the exact match, or INVALID
118 * is there is no match.
119 */
120extern fib_node_index_t fib_table_lookup_exact_match(u32 fib_index,
121 const fib_prefix_t *prefix);
122
123/**
124 * @brief
125 * Get the less specific (covering) prefix
126 *
127 * @param fib_index
128 * The index of the FIB
129 *
130 * @param prefix
131 * The prefix to lookup
132 *
133 * @return
134 * The index of the less specific fib_entry_t.
135 */
136extern fib_node_index_t fib_table_get_less_specific(u32 fib_index,
137 const fib_prefix_t *prefix);
138
139/**
140 * @brief
141 * Add a 'special' entry to the FIB that links to the adj passed
142 * A special entry is an entry that the FIB is not expect to resolve
143 * via the usual mechanisms (i.e. recurisve or neighbour adj DB lookup).
144 * Instead the client/source provides the adj to link to.
145 * This add is reference counting per-source. So n 'removes' are required
146 * for n 'adds', if the entry is no longer required.
147 *
148 * @param fib_index
149 * The index of the FIB
150 *
151 * @param prefix
152 * The prefix to add
153 *
154 * @param source
155 * The ID of the client/source adding the entry.
156 *
157 * @param flags
158 * Flags for the entry.
159 *
160 * @param adj_index
161 * The adjacency to link to.
162 *
163 * @return
164 * the index of the fib_entry_t that is created (or exists already).
165 */
166extern fib_node_index_t fib_table_entry_special_add(u32 fib_index,
167 const fib_prefix_t *prefix,
168 fib_source_t source,
169 fib_entry_flag_t flags,
170 adj_index_t adj_index);
171
172/**
173 * @brief
174 * Add a 'special' entry to the FIB that links to the DPO passed
175 * A special entry is an entry that the FIB is not expect to resolve
176 * via the usual mechanisms (i.e. recurisve or neighbour adj DB lookup).
177 * Instead the client/source provides the DPO to link to.
178 * This add is reference counting per-source. So n 'removes' are required
179 * for n 'adds', if the entry is no longer required.
180 *
181 * @param fib_index
182 * The index of the FIB
183 *
184 * @param prefix
185 * The prefix to add
186 *
187 * @param source
188 * The ID of the client/source adding the entry.
189 *
190 * @param flags
191 * Flags for the entry.
192 *
193 * @param dpo
194 * The DPO to link to.
195 *
196 * @return
197 * the index of the fib_entry_t that is created (or existed already).
198 */
199extern fib_node_index_t fib_table_entry_special_dpo_add(u32 fib_index,
200 const fib_prefix_t *prefix,
201 fib_source_t source,
202 fib_entry_flag_t stype,
203 const dpo_id_t *dpo);
204
205/**
206 * @brief
207 * Update a 'special' entry to the FIB that links to the DPO passed
208 * A special entry is an entry that the FIB is not expect to resolve
209 * via the usual mechanisms (i.e. recurisve or neighbour adj DB lookup).
210 * Instead the client/source provides the DPO to link to.
211 * Special entries are add/remove reference counted per-source. So n
212 * 'removes' are required for n 'adds', if the entry is no longer required.
Neale Ranns948e00f2016-10-20 13:39:34 +0100213 * An 'update' is an 'add' if no 'add' has already been called, otherwise an 'add'
214 * is therefore assumed to act on the reference instance of that add.
Neale Ranns0bfe5d82016-08-25 15:29:12 +0100215 *
216 * @param fib_entry_index
217 * The index of the FIB entry to update
218 *
219 * @param source
220 * The ID of the client/source adding the entry.
221 *
222 * @param flags
223 * Flags for the entry.
224 *
225 * @param dpo
226 * The DPO to link to.
227 *
228 * @return
229 * the index of the fib_entry_t that is created (or existed already).
230 */
Neale Ranns948e00f2016-10-20 13:39:34 +0100231extern fib_node_index_t fib_table_entry_special_dpo_update (u32 fib_index,
232 const fib_prefix_t *prefix,
233 fib_source_t source,
234 fib_entry_flag_t stype,
235 const dpo_id_t *dpo);
Neale Ranns0bfe5d82016-08-25 15:29:12 +0100236
237/**
238 * @brief
239 * Remove a 'special' entry from the FIB.
240 * This add is reference counting per-source. So n 'removes' are required
241 * for n 'adds', if the entry is no longer required.
242 *
243 * @param fib_index
244 * The index of the FIB
245 *
246 * @param prefix
247 * The prefix to remove
248 *
249 * @param source
250 * The ID of the client/source adding the entry.
251 *
252 */
253extern void fib_table_entry_special_remove(u32 fib_index,
254 const fib_prefix_t *prefix,
255 fib_source_t source);
256
257/**
258 * @brief
259 * Add one path to an entry (aka route) in the FIB. If the entry does not
260 * exist, it will be created.
261 * See the documentation for fib_route_path_t for more descirptions of
262 * the path parameters.
263 *
264 * @param fib_index
265 * The index of the FIB
266 *
267 * @param prefix
268 * The prefix for the entry to add
269 *
270 * @param source
271 * The ID of the client/source adding the entry.
272 *
273 * @param flags
274 * Flags for the entry.
275 *
276 * @paran next_hop_proto
277 * The protocol of the next hop. This cannot be derived in the event that
278 * the next hop is all zeros.
279 *
280 * @param next_hop
281 * The address of the next-hop.
282 *
283 * @param sw_if_index
284 * The index of the interface.
285 *
286 * @param next_hop_fib_index,
287 * The fib index of the next-hop for recursive resolution
288 *
289 * @param next_hop_weight
290 * [un]equal cost path weight
291 *
Neale Rannsad422ed2016-11-02 14:20:04 +0000292 * @param next_hop_label_stack
293 * The path's out-going label stack. NULL is there is none.
Neale Ranns0bfe5d82016-08-25 15:29:12 +0100294 *
295 * @param pf
296 * Flags for the path
297 *
298 * @return
299 * the index of the fib_entry_t that is created (or existed already).
300 */
301extern fib_node_index_t fib_table_entry_path_add(u32 fib_index,
302 const fib_prefix_t *prefix,
303 fib_source_t source,
304 fib_entry_flag_t flags,
305 fib_protocol_t next_hop_proto,
306 const ip46_address_t *next_hop,
307 u32 next_hop_sw_if_index,
308 u32 next_hop_fib_index,
309 u32 next_hop_weight,
Neale Rannsad422ed2016-11-02 14:20:04 +0000310 mpls_label_t *next_hop_label_stack,
Neale Ranns0bfe5d82016-08-25 15:29:12 +0100311 fib_route_path_flags_t pf);
312/**
313 * @brief
314 * Add n paths to an entry (aka route) in the FIB. If the entry does not
315 * exist, it will be created.
316 * See the documentation for fib_route_path_t for more descirptions of
317 * the path parameters.
318 *
319 * @param fib_index
320 * The index of the FIB
321 *
322 * @param prefix
323 * The prefix for the entry to add
324 *
325 * @param source
326 * The ID of the client/source adding the entry.
327 *
328 * @param flags
329 * Flags for the entry.
330 *
331 * @param rpaths
Neale Rannsad422ed2016-11-02 14:20:04 +0000332 * A vector of paths. Not const since they may be modified.
Neale Ranns0bfe5d82016-08-25 15:29:12 +0100333 *
334 * @return
335 * the index of the fib_entry_t that is created (or existed already).
336 */
337extern fib_node_index_t fib_table_entry_path_add2(u32 fib_index,
338 const fib_prefix_t *prefix,
339 fib_source_t source,
340 fib_entry_flag_t flags,
Neale Rannsad422ed2016-11-02 14:20:04 +0000341 fib_route_path_t *rpath);
Neale Ranns0bfe5d82016-08-25 15:29:12 +0100342
343/**
344 * @brief
345 * remove one path to an entry (aka route) in the FIB. If this is the entry's
346 * last path, then the entry will be removed, unless it has other sources.
347 * See the documentation for fib_route_path_t for more descirptions of
348 * the path parameters.
349 *
350 * @param fib_index
351 * The index of the FIB
352 *
353 * @param prefix
354 * The prefix for the entry to add
355 *
356 * @param source
357 * The ID of the client/source adding the entry.
358 *
359 * @paran next_hop_proto
360 * The protocol of the next hop. This cannot be derived in the event that
361 * the next hop is all zeros.
362 *
363 * @param next_hop
364 * The address of the next-hop.
365 *
366 * @param sw_if_index
367 * The index of the interface.
368 *
369 * @param next_hop_fib_index,
370 * The fib index of the next-hop for recursive resolution
371 *
372 * @param next_hop_weight
373 * [un]equal cost path weight
374 *
375 * @param pf
376 * Flags for the path
377 */
378extern void fib_table_entry_path_remove(u32 fib_index,
379 const fib_prefix_t *prefix,
380 fib_source_t source,
381 fib_protocol_t next_hop_proto,
382 const ip46_address_t *next_hop,
383 u32 next_hop_sw_if_index,
384 u32 next_hop_fib_index,
385 u32 next_hop_weight,
386 fib_route_path_flags_t pf);
387
388/**
389 * @brief
390 * Remove n paths to an entry (aka route) in the FIB. If this is the entry's
391 * last path, then the entry will be removed, unless it has other sources.
392 * See the documentation for fib_route_path_t for more descirptions of
393 * the path parameters.
394 *
395 * @param fib_index
396 * The index of the FIB
397 *
398 * @param prefix
399 * The prefix for the entry to add
400 *
401 * @param source
402 * The ID of the client/source adding the entry.
403 *
404 * @param rpaths
405 * A vector of paths.
406 */
407extern void fib_table_entry_path_remove2(u32 fib_index,
408 const fib_prefix_t *prefix,
409 fib_source_t source,
Neale Rannsad422ed2016-11-02 14:20:04 +0000410 fib_route_path_t *paths);
Neale Ranns0bfe5d82016-08-25 15:29:12 +0100411
412/**
413 * @brief
414 * Update an entry to have a new set of paths. If the entry does not
415 * exist, it will be created.
416 * The difference between an 'path-add' and an update, is that path-add is
417 * an incremental addition of paths, whereas an update is a wholesale swap.
418 *
419 * @param fib_index
420 * The index of the FIB
421 *
422 * @param prefix
423 * The prefix for the entry to add
424 *
425 * @param source
426 * The ID of the client/source adding the entry.
427 *
428 * @param rpaths
Neale Rannsad422ed2016-11-02 14:20:04 +0000429 * A vector of paths. Not const since they may be modified.
Neale Ranns0bfe5d82016-08-25 15:29:12 +0100430 *
431 * @return
432 * the index of the fib_entry_t that is created (or existed already).
433 */
434extern fib_node_index_t fib_table_entry_update(u32 fib_index,
435 const fib_prefix_t *prefix,
436 fib_source_t source,
437 fib_entry_flag_t flags,
Neale Rannsad422ed2016-11-02 14:20:04 +0000438 fib_route_path_t *paths);
Neale Ranns0bfe5d82016-08-25 15:29:12 +0100439
440/**
441 * @brief
442 * Update the entry to have just one path. If the entry does not
443 * exist, it will be created.
444 * See the documentation for fib_route_path_t for more descirptions of
445 * the path parameters.
446 *
447 * @param fib_index
448 * The index of the FIB
449 *
450 * @param prefix
451 * The prefix for the entry to add
452 *
453 * @param source
454 * The ID of the client/source adding the entry.
455 *
456 * @param flags
457 * Flags for the entry.
458 *
459 * @paran next_hop_proto
460 * The protocol of the next hop. This cannot be derived in the event that
461 * the next hop is all zeros.
462 *
463 * @param next_hop
464 * The address of the next-hop.
465 *
466 * @param sw_if_index
467 * The index of the interface.
468 *
469 * @param next_hop_fib_index,
470 * The fib index of the next-hop for recursive resolution
471 *
472 * @param next_hop_weight
473 * [un]equal cost path weight
474 *
Neale Rannsad422ed2016-11-02 14:20:04 +0000475 * @param next_hop_label_stack
476 * The path's out-going label stack. NULL is there is none.
Neale Ranns0bfe5d82016-08-25 15:29:12 +0100477 *
478 * @param pf
479 * Flags for the path
480 *
481 * @return
482 * the index of the fib_entry_t that is created (or existed already).
483 */
484extern fib_node_index_t fib_table_entry_update_one_path(u32 fib_index,
485 const fib_prefix_t *prefix,
486 fib_source_t source,
487 fib_entry_flag_t flags,
488 fib_protocol_t next_hop_proto,
489 const ip46_address_t *next_hop,
490 u32 next_hop_sw_if_index,
491 u32 next_hop_fib_index,
492 u32 next_hop_weight,
Neale Rannsad422ed2016-11-02 14:20:04 +0000493 mpls_label_t *next_hop_label_stack,
Neale Ranns0bfe5d82016-08-25 15:29:12 +0100494 fib_route_path_flags_t pf);
495
496/**
497 * @brief
498 * Add a MPLS local label for the prefix/route. If the entry does not
499 * exist, it will be created. In theory more than one local label can be
500 * added, but this is not yet supported.
501 *
502 * @param fib_index
503 * The index of the FIB
504 *
505 * @param prefix
506 * The prefix for the entry to which to add the label
507 *
508 * @param label
509 * The MPLS label to add
510 *
511 * @return
512 * the index of the fib_entry_t that is created (or existed already).
513 */
514extern fib_node_index_t fib_table_entry_local_label_add(u32 fib_index,
515 const fib_prefix_t *prefix,
516 mpls_label_t label);
517/**
518 * @brief
519 * remove a MPLS local label for the prefix/route.
520 *
521 * @param fib_index
522 * The index of the FIB
523 *
524 * @param prefix
525 * The prefix for the entry to which to add the label
526 *
527 * @param label
528 * The MPLS label to add
529 */
530extern void fib_table_entry_local_label_remove(u32 fib_index,
531 const fib_prefix_t *prefix,
532 mpls_label_t label);
533
534/**
535 * @brief
536 * Delete a FIB entry. If the entry has no more sources, then it is
537 * removed from the table.
538 *
539 * @param fib_index
540 * The index of the FIB
541 *
542 * @param prefix
543 * The prefix for the entry to remove
544 *
545 * @param source
546 * The ID of the client/source adding the entry.
547 */
548extern void fib_table_entry_delete(u32 fib_index,
549 const fib_prefix_t *prefix,
550 fib_source_t source);
551
552/**
553 * @brief
554 * Delete a FIB entry. If the entry has no more sources, then it is
555 * removed from the table.
556 *
557 * @param entry_index
558 * The index of the FIB entry
559 *
560 * @param source
561 * The ID of the client/source adding the entry.
562 */
563extern void fib_table_entry_delete_index(fib_node_index_t entry_index,
564 fib_source_t source);
565
566/**
567 * @brief
568 * Flush all entries from a table for the source
569 *
570 * @param fib_index
571 * The index of the FIB
572 *
573 * @paran proto
574 * The protocol of the entries in the table
575 *
576 * @param source
577 * the source to flush
578 */
579extern void fib_table_flush(u32 fib_index,
580 fib_protocol_t proto,
581 fib_source_t source);
582
583/**
584 * @brief
585 * Get the index of the FIB bound to the interface
586 *
587 * @paran proto
588 * The protocol of the FIB (and thus the entries therein)
589 *
590 * @param sw_if_index
591 * The interface index
592 *
593 * @return fib_index
594 * The index of the FIB
595 */
596extern u32 fib_table_get_index_for_sw_if_index(fib_protocol_t proto,
597 u32 sw_if_index);
598
599/**
600 * @brief
601 * Get the Table-ID of the FIB bound to the interface
602 *
603 * @paran proto
604 * The protocol of the FIB (and thus the entries therein)
605 *
606 * @param sw_if_index
607 * The interface index
608 *
609 * @return fib_index
610 * The tableID of the FIB
611 */
612extern u32 fib_table_get_table_id_for_sw_if_index(fib_protocol_t proto,
613 u32 sw_if_index);
614
615/**
616 * @brief
617 * Get the index of the FIB for a Table-ID. This DOES NOT create the
618 * FIB if it does not exist.
619 *
620 * @paran proto
621 * The protocol of the FIB (and thus the entries therein)
622 *
623 * @param table-id
624 * The Table-ID
625 *
626 * @return fib_index
627 * The index of the FIB, which may be INVALID.
628 */
629extern u32 fib_table_find(fib_protocol_t proto, u32 table_id);
630
631
632/**
633 * @brief
634 * Get the index of the FIB for a Table-ID. This DOES create the
635 * FIB if it does not exist.
636 *
637 * @paran proto
638 * The protocol of the FIB (and thus the entries therein)
639 *
640 * @param table-id
641 * The Table-ID
642 *
643 * @return fib_index
644 * The index of the FIB
645 */
646extern u32 fib_table_find_or_create_and_lock(fib_protocol_t proto,
647 u32 table_id);
648
649/**
650 * @brief
651 * Create a new table with no table ID. This means it does not get
652 * added to the hash-table and so can only be found by using the index returned.
653 *
654 * @paran proto
655 * The protocol of the FIB (and thus the entries therein)
656 *
657 * @param fmt
658 * A string to describe the table
659 *
660 * @return fib_index
661 * The index of the FIB
662 */
663extern u32 fib_table_create_and_lock(fib_protocol_t proto,
664 const char *const fmt,
665 ...);
666
667/**
668 * @brief
669 * Get the flow hash configured used by the table
670 *
671 * @param fib_index
672 * The index of the FIB
673 *
674 * @paran proto
675 * The protocol of the FIB (and thus the entries therein)
676 *
677 * @return The flow hash config
678 */
679extern flow_hash_config_t fib_table_get_flow_hash_config(u32 fib_index,
680 fib_protocol_t proto);
681
682/**
683 * @brief
684 * Take a reference counting lock on the table
685 *
686 * @param fib_index
687 * The index of the FIB
688 *
689 * @paran proto
690 * The protocol of the FIB (and thus the entries therein)
691 */
692extern void fib_table_unlock(u32 fib_index,
693 fib_protocol_t proto);
694
695/**
696 * @brief
697 * Release a reference counting lock on the table. When the last lock
698 * has gone. the FIB is deleted.
699 *
700 * @param fib_index
701 * The index of the FIB
702 *
703 * @paran proto
704 * The protocol of the FIB (and thus the entries therein)
705 */
706extern void fib_table_lock(u32 fib_index,
707 fib_protocol_t proto);
708
709/**
710 * @brief
711 * Return the number of entries in the FIB added by a given source.
712 *
713 * @param fib_index
714 * The index of the FIB
715 *
716 * @paran proto
717 * The protocol of the FIB (and thus the entries therein)
718 *
719 * @return number of sourced entries.
720 */
721extern u32 fib_table_get_num_entries(u32 fib_index,
722 fib_protocol_t proto,
723 fib_source_t source);
724
725/**
726 * @brief
727 * Get a pointer to a FIB table
728 */
729extern fib_table_t *fib_table_get(fib_node_index_t index,
730 fib_protocol_t proto);
731
Neale Ranns32e1c012016-11-22 17:07:28 +0000732/**
733 * @brief Call back function when walking entries in a FIB table
734 */
735typedef int (*fib_table_walk_fn_t)(fib_node_index_t fei,
736 void *ctx);
737
738/**
739 * @brief Walk all entries in a FIB table
740 * N.B: This is NOT safe to deletes. If you need to delete walk the whole
741 * table and store elements in a vector, then delete the elements
742 */
743extern void fib_table_walk(u32 fib_index,
744 fib_protocol_t proto,
745 fib_table_walk_fn_t fn,
746 void *ctx);
747
Neale Ranns0bfe5d82016-08-25 15:29:12 +0100748#endif