blob: 3b08f4b0089e63d4d705dfb05643492f2af8a5bd [file] [log] [blame]
Ed Warnickecb9cada2015-12-08 15:45:58 -07001/*
2 * Copyright (c) 2015 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 * ip/ip4_input.c: IP v4 input node
17 *
18 * Copyright (c) 2008 Eliot Dresselhaus
19 *
20 * Permission is hereby granted, free of charge, to any person obtaining
21 * a copy of this software and associated documentation files (the
22 * "Software"), to deal in the Software without restriction, including
23 * without limitation the rights to use, copy, modify, merge, publish,
24 * distribute, sublicense, and/or sell copies of the Software, and to
25 * permit persons to whom the Software is furnished to do so, subject to
26 * the following conditions:
27 *
28 * The above copyright notice and this permission notice shall be
29 * included in all copies or substantial portions of the Software.
30 *
31 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
32 * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
33 * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
34 * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
35 * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
36 * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
37 * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
38 */
39
40#include <vnet/ip/ip.h>
41#include <vnet/ethernet/ethernet.h>
42#include <vnet/ppp/ppp.h>
43#include <vnet/hdlc/hdlc.h>
44
Dave Barachd7cb1b52016-12-09 09:52:16 -050045typedef struct
46{
Ed Warnickecb9cada2015-12-08 15:45:58 -070047 u8 packet_data[64];
48} ip4_input_trace_t;
49
Dave Barachd7cb1b52016-12-09 09:52:16 -050050static u8 *
51format_ip4_input_trace (u8 * s, va_list * va)
Ed Warnickecb9cada2015-12-08 15:45:58 -070052{
53 CLIB_UNUSED (vlib_main_t * vm) = va_arg (*va, vlib_main_t *);
54 CLIB_UNUSED (vlib_node_t * node) = va_arg (*va, vlib_node_t *);
Dave Barachd7cb1b52016-12-09 09:52:16 -050055 ip4_input_trace_t *t = va_arg (*va, ip4_input_trace_t *);
Ed Warnickecb9cada2015-12-08 15:45:58 -070056
57 s = format (s, "%U",
Dave Barachd7cb1b52016-12-09 09:52:16 -050058 format_ip4_header, t->packet_data, sizeof (t->packet_data));
Ed Warnickecb9cada2015-12-08 15:45:58 -070059
60 return s;
61}
62
Dave Barachd7cb1b52016-12-09 09:52:16 -050063typedef enum
64{
Ed Warnickecb9cada2015-12-08 15:45:58 -070065 IP4_INPUT_NEXT_DROP,
66 IP4_INPUT_NEXT_PUNT,
67 IP4_INPUT_NEXT_LOOKUP,
68 IP4_INPUT_NEXT_LOOKUP_MULTICAST,
Ole Troan92eade12016-01-13 20:17:08 +010069 IP4_INPUT_NEXT_ICMP_ERROR,
Ed Warnickecb9cada2015-12-08 15:45:58 -070070 IP4_INPUT_N_NEXT,
71} ip4_input_next_t;
72
73/* Validate IP v4 packets and pass them either to forwarding code
74 or drop/punt exception packets. */
75always_inline uword
76ip4_input_inline (vlib_main_t * vm,
77 vlib_node_runtime_t * node,
Dave Barachd7cb1b52016-12-09 09:52:16 -050078 vlib_frame_t * frame, int verify_checksum)
Ed Warnickecb9cada2015-12-08 15:45:58 -070079{
Dave Barachd7cb1b52016-12-09 09:52:16 -050080 ip4_main_t *im = &ip4_main;
81 vnet_main_t *vnm = vnet_get_main ();
82 ip_lookup_main_t *lm = &im->lookup_main;
83 u32 n_left_from, *from, *to_next;
Ed Warnickecb9cada2015-12-08 15:45:58 -070084 ip4_input_next_t next_index;
Dave Barachd7cb1b52016-12-09 09:52:16 -050085 vlib_node_runtime_t *error_node =
86 vlib_node_get_runtime (vm, ip4_input_node.index);
87 vlib_simple_counter_main_t *cm;
Damjan Marion586afd72017-04-05 19:18:20 +020088 u32 thread_index = vlib_get_thread_index ();
Ed Warnickecb9cada2015-12-08 15:45:58 -070089
90 from = vlib_frame_vector_args (frame);
91 n_left_from = frame->n_vectors;
92 next_index = node->cached_next_index;
93
94 if (node->flags & VLIB_NODE_FLAG_TRACE)
95 vlib_trace_frame_buffers_only (vm, node, from, frame->n_vectors,
96 /* stride */ 1,
97 sizeof (ip4_input_trace_t));
98
99 cm = vec_elt_at_index (vnm->interface_main.sw_if_counters,
Dave Barachd7cb1b52016-12-09 09:52:16 -0500100 VNET_INTERFACE_COUNTER_IP4);
Ed Warnickecb9cada2015-12-08 15:45:58 -0700101
102 while (n_left_from > 0)
103 {
104 u32 n_left_to_next;
105
Dave Barachd7cb1b52016-12-09 09:52:16 -0500106 vlib_get_next_frame (vm, node, next_index, to_next, n_left_to_next);
Ed Warnickecb9cada2015-12-08 15:45:58 -0700107
108 while (n_left_from >= 4 && n_left_to_next >= 2)
109 {
Dave Barachd7cb1b52016-12-09 09:52:16 -0500110 vlib_buffer_t *p0, *p1;
111 ip4_header_t *ip0, *ip1;
Damjan Marion4d489932016-12-09 03:21:27 -0800112 u32 sw_if_index0, pi0, ip_len0, cur_len0, next0;
113 u32 sw_if_index1, pi1, ip_len1, cur_len1, next1;
Ed Warnickecb9cada2015-12-08 15:45:58 -0700114 i32 len_diff0, len_diff1;
Damjan Marion8b3191e2016-11-09 19:54:20 +0100115 u8 error0, error1, arc0, arc1;
Ed Warnickecb9cada2015-12-08 15:45:58 -0700116
117 /* Prefetch next iteration. */
118 {
Dave Barachd7cb1b52016-12-09 09:52:16 -0500119 vlib_buffer_t *p2, *p3;
Ed Warnickecb9cada2015-12-08 15:45:58 -0700120
121 p2 = vlib_get_buffer (vm, from[2]);
122 p3 = vlib_get_buffer (vm, from[3]);
123
124 vlib_prefetch_buffer_header (p2, LOAD);
125 vlib_prefetch_buffer_header (p3, LOAD);
126
127 CLIB_PREFETCH (p2->data, sizeof (ip0[0]), LOAD);
128 CLIB_PREFETCH (p3->data, sizeof (ip1[0]), LOAD);
129 }
130
131 to_next[0] = pi0 = from[0];
132 to_next[1] = pi1 = from[1];
133 from += 2;
134 to_next += 2;
135 n_left_from -= 2;
136 n_left_to_next -= 2;
137
138 p0 = vlib_get_buffer (vm, pi0);
139 p1 = vlib_get_buffer (vm, pi1);
140
141 ip0 = vlib_buffer_get_current (p0);
142 ip1 = vlib_buffer_get_current (p1);
143
144 sw_if_index0 = vnet_buffer (p0)->sw_if_index[VLIB_RX];
145 sw_if_index1 = vnet_buffer (p1)->sw_if_index[VLIB_RX];
146
Damjan Marion4d489932016-12-09 03:21:27 -0800147 error0 = error1 = IP4_ERROR_NONE;
148
149 if (PREDICT_FALSE (ip4_address_is_multicast (&ip0->dst_address)))
150 {
151 arc0 = lm->mcast_feature_arc_index;
152 next0 = IP4_INPUT_NEXT_LOOKUP_MULTICAST;
153 }
154 else
155 {
156 arc0 = lm->ucast_feature_arc_index;
157 next0 = IP4_INPUT_NEXT_LOOKUP;
158 if (PREDICT_FALSE (ip0->ttl < 1))
159 error0 = IP4_ERROR_TIME_EXPIRED;
160 }
161
162 if (PREDICT_FALSE (ip4_address_is_multicast (&ip1->dst_address)))
163 {
164 arc1 = lm->mcast_feature_arc_index;
165 next1 = IP4_INPUT_NEXT_LOOKUP_MULTICAST;
166 }
167 else
168 {
169 arc1 = lm->ucast_feature_arc_index;
170 next1 = IP4_INPUT_NEXT_LOOKUP;
171 if (PREDICT_FALSE (ip1->ttl < 1))
172 error1 = IP4_ERROR_TIME_EXPIRED;
173 }
Ed Warnickecb9cada2015-12-08 15:45:58 -0700174
175 vnet_buffer (p0)->ip.adj_index[VLIB_RX] = ~0;
176 vnet_buffer (p1)->ip.adj_index[VLIB_RX] = ~0;
177
Damjan Marion8b3191e2016-11-09 19:54:20 +0100178 vnet_feature_arc_start (arc0, sw_if_index0, &next0, p0);
179 vnet_feature_arc_start (arc1, sw_if_index1, &next1, p1);
Ed Warnickecb9cada2015-12-08 15:45:58 -0700180
Damjan Marion586afd72017-04-05 19:18:20 +0200181 vlib_increment_simple_counter (cm, thread_index, sw_if_index0, 1);
182 vlib_increment_simple_counter (cm, thread_index, sw_if_index1, 1);
Ed Warnickecb9cada2015-12-08 15:45:58 -0700183
Damjan Marion4d489932016-12-09 03:21:27 -0800184 /* Punt packets with options or wrong version. */
185 if (PREDICT_FALSE (ip0->ip_version_and_header_length != 0x45))
186 error0 = (ip0->ip_version_and_header_length & 0xf) != 5 ?
187 IP4_ERROR_OPTIONS : IP4_ERROR_VERSION;
Ed Warnickecb9cada2015-12-08 15:45:58 -0700188
Damjan Marion4d489932016-12-09 03:21:27 -0800189 if (PREDICT_FALSE (ip1->ip_version_and_header_length != 0x45))
190 error1 = (ip1->ip_version_and_header_length & 0xf) != 5 ?
191 IP4_ERROR_OPTIONS : IP4_ERROR_VERSION;
Ed Warnickecb9cada2015-12-08 15:45:58 -0700192
193 /* Verify header checksum. */
194 if (verify_checksum)
195 {
196 ip_csum_t sum0, sum1;
197
198 ip4_partial_header_checksum_x1 (ip0, sum0);
199 ip4_partial_header_checksum_x1 (ip1, sum1);
200
Damjan Marion4d489932016-12-09 03:21:27 -0800201 error0 = 0xffff != ip_csum_fold (sum0) ?
202 IP4_ERROR_BAD_CHECKSUM : error0;
203 error1 = 0xffff != ip_csum_fold (sum1) ?
204 IP4_ERROR_BAD_CHECKSUM : error1;
Ed Warnickecb9cada2015-12-08 15:45:58 -0700205 }
206
207 /* Drop fragmentation offset 1 packets. */
Damjan Marion4d489932016-12-09 03:21:27 -0800208 error0 = ip4_get_fragment_offset (ip0) == 1 ?
209 IP4_ERROR_FRAGMENT_OFFSET_ONE : error0;
210 error1 = ip4_get_fragment_offset (ip1) == 1 ?
211 IP4_ERROR_FRAGMENT_OFFSET_ONE : error1;
Ed Warnickecb9cada2015-12-08 15:45:58 -0700212
213 /* Verify lengths. */
214 ip_len0 = clib_net_to_host_u16 (ip0->length);
215 ip_len1 = clib_net_to_host_u16 (ip1->length);
216
217 /* IP length must be at least minimal IP header. */
218 error0 = ip_len0 < sizeof (ip0[0]) ? IP4_ERROR_TOO_SHORT : error0;
219 error1 = ip_len1 < sizeof (ip1[0]) ? IP4_ERROR_TOO_SHORT : error1;
220
221 cur_len0 = vlib_buffer_length_in_chain (vm, p0);
222 cur_len1 = vlib_buffer_length_in_chain (vm, p1);
223
224 len_diff0 = cur_len0 - ip_len0;
225 len_diff1 = cur_len1 - ip_len1;
226
227 error0 = len_diff0 < 0 ? IP4_ERROR_BAD_LENGTH : error0;
228 error1 = len_diff1 < 0 ? IP4_ERROR_BAD_LENGTH : error1;
229
230 p0->error = error_node->errors[error0];
231 p1->error = error_node->errors[error1];
232
Dave Barachd7cb1b52016-12-09 09:52:16 -0500233 if (PREDICT_FALSE (error0 != IP4_ERROR_NONE))
234 {
235 if (error0 == IP4_ERROR_TIME_EXPIRED)
236 {
237 icmp4_error_set_vnet_buffer (p0, ICMP4_time_exceeded,
238 ICMP4_time_exceeded_ttl_exceeded_in_transit,
239 0);
240 next0 = IP4_INPUT_NEXT_ICMP_ERROR;
241 }
242 else
Damjan Marion4d489932016-12-09 03:21:27 -0800243 next0 = error0 != IP4_ERROR_OPTIONS ?
244 IP4_INPUT_NEXT_DROP : IP4_INPUT_NEXT_PUNT;
Dave Barachd7cb1b52016-12-09 09:52:16 -0500245 }
246 if (PREDICT_FALSE (error1 != IP4_ERROR_NONE))
247 {
248 if (error1 == IP4_ERROR_TIME_EXPIRED)
249 {
250 icmp4_error_set_vnet_buffer (p1, ICMP4_time_exceeded,
251 ICMP4_time_exceeded_ttl_exceeded_in_transit,
252 0);
253 next1 = IP4_INPUT_NEXT_ICMP_ERROR;
254 }
255 else
Damjan Marion4d489932016-12-09 03:21:27 -0800256 next1 = error1 != IP4_ERROR_OPTIONS ?
257 IP4_INPUT_NEXT_DROP : IP4_INPUT_NEXT_PUNT;
Dave Barachd7cb1b52016-12-09 09:52:16 -0500258 }
Ed Warnickecb9cada2015-12-08 15:45:58 -0700259
260 vlib_validate_buffer_enqueue_x2 (vm, node, next_index,
261 to_next, n_left_to_next,
262 pi0, pi1, next0, next1);
Dave Barachd7cb1b52016-12-09 09:52:16 -0500263 }
Ed Warnickecb9cada2015-12-08 15:45:58 -0700264 while (n_left_from > 0 && n_left_to_next > 0)
265 {
Dave Barachd7cb1b52016-12-09 09:52:16 -0500266 vlib_buffer_t *p0;
267 ip4_header_t *ip0;
Damjan Marion4d489932016-12-09 03:21:27 -0800268 u32 sw_if_index0, pi0, ip_len0, cur_len0, next0;
Ed Warnickecb9cada2015-12-08 15:45:58 -0700269 i32 len_diff0;
Damjan Marion8b3191e2016-11-09 19:54:20 +0100270 u8 error0, arc0;
Ed Warnickecb9cada2015-12-08 15:45:58 -0700271
272 pi0 = from[0];
273 to_next[0] = pi0;
274 from += 1;
275 to_next += 1;
276 n_left_from -= 1;
277 n_left_to_next -= 1;
278
279 p0 = vlib_get_buffer (vm, pi0);
280 ip0 = vlib_buffer_get_current (p0);
281
282 sw_if_index0 = vnet_buffer (p0)->sw_if_index[VLIB_RX];
283
Damjan Marion4d489932016-12-09 03:21:27 -0800284 error0 = IP4_ERROR_NONE;
285
286 if (PREDICT_FALSE (ip4_address_is_multicast (&ip0->dst_address)))
287 {
288 arc0 = lm->mcast_feature_arc_index;
289 next0 = IP4_INPUT_NEXT_LOOKUP_MULTICAST;
290 }
291 else
292 {
293 arc0 = lm->ucast_feature_arc_index;
294 next0 = IP4_INPUT_NEXT_LOOKUP;
295 if (PREDICT_FALSE (ip0->ttl < 1))
296 error0 = IP4_ERROR_TIME_EXPIRED;
297 }
298
Ed Warnickecb9cada2015-12-08 15:45:58 -0700299 vnet_buffer (p0)->ip.adj_index[VLIB_RX] = ~0;
Damjan Marion8b3191e2016-11-09 19:54:20 +0100300 vnet_feature_arc_start (arc0, sw_if_index0, &next0, p0);
Ed Warnickecb9cada2015-12-08 15:45:58 -0700301
Damjan Marion586afd72017-04-05 19:18:20 +0200302 vlib_increment_simple_counter (cm, thread_index, sw_if_index0, 1);
Ed Warnickecb9cada2015-12-08 15:45:58 -0700303
Damjan Marion4d489932016-12-09 03:21:27 -0800304 /* Punt packets with options or wrong version. */
305 if (PREDICT_FALSE (ip0->ip_version_and_header_length != 0x45))
306 error0 = (ip0->ip_version_and_header_length & 0xf) != 5 ?
307 IP4_ERROR_OPTIONS : IP4_ERROR_VERSION;
Ed Warnickecb9cada2015-12-08 15:45:58 -0700308
309 /* Verify header checksum. */
310 if (verify_checksum)
311 {
312 ip_csum_t sum0;
313
314 ip4_partial_header_checksum_x1 (ip0, sum0);
Dave Barachd7cb1b52016-12-09 09:52:16 -0500315 error0 =
316 0xffff !=
317 ip_csum_fold (sum0) ? IP4_ERROR_BAD_CHECKSUM : error0;
Ed Warnickecb9cada2015-12-08 15:45:58 -0700318 }
319
320 /* Drop fragmentation offset 1 packets. */
Dave Barachd7cb1b52016-12-09 09:52:16 -0500321 error0 =
322 ip4_get_fragment_offset (ip0) ==
323 1 ? IP4_ERROR_FRAGMENT_OFFSET_ONE : error0;
Ed Warnickecb9cada2015-12-08 15:45:58 -0700324
Ed Warnickecb9cada2015-12-08 15:45:58 -0700325 /* Verify lengths. */
326 ip_len0 = clib_net_to_host_u16 (ip0->length);
327
328 /* IP length must be at least minimal IP header. */
329 error0 = ip_len0 < sizeof (ip0[0]) ? IP4_ERROR_TOO_SHORT : error0;
330
331 cur_len0 = vlib_buffer_length_in_chain (vm, p0);
332 len_diff0 = cur_len0 - ip_len0;
333 error0 = len_diff0 < 0 ? IP4_ERROR_BAD_LENGTH : error0;
334
335 p0->error = error_node->errors[error0];
Dave Barachd7cb1b52016-12-09 09:52:16 -0500336 if (PREDICT_FALSE (error0 != IP4_ERROR_NONE))
337 {
338 if (error0 == IP4_ERROR_TIME_EXPIRED)
339 {
340 icmp4_error_set_vnet_buffer (p0, ICMP4_time_exceeded,
341 ICMP4_time_exceeded_ttl_exceeded_in_transit,
342 0);
343 next0 = IP4_INPUT_NEXT_ICMP_ERROR;
344 }
345 else
Damjan Marion4d489932016-12-09 03:21:27 -0800346 next0 = error0 != IP4_ERROR_OPTIONS ?
347 IP4_INPUT_NEXT_DROP : IP4_INPUT_NEXT_PUNT;
Dave Barachd7cb1b52016-12-09 09:52:16 -0500348 }
Ed Warnickecb9cada2015-12-08 15:45:58 -0700349
350 vlib_validate_buffer_enqueue_x1 (vm, node, next_index,
351 to_next, n_left_to_next,
352 pi0, next0);
353 }
354
355 vlib_put_next_frame (vm, node, next_index, n_left_to_next);
356 }
357
358 return frame->n_vectors;
359}
360
Dave Barach132d51d2016-07-07 10:10:17 -0400361/** \brief IPv4 input node.
362 @node ip4-input
363
364 This is the IPv4 input node: validates ip4 header checksums,
365 verifies ip header lengths, discards pkts with expired TTLs,
366 and sends pkts to the set of ip feature nodes configured on
367 the rx interface.
368
369 @param vm vlib_main_t corresponding to the current thread
370 @param node vlib_node_runtime_t
371 @param frame vlib_frame_t whose contents should be dispatched
372
373 @par Graph mechanics: buffer metadata, next index usage
374
375 @em Uses:
Dave Barachd7cb1b52016-12-09 09:52:16 -0500376 - vnet_feature_config_main_t cm corresponding to each pkt's dst address unicast /
Dave Barach132d51d2016-07-07 10:10:17 -0400377 multicast status.
378 - <code>b->current_config_index</code> corresponding to each pkt's
Dave Barachd7cb1b52016-12-09 09:52:16 -0500379 rx sw_if_index.
Dave Barach132d51d2016-07-07 10:10:17 -0400380 - This sets the per-packet graph trajectory, ensuring that
381 each packet visits the per-interface features in order.
382
383 - <code>vnet_buffer(b)->sw_if_index[VLIB_RX]</code>
384 - Indicates the @c sw_if_index value of the interface that the
385 packet was received on.
386
387 @em Sets:
388 - <code>vnet_buffer(b)->ip.adj_index[VLIB_TX]</code>
389 - The lookup result adjacency index.
390
391 <em>Next Indices:</em>
392 - Dispatches pkts to the (first) feature node:
393 <code> vnet_get_config_data (... &next0 ...); </code>
Dave Barachd7cb1b52016-12-09 09:52:16 -0500394 or @c error-drop
Dave Barach132d51d2016-07-07 10:10:17 -0400395*/
Ed Warnickecb9cada2015-12-08 15:45:58 -0700396static uword
Dave Barachd7cb1b52016-12-09 09:52:16 -0500397ip4_input (vlib_main_t * vm, vlib_node_runtime_t * node, vlib_frame_t * frame)
Ed Warnickecb9cada2015-12-08 15:45:58 -0700398{
399 return ip4_input_inline (vm, node, frame, /* verify_checksum */ 1);
400}
401
402static uword
403ip4_input_no_checksum (vlib_main_t * vm,
Dave Barachd7cb1b52016-12-09 09:52:16 -0500404 vlib_node_runtime_t * node, vlib_frame_t * frame)
Ed Warnickecb9cada2015-12-08 15:45:58 -0700405{
406 return ip4_input_inline (vm, node, frame, /* verify_checksum */ 0);
407}
408
Dave Barachd7cb1b52016-12-09 09:52:16 -0500409static char *ip4_error_strings[] = {
Ed Warnickecb9cada2015-12-08 15:45:58 -0700410#define _(sym,string) string,
411 foreach_ip4_error
412#undef _
413};
414
Dave Barachd7cb1b52016-12-09 09:52:16 -0500415/* *INDENT-OFF* */
Ed Warnickecb9cada2015-12-08 15:45:58 -0700416VLIB_REGISTER_NODE (ip4_input_node) = {
417 .function = ip4_input,
418 .name = "ip4-input",
419 .vector_size = sizeof (u32),
420
421 .n_errors = IP4_N_ERROR,
422 .error_strings = ip4_error_strings,
423
424 .n_next_nodes = IP4_INPUT_N_NEXT,
425 .next_nodes = {
426 [IP4_INPUT_NEXT_DROP] = "error-drop",
427 [IP4_INPUT_NEXT_PUNT] = "error-punt",
428 [IP4_INPUT_NEXT_LOOKUP] = "ip4-lookup",
Neale Ranns32e1c012016-11-22 17:07:28 +0000429 [IP4_INPUT_NEXT_LOOKUP_MULTICAST] = "ip4-mfib-forward-lookup",
Ole Troan92eade12016-01-13 20:17:08 +0100430 [IP4_INPUT_NEXT_ICMP_ERROR] = "ip4-icmp-error",
Ed Warnickecb9cada2015-12-08 15:45:58 -0700431 },
432
433 .format_buffer = format_ip4_header,
434 .format_trace = format_ip4_input_trace,
435};
Dave Barachd7cb1b52016-12-09 09:52:16 -0500436/* *INDENT-ON* */
Ed Warnickecb9cada2015-12-08 15:45:58 -0700437
Dave Barachd7cb1b52016-12-09 09:52:16 -0500438VLIB_NODE_FUNCTION_MULTIARCH (ip4_input_node, ip4_input);
Damjan Marion1c80e832016-05-11 23:07:18 +0200439
Dave Barachd7cb1b52016-12-09 09:52:16 -0500440/* *INDENT-OFF* */
Ed Warnickecb9cada2015-12-08 15:45:58 -0700441VLIB_REGISTER_NODE (ip4_input_no_checksum_node,static) = {
442 .function = ip4_input_no_checksum,
443 .name = "ip4-input-no-checksum",
444 .vector_size = sizeof (u32),
445
446 .n_next_nodes = IP4_INPUT_N_NEXT,
447 .next_nodes = {
448 [IP4_INPUT_NEXT_DROP] = "error-drop",
449 [IP4_INPUT_NEXT_PUNT] = "error-punt",
450 [IP4_INPUT_NEXT_LOOKUP] = "ip4-lookup",
Neale Ranns32e1c012016-11-22 17:07:28 +0000451 [IP4_INPUT_NEXT_LOOKUP_MULTICAST] = "ip4-mfib-forward-lookup",
Ole Troan92eade12016-01-13 20:17:08 +0100452 [IP4_INPUT_NEXT_ICMP_ERROR] = "ip4-icmp-error",
Ed Warnickecb9cada2015-12-08 15:45:58 -0700453 },
454
455 .format_buffer = format_ip4_header,
456 .format_trace = format_ip4_input_trace,
457};
Dave Barachd7cb1b52016-12-09 09:52:16 -0500458/* *INDENT-ON* */
Ed Warnickecb9cada2015-12-08 15:45:58 -0700459
Dave Barachd7cb1b52016-12-09 09:52:16 -0500460VLIB_NODE_FUNCTION_MULTIARCH (ip4_input_no_checksum_node,
461 ip4_input_no_checksum);
Damjan Marion1c80e832016-05-11 23:07:18 +0200462
Dave Barachd7cb1b52016-12-09 09:52:16 -0500463static clib_error_t *
464ip4_init (vlib_main_t * vm)
Ed Warnickecb9cada2015-12-08 15:45:58 -0700465{
Dave Barachd7cb1b52016-12-09 09:52:16 -0500466 clib_error_t *error;
Ed Warnickecb9cada2015-12-08 15:45:58 -0700467
Dave Barachd7cb1b52016-12-09 09:52:16 -0500468 ethernet_register_input_type (vm, ETHERNET_TYPE_IP4, ip4_input_node.index);
469 ppp_register_input_protocol (vm, PPP_PROTOCOL_ip4, ip4_input_node.index);
470 hdlc_register_input_protocol (vm, HDLC_PROTOCOL_ip4, ip4_input_node.index);
Ed Warnickecb9cada2015-12-08 15:45:58 -0700471
472 {
Dave Barachd7cb1b52016-12-09 09:52:16 -0500473 pg_node_t *pn;
Ed Warnickecb9cada2015-12-08 15:45:58 -0700474 pn = pg_get_node (ip4_input_node.index);
475 pn->unformat_edit = unformat_pg_ip4_header;
476 pn = pg_get_node (ip4_input_no_checksum_node.index);
477 pn->unformat_edit = unformat_pg_ip4_header;
478 }
479
480 if ((error = vlib_call_init_function (vm, ip4_cli_init)))
481 return error;
482
483 if ((error = vlib_call_init_function (vm, ip4_source_check_init)))
484 return error;
485
Dave Barachd7cb1b52016-12-09 09:52:16 -0500486 if ((error = vlib_call_init_function
Dave Barach6f9bca22016-04-30 10:25:32 -0400487 (vm, ip4_source_and_port_range_check_init)))
488 return error;
489
Ed Warnickecb9cada2015-12-08 15:45:58 -0700490 /* Set flow hash to something non-zero. */
491 ip4_main.flow_hash_seed = 0xdeadbeef;
492
493 /* Default TTL for packets we generate. */
494 ip4_main.host_config.ttl = 64;
495
496 return error;
497}
498
499VLIB_INIT_FUNCTION (ip4_init);
Dave Barachd7cb1b52016-12-09 09:52:16 -0500500
501/*
502 * fd.io coding-style-patch-verification: ON
503 *
504 * Local Variables:
505 * eval: (c-set-style "gnu")
506 * End:
507 */