FD.io VPP  v18.01-8-g0eacf49
Vector Packet Processing
fib_node.c
Go to the documentation of this file.
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 #include <vnet/fib/fib_node.h>
17 #include <vnet/fib/fib_node_list.h>
18 #include <vnet/fib/fib_table.h>
19 #include <vnet/mfib/mfib_table.h>
20 
21 /*
22  * The per-type vector of virtual function tables
23  */
25 
26 /**
27  * The last registered new type
28  */
30 
31 /*
32  * the node type names
33  */
34 static const char *fn_type_names[] = FIB_NODE_TYPES;
35 
36 const char*
38 {
39  if (type < FIB_NODE_TYPE_LAST)
40  return (fn_type_names[type]);
41  else
42  {
43  if (NULL != fn_vfts[type].fnv_format)
44  {
45  return ("fixme");
46  }
47  else
48  {
49  return ("unknown");
50  }
51  }
52 }
53 
54 /**
55  * fib_node_register_type
56  *
57  * Register the function table for a given type
58  */
59 void
61  const fib_node_vft_t *vft)
62 {
63  /*
64  * assert that one only registration is made per-node type
65  */
66  if (vec_len(fn_vfts) > type)
67  ASSERT(NULL == fn_vfts[type].fnv_get);
68 
69  /*
70  * Assert that we are getting each of the required functions
71  */
72  ASSERT(NULL != vft->fnv_get);
73  ASSERT(NULL != vft->fnv_last_lock);
74 
75  vec_validate(fn_vfts, type);
76  fn_vfts[type] = *vft;
77 }
78 
81 {
82  fib_node_type_t new_type;
83 
84  new_type = ++last_new_type;
85 
86  fib_node_register_type(new_type, vft);
87 
88  return (new_type);
89 }
90 
91 static u8*
93 {
94  return (format(s, "{%s:%d}", fn_type_names[fnp->fnp_type], fnp->fnp_index));
95 }
96 
97 u32
99  fib_node_index_t parent_index,
100  fib_node_type_t type,
101  fib_node_index_t index)
102 {
103  fib_node_t *parent;
104 
105  parent = fn_vfts[parent_type].fnv_get(parent_index);
106 
107  /*
108  * return the index of the sibling in the child list
109  */
110  fib_node_lock(parent);
111 
112  if (FIB_NODE_INDEX_INVALID == parent->fn_children)
113  {
114  parent->fn_children = fib_node_list_create();
115  }
116 
117  return (fib_node_list_push_front(parent->fn_children,
118  0, type,
119  index));
120 }
121 
122 void
124  fib_node_index_t parent_index,
125  fib_node_index_t sibling_index)
126 {
127  fib_node_t *parent;
128 
129  parent = fn_vfts[parent_type].fnv_get(parent_index);
130 
131  fib_node_list_remove(parent->fn_children, sibling_index);
132 
133  if (0 == fib_node_list_get_size(parent->fn_children))
134  {
136  }
137 
138  fib_node_unlock(parent);
139 }
140 
141 u32
143  fib_node_index_t parent_index)
144 {
145  fib_node_t *parent;
146 
147  parent = fn_vfts[parent_type].fnv_get(parent_index);
148 
149  return (fib_node_list_get_size(parent->fn_children));
150 }
151 
152 
156 {
157  fib_node_t *node;
158 
159  node = fn_vfts[ptr->fnp_type].fnv_get(ptr->fnp_index);
160 
161  return (fn_vfts[ptr->fnp_type].fnv_back_walk(node, ctx));
162 }
163 
164 static int
166  void *arg)
167 {
168  u8 **s = (u8**) arg;
169 
170  *s = fib_node_format(ptr, *s);
171 
172  return (1);
173 }
174 
175 u8*
177  u8 *s)
178 {
180 
181  return (s);
182 }
183 
184 void
186  fib_node_type_t type)
187 {
188  /**
189  * The node's type. used to retrieve the VFT.
190  */
191  node->fn_type = type;
192  node->fn_locks = 0;
194 }
195 
196 void
198 {
200 }
201 
202 void
204 {
205  node->fn_locks++;
206 }
207 
208 void
210 {
211  node->fn_locks--;
212 
213  if (0 == node->fn_locks)
214  {
215  fn_vfts[node->fn_type].fnv_last_lock(node);
216  }
217 }
218 
219 void
220 fib_show_memory_usage (const char *name,
221  u32 in_use_elts,
222  u32 allocd_elts,
223  size_t size_elt)
224 {
225  vlib_cli_output (vlib_get_main(), "%=30s %=5d %=8d/%=9d %d/%d ",
226  name, size_elt,
227  in_use_elts, allocd_elts,
228  in_use_elts*size_elt, allocd_elts*size_elt);
229 }
230 
231 static clib_error_t *
233  unformat_input_t * input,
234  vlib_cli_command_t * cmd)
235 {
236  fib_node_vft_t *vft;
237 
238  vlib_cli_output (vm, "FIB memory");
239  vlib_cli_output (vm, " Tables:");
240  vlib_cli_output (vm, "%=30s %=6s %=8s", "SAFI", "Number", "Bytes");
243  vlib_cli_output (vm, " Nodes:");
244  vlib_cli_output (vm, "%=30s %=5s %=8s/%=9s totals",
245  "Name","Size", "in-use", "allocated");
246 
247  vec_foreach(vft, fn_vfts)
248  {
249  if (NULL != vft->fnv_mem_show)
250  vft->fnv_mem_show();
251  }
252 
254 
255  return (NULL);
256 }
257 
258 /* *INDENT-OFF* */
259 /*?
260  * The '<em>sh fib memory </em>' command displays the memory usage for each
261  * FIB object type.
262  *
263  * @cliexpar
264  * @cliexstart{show fib memory}
265  *FIB memory
266  * Tables:
267  * SAFI Number Bytes
268  * IPv4 unicast 2 673066
269  * IPv6 unicast 2 1054608
270  * MPLS 1 4194312
271  * IPv4 multicast 2 2322
272  * IPv6 multicast 2 ???
273  * Nodes:
274  * Name Size in-use /allocated totals
275  * Entry 96 20 / 20 1920/1920
276  * Entry Source 32 0 / 0 0/0
277  * Entry Path-Extensions 60 0 / 0 0/0
278  * multicast-Entry 192 12 / 12 2304/2304
279  * Path-list 40 28 / 28 1120/1120
280  * uRPF-list 16 20 / 20 320/320
281  * Path 72 28 / 28 2016/2016
282  * Node-list elements 20 28 / 28 560/560
283  * Node-list heads 8 30 / 30 240/240
284  * @cliexend
285 ?*/
286 VLIB_CLI_COMMAND (show_fib_memory, static) = {
287  .path = "show fib memory",
288  .function = fib_memory_show,
289  .short_help = "show fib memory",
290 };
291 /* *INDENT-ON* */
#define vec_validate(V, I)
Make sure vector is long enough for given index (no header, unspecified alignment) ...
Definition: vec.h:432
static fib_node_type_t last_new_type
The last registered new type.
Definition: fib_node.c:29
void fib_node_init(fib_node_t *node, fib_node_type_t type)
Definition: fib_node.c:185
#define NULL
Definition: clib.h:55
enum fib_node_back_walk_rc_t_ fib_node_back_walk_rc_t
Return code from a back walk function.
void fib_node_list_memory_show(void)
void fib_node_deinit(fib_node_t *node)
Definition: fib_node.c:197
u8 * format(u8 *s, const char *fmt,...)
Definition: format.c:419
static fib_node_vft_t * fn_vfts
Definition: fib_node.c:24
void fib_node_list_walk(fib_node_list_t list, fib_node_list_walk_cb_t fn, void *args)
Walk the list of node.
fib_node_type_t fib_node_register_new_type(const fib_node_vft_t *vft)
Create a new FIB node type and Register the function table for it.
Definition: fib_node.c:80
u32 fib_node_child_add(fib_node_type_t parent_type, fib_node_index_t parent_index, fib_node_type_t type, fib_node_index_t index)
Definition: fib_node.c:98
void fib_node_register_type(fib_node_type_t type, const fib_node_vft_t *vft)
fib_node_register_type
Definition: fib_node.c:60
fib_node_index_t fnp_index
node&#39;s index
Definition: fib_node.h:188
void fib_node_list_remove(fib_node_list_t list, u32 sibling)
fib_node_back_walk_rc_t fib_node_back_walk_one(fib_node_ptr_t *ptr, fib_node_back_walk_ctx_t *ctx)
Definition: fib_node.c:154
fib_node_last_lock_gone_t fnv_last_lock
Definition: fib_node.h:275
void fib_show_memory_usage(const char *name, u32 in_use_elts, u32 allocd_elts, size_t size_elt)
Show the memory usage for a type.
Definition: fib_node.c:220
A representation of one pointer to another node.
Definition: fib_node.h:180
#define FIB_NODE_TYPES
Definition: fib_node.h:59
fib_node_type_t fnp_type
node type
Definition: fib_node.h:184
void fib_node_lock(fib_node_t *node)
Definition: fib_node.c:203
struct _unformat_input_t unformat_input_t
u32 fib_node_list_push_front(fib_node_list_t list, int owner_id, fib_node_type_t type, fib_node_index_t index)
Insert an element at the from of the list.
fib_node_type_t fn_type
The node&#39;s type.
Definition: fib_node.h:290
static const char * fn_type_names[]
Definition: fib_node.c:34
An node in the FIB graph.
Definition: fib_node.h:286
void fib_node_unlock(fib_node_t *node)
Definition: fib_node.c:209
fib_node_list_t fn_children
The node&#39;s VFT.
Definition: fib_node.h:306
vlib_main_t * vm
Definition: buffer.c:283
u8 * format_mfib_table_memory(u8 *s, va_list *args)
format (display) the memory usage for mfibs
Definition: mfib_table.c:632
fib_node_get_t fnv_get
Definition: fib_node.h:274
fib_node_back_walk_t fnv_back_walk
Definition: fib_node.h:276
u32 fib_node_index_t
A typedef of a node index.
Definition: fib_types.h:29
u8 * format_fib_table_memory(u8 *s, va_list *args)
format (display) the memory used by the FIB tables
Definition: fib_table.c:1301
u32 fib_node_get_n_children(fib_node_type_t parent_type, fib_node_index_t parent_index)
Definition: fib_node.c:142
Context passed between object during a back walk.
Definition: fib_node.h:199
#define VLIB_CLI_COMMAND(x,...)
Definition: cli.h:154
u32 fib_node_list_get_size(fib_node_list_t list)
static clib_error_t * fib_memory_show(vlib_main_t *vm, unformat_input_t *input, vlib_cli_command_t *cmd)
Definition: fib_node.c:232
#define ASSERT(truth)
fib_node_list_t fib_node_list_create(void)
Create a new node list.
unsigned int u32
Definition: types.h:88
long ctx[MAX_CONNS]
Definition: main.c:122
static int fib_node_ptr_format_one_child(fib_node_ptr_t *ptr, void *arg)
Definition: fib_node.c:165
void fib_node_list_destroy(fib_node_list_t *list)
void fib_node_child_remove(fib_node_type_t parent_type, fib_node_index_t parent_index, fib_node_index_t sibling_index)
Definition: fib_node.c:123
static vlib_main_t * vlib_get_main(void)
Definition: global_funcs.h:23
#define FIB_NODE_INDEX_INVALID
Definition: fib_types.h:30
#define vec_len(v)
Number of elements in vector (rvalue-only, NULL tolerant)
unsigned char u8
Definition: types.h:56
u32 fn_locks
Number of dependents on this node.
Definition: fib_node.h:312
A FIB graph nodes virtual function table.
Definition: fib_node.h:273
static u8 * fib_node_format(fib_node_ptr_t *fnp, u8 *s)
Definition: fib_node.c:92
enum fib_node_type_t_ fib_node_type_t
The types of nodes in a FIB graph.
u32 fib_node_list_t
A list of FIB nodes.
Definition: fib_node.h:194
#define vec_foreach(var, vec)
Vector iterator.
u8 * fib_node_children_format(fib_node_list_t list, u8 *s)
Definition: fib_node.c:176
void vlib_cli_output(vlib_main_t *vm, char *fmt,...)
Definition: cli.c:680
const char * fib_node_type_get_name(fib_node_type_t type)
Definition: fib_node.c:37
fib_node_memory_show_t fnv_mem_show
Definition: fib_node.h:278