BIER API and load-balancing fixes
[vpp.git] / src / vnet / bier / bier_table.h
1 /*
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 __BIER_TABLE_H__
17 #define __BIER_TABLE_H__
18
19 #include <vlib/vlib.h>
20 #include <vnet/fib/fib_types.h>
21 #include <vnet/bier/bier_types.h>
22 #include <vnet/bier/bier_entry.h>
23
24 #include <vnet/dpo/dpo.h>
25
26 /**
27  * Forward declarations
28  */
29 struct bier_route_update_t_;
30
31 /**
32  * A BIER Table is the bit-indexed forwarding table.
33  * Each entry (bit-position) represents one destination, and its reachability
34  *
35  * The number of entries in a table is thus the maximum supported
36  * bit-position. Since this is smal <4096, the table is a flat arry
37  */
38 typedef struct bier_table_t_ {
39     /**
40      * required for pool_get_aligned.
41      *  memebers used in the switch path come first!
42      */
43     CLIB_CACHE_LINE_ALIGN_MARK(cacheline0);
44
45     /**
46      * Save the MPLS local label associated with the table
47      */
48     mpls_label_t bt_ll;
49
50     /**
51      * The path-list used for the ECMP-tables
52      */
53     fib_node_index_t bt_pl;
54
55     /**
56      * The index of the lfib entry created for this table.
57      * Only the EOS is required.
58      */
59     fib_node_index_t bt_lfei;
60
61     /**
62      * Number of locks on the table
63      */
64     u16 bt_locks;
65
66     /**
67      * Entries in the table
68      * This is a vector sized to the appropriate number of entries
69      * given the table's supported Bit-string length
70      */
71     index_t *bt_entries;
72
73     /**
74      * The identity/key or the table. we need the hdr_len in the data-path
75      */
76     bier_table_id_t bt_id;
77
78     /**
79      * f-masks in the ECMP table
80      * This is a vector sized to the appropriate number of entries
81      * given the table's supported Bit-string length.
82      * In the ECMP table the LB choice has been pre-resolved, so each entry
83      * links to just one f-mask, i.e. there is a 1:1 mapping of bit-position to
84      * fmask. For efficient forwarding we collapse the fmasks up to the table.
85      */
86     index_t *bt_fmasks;
87 } bier_table_t;
88
89 STATIC_ASSERT((sizeof(bier_table_t) <= 2*CLIB_CACHE_LINE_BYTES),
90               "BIER table fits on 2 cache lines");
91
92 extern index_t bier_table_add_or_lock(const bier_table_id_t *id,
93                                       mpls_label_t ll);
94 extern void bier_table_unlock(const bier_table_id_t *id);
95
96 extern void bier_table_route_path_add(const bier_table_id_t *bti,
97                                       bier_bp_t bp,
98                                       fib_route_path_t *brp);
99 extern void bier_table_route_path_remove(const bier_table_id_t *bti,
100                                          bier_bp_t bp,
101                                          fib_route_path_t *brp);
102 extern void bier_table_route_path_update(const bier_table_id_t *bti,
103                                          bier_bp_t bp,
104                                          fib_route_path_t *brp);
105 extern void bier_table_route_delete(const bier_table_id_t *bti,
106                                     bier_bp_t b);
107
108 extern void bier_table_show_all(vlib_main_t * vm,
109                                 bier_show_flags_t flags);
110
111 extern const bier_table_id_t *bier_table_get_id(index_t bti);
112
113 extern u8 *format_bier_table (u8 *s, va_list *args);
114 extern u8 *format_bier_table_entry (u8 *s, va_list *args);
115
116 extern index_t bier_table_ecmp_create_and_lock(const bier_table_id_t *id);
117 extern void bier_table_ecmp_unlock(index_t bti);
118 extern void bier_table_ecmp_set_fmask(index_t bti,
119                                       bier_bp_t bp,
120                                       index_t bfmi);
121
122 extern void bier_table_contribute_forwarding(index_t bti,
123                                              dpo_id_t *dpo);
124
125 /**
126  * Types and functions to walk the ECMP tables of a main table
127  */
128 typedef void (*bier_table_ecmp_walk_fn_t)(index_t btei,
129                                           void *ctx);
130 extern void bier_table_ecmp_walk(index_t bti,
131                                  bier_table_ecmp_walk_fn_t fn,
132                                  void *ctx);
133 extern int bier_table_is_main (const bier_table_t *bt);
134
135 /**
136  * Types and functions to walk all the BIER Tables
137  */
138 typedef void (*bier_tables_walk_fn_t)(const bier_table_t *bt,
139                                       void *ctx);
140 extern void bier_tables_walk(bier_tables_walk_fn_t fn,
141                              void *ctx);
142
143 /**
144  * Types and functions to walk all the entries in one BIER Table
145  */
146 typedef void (*bier_table_walk_fn_t)(const bier_table_t *bt,
147                                      const bier_entry_t *be,
148                                      void *ctx);
149 extern void bier_table_walk(const bier_table_id_t *id,
150                             bier_table_walk_fn_t fn,
151                             void *ctx);
152
153 /*
154  * provided for fast data plane access.
155  */
156 extern bier_table_t *bier_table_pool;
157
158 static inline bier_table_t *
159 bier_table_get (index_t bti)
160 {
161     return (pool_elt_at_index(bier_table_pool, bti));
162 }
163
164 static inline const index_t
165 bier_table_lookup (const bier_table_t *bt,
166                    bier_bp_t bp)
167 {
168     return (bt->bt_entries[BIER_BP_TO_INDEX(bp)]);
169 }
170
171 static inline const index_t
172 bier_table_fwd_lookup (const bier_table_t *bt,
173                        bier_bp_t bp)
174 {
175     return (bt->bt_fmasks[BIER_BP_TO_INDEX(bp)]);
176 }
177
178 #endif