FD.io VPP  v20.01-48-g3e0dafb74
Vector Packet Processing
nat_ipfix_logging.c
Go to the documentation of this file.
1 /*
2  * nat_ipfix_logging.c - NAT Events IPFIX logging
3  *
4  * Copyright (c) 2016 Cisco and/or its affiliates.
5  * Licensed under the Apache License, Version 2.0 (the "License");
6  * you may not use this file except in compliance with the License.
7  * You may obtain a copy of the License at:
8  *
9  * http://www.apache.org/licenses/LICENSE-2.0
10  *
11  * Unless required by applicable law or agreed to in writing, software
12  * distributed under the License is distributed on an "AS IS" BASIS,
13  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14  * See the License for the specific language governing permissions and
15  * limitations under the License.
16  */
17 
19 #include <vlibmemory/api.h>
20 #include <nat/nat_inlines.h>
21 #include <nat/nat_ipfix_logging.h>
22 #include <vppinfra/atomics.h>
23 
26 
27 #define NAT44_SESSION_CREATE_LEN 26
28 #define NAT_ADDRESSES_EXHAUTED_LEN 13
29 #define MAX_ENTRIES_PER_USER_LEN 21
30 #define MAX_SESSIONS_LEN 17
31 #define MAX_BIBS_LEN 17
32 #define MAX_FRAGMENTS_IP4_LEN 21
33 #define MAX_FRAGMENTS_IP6_LEN 33
34 #define NAT64_BIB_LEN 38
35 #define NAT64_SES_LEN 62
36 
37 #define NAT44_SESSION_CREATE_FIELD_COUNT 8
38 #define NAT_ADDRESSES_EXHAUTED_FIELD_COUNT 3
39 #define MAX_ENTRIES_PER_USER_FIELD_COUNT 5
40 #define MAX_SESSIONS_FIELD_COUNT 4
41 #define MAX_BIBS_FIELD_COUNT 4
42 #define MAX_FRAGMENTS_FIELD_COUNT 5
43 #define NAT64_BIB_FIELD_COUNT 8
44 #define NAT64_SES_FIELD_COUNT 12
45 
46 typedef struct
47 {
56 
57 typedef struct
58 {
61 
62 typedef struct
63 {
67 
68 typedef struct
69 {
72 
73 typedef struct
74 {
77 
78 typedef struct
79 {
83 
84 typedef struct
85 {
87  u64 src[2];
89 
90 typedef struct
91 {
93  u64 src_ip[2];
98  u64 dst_ip[2];
104 
105 typedef struct
106 {
115 
116 #define skip_if_disabled() \
117 do { \
118  snat_ipfix_logging_main_t *silm = &snat_ipfix_logging_main; \
119  if (PREDICT_TRUE (!clib_atomic_fetch_or(&silm->enabled, 0))) \
120  return; \
121 } while (0)
122 
123 #define update_template_id(old_id, new_id) \
124 do { \
125  u16 template_id = clib_atomic_fetch_or(old_id, 0); \
126  clib_atomic_cmp_and_swap(old_id, template_id, new_id); \
127 } while (0)
128 
129 /**
130  * @brief Create an IPFIX template packet rewrite string
131  *
132  * @param frm flow report main
133  * @param fr flow report
134  * @param collector_address collector address
135  * @param src_address source address
136  * @param collector_port collector
137  * @param event NAT event ID
138  * @param quota_event NAT quota exceeded event ID
139  *
140  * @returns template packet
141  */
142 static inline u8 *
144  flow_report_t * fr,
145  ip4_address_t * collector_address,
147  u16 collector_port,
148  nat_event_t event, quota_exceed_event_t quota_event)
149 {
151  ip4_header_t *ip;
152  udp_header_t *udp;
157  ipfix_field_specifier_t *first_field;
158  u8 *rewrite = 0;
160  u32 field_count = 0;
161  flow_report_stream_t *stream;
162  u32 stream_index;
163 
164  stream = &frm->streams[fr->stream_index];
165 
166  stream_index = clib_atomic_fetch_or(&silm->stream_index, 0);
168  stream_index, fr->stream_index);
169 
170  if (event == NAT_ADDRESSES_EXHAUTED)
171  {
173 
175  fr->template_id);
176  }
177  else if (event == NAT44_SESSION_CREATE)
178  {
179  field_count = NAT44_SESSION_CREATE_FIELD_COUNT;
180 
182  fr->template_id);
183  }
184  else if (event == NAT64_BIB_CREATE)
185  {
186  field_count = NAT64_BIB_FIELD_COUNT;
187 
189  fr->template_id);
190  }
191  else if (event == NAT64_SESSION_CREATE)
192  {
193  field_count = NAT64_SES_FIELD_COUNT;
194 
196  fr->template_id);
197  }
198  else if (event == QUOTA_EXCEEDED)
199  {
200  if (quota_event == MAX_ENTRIES_PER_USER)
201  {
202  field_count = MAX_ENTRIES_PER_USER_FIELD_COUNT;
203 
205  fr->template_id);
206 
207  }
208  else if (quota_event == MAX_SESSION_ENTRIES)
209  {
210  field_count = MAX_SESSIONS_FIELD_COUNT;
211 
213  fr->template_id);
214  }
215  else if (quota_event == MAX_BIB_ENTRIES)
216  {
217  field_count = MAX_BIBS_FIELD_COUNT;
218 
220  fr->template_id);
221  }
222  else if (quota_event == MAX_FRAGMENTS_PENDING_REASSEMBLY)
223  {
224  field_count = MAX_FRAGMENTS_FIELD_COUNT;
225 
227  fr->template_id);
228  }
229  else if (quota_event == MAX_FRAGMENTS_PENDING_REASSEMBLY_IP6)
230  {
231  field_count = MAX_FRAGMENTS_FIELD_COUNT;
232 
234  fr->template_id);
235  }
236  }
237 
238  /* allocate rewrite space */
239  vec_validate_aligned (rewrite,
241  + field_count * sizeof (ipfix_field_specifier_t) - 1,
243 
244  tp = (ip4_ipfix_template_packet_t *) rewrite;
245  ip = (ip4_header_t *) & tp->ip4;
246  udp = (udp_header_t *) (ip + 1);
247  h = (ipfix_message_header_t *) (udp + 1);
248  s = (ipfix_set_header_t *) (h + 1);
249  t = (ipfix_template_header_t *) (s + 1);
250  first_field = f = (ipfix_field_specifier_t *) (t + 1);
251 
252  ip->ip_version_and_header_length = 0x45;
253  ip->ttl = 254;
254  ip->protocol = IP_PROTOCOL_UDP;
255  ip->src_address.as_u32 = src_address->as_u32;
256  ip->dst_address.as_u32 = collector_address->as_u32;
257  udp->src_port = clib_host_to_net_u16 (stream->src_port);
258  udp->dst_port = clib_host_to_net_u16 (collector_port);
259  udp->length = clib_host_to_net_u16 (vec_len (rewrite) - sizeof (*ip));
260 
261  /* FIXUP: message header export_time */
262  h->domain_id = clib_host_to_net_u32 (stream->domain_id);
263 
264  /* Add TLVs to the template */
265  if (event == NAT_ADDRESSES_EXHAUTED)
266  {
267  f->e_id_length = ipfix_e_id_length (0, observationTimeMilliseconds, 8);
268  f++;
269  f->e_id_length = ipfix_e_id_length (0, natEvent, 1);
270  f++;
271  f->e_id_length = ipfix_e_id_length (0, natPoolId, 4);
272  f++;
273  }
274  else if (event == NAT44_SESSION_CREATE)
275  {
276  f->e_id_length = ipfix_e_id_length (0, observationTimeMilliseconds, 8);
277  f++;
278  f->e_id_length = ipfix_e_id_length (0, natEvent, 1);
279  f++;
280  f->e_id_length = ipfix_e_id_length (0, sourceIPv4Address, 4);
281  f++;
282  f->e_id_length = ipfix_e_id_length (0, postNATSourceIPv4Address, 4);
283  f++;
284  f->e_id_length = ipfix_e_id_length (0, protocolIdentifier, 1);
285  f++;
286  f->e_id_length = ipfix_e_id_length (0, sourceTransportPort, 2);
287  f++;
288  f->e_id_length = ipfix_e_id_length (0, postNAPTSourceTransportPort, 2);
289  f++;
290  f->e_id_length = ipfix_e_id_length (0, ingressVRFID, 4);
291  f++;
292  }
293  else if (event == NAT64_BIB_CREATE)
294  {
295  f->e_id_length = ipfix_e_id_length (0, observationTimeMilliseconds, 8);
296  f++;
297  f->e_id_length = ipfix_e_id_length (0, natEvent, 1);
298  f++;
299  f->e_id_length = ipfix_e_id_length (0, sourceIPv6Address, 16);
300  f++;
301  f->e_id_length = ipfix_e_id_length (0, postNATSourceIPv4Address, 4);
302  f++;
303  f->e_id_length = ipfix_e_id_length (0, protocolIdentifier, 1);
304  f++;
305  f->e_id_length = ipfix_e_id_length (0, sourceTransportPort, 2);
306  f++;
307  f->e_id_length = ipfix_e_id_length (0, postNAPTSourceTransportPort, 2);
308  f++;
309  f->e_id_length = ipfix_e_id_length (0, ingressVRFID, 4);
310  f++;
311  }
312  else if (event == NAT64_SESSION_CREATE)
313  {
314  f->e_id_length = ipfix_e_id_length (0, observationTimeMilliseconds, 8);
315  f++;
316  f->e_id_length = ipfix_e_id_length (0, natEvent, 1);
317  f++;
318  f->e_id_length = ipfix_e_id_length (0, sourceIPv6Address, 16);
319  f++;
320  f->e_id_length = ipfix_e_id_length (0, postNATSourceIPv4Address, 4);
321  f++;
322  f->e_id_length = ipfix_e_id_length (0, protocolIdentifier, 1);
323  f++;
324  f->e_id_length = ipfix_e_id_length (0, sourceTransportPort, 2);
325  f++;
326  f->e_id_length = ipfix_e_id_length (0, postNAPTSourceTransportPort, 2);
327  f++;
328  f->e_id_length = ipfix_e_id_length (0, destinationIPv6Address, 16);
329  f++;
330  f->e_id_length = ipfix_e_id_length (0, postNATDestinationIPv4Address, 4);
331  f++;
332  f->e_id_length = ipfix_e_id_length (0, destinationTransportPort, 2);
333  f++;
334  f->e_id_length = ipfix_e_id_length (0, postNAPTDestinationTransportPort,
335  2);
336  f++;
337  f->e_id_length = ipfix_e_id_length (0, ingressVRFID, 4);
338  f++;
339  }
340  else if (event == QUOTA_EXCEEDED)
341  {
342  if (quota_event == MAX_ENTRIES_PER_USER)
343  {
344  f->e_id_length = ipfix_e_id_length (0, observationTimeMilliseconds,
345  8);
346  f++;
347  f->e_id_length = ipfix_e_id_length (0, natEvent, 1);
348  f++;
349  f->e_id_length = ipfix_e_id_length (0, natQuotaExceededEvent, 4);
350  f++;
351  f->e_id_length = ipfix_e_id_length (0, maxEntriesPerUser, 4);
352  f++;
353  f->e_id_length = ipfix_e_id_length (0, sourceIPv4Address, 4);
354  f++;
355  }
356  else if (quota_event == MAX_SESSION_ENTRIES)
357  {
358  f->e_id_length = ipfix_e_id_length (0, observationTimeMilliseconds,
359  8);
360  f++;
361  f->e_id_length = ipfix_e_id_length (0, natEvent, 1);
362  f++;
363  f->e_id_length = ipfix_e_id_length (0, natQuotaExceededEvent, 4);
364  f++;
365  f->e_id_length = ipfix_e_id_length (0, maxSessionEntries, 4);
366  f++;
367  }
368  else if (quota_event == MAX_BIB_ENTRIES)
369  {
370  f->e_id_length = ipfix_e_id_length (0, observationTimeMilliseconds,
371  8);
372  f++;
373  f->e_id_length = ipfix_e_id_length (0, natEvent, 1);
374  f++;
375  f->e_id_length = ipfix_e_id_length (0, natQuotaExceededEvent, 4);
376  f++;
377  f->e_id_length = ipfix_e_id_length (0, maxBIBEntries, 4);
378  f++;
379  }
380  else if (quota_event == MAX_FRAGMENTS_PENDING_REASSEMBLY)
381  {
382  f->e_id_length = ipfix_e_id_length (0, observationTimeMilliseconds,
383  8);
384  f++;
385  f->e_id_length = ipfix_e_id_length (0, natEvent, 1);
386  f++;
387  f->e_id_length = ipfix_e_id_length (0, natQuotaExceededEvent, 4);
388  f++;
389  f->e_id_length = ipfix_e_id_length (0, maxFragmentsPendingReassembly,
390  4);
391  f++;
392  f->e_id_length = ipfix_e_id_length (0, sourceIPv4Address, 4);
393  f++;
394  }
395  else if (quota_event == MAX_FRAGMENTS_PENDING_REASSEMBLY_IP6)
396  {
397  f->e_id_length = ipfix_e_id_length (0, observationTimeMilliseconds,
398  8);
399  f++;
400  f->e_id_length = ipfix_e_id_length (0, natEvent, 1);
401  f++;
402  f->e_id_length = ipfix_e_id_length (0, natQuotaExceededEvent, 4);
403  f++;
404  f->e_id_length = ipfix_e_id_length (0, maxFragmentsPendingReassembly,
405  4);
406  f++;
407  f->e_id_length = ipfix_e_id_length (0, sourceIPv6Address, 16);
408  f++;
409  }
410  }
411 
412  /* Back to the template packet... */
413  ip = (ip4_header_t *) & tp->ip4;
414  udp = (udp_header_t *) (ip + 1);
415 
416  ASSERT (f - first_field);
417  /* Field count in this template */
418  t->id_count = ipfix_id_count (fr->template_id, f - first_field);
419 
420  /* set length in octets */
421  s->set_id_length =
422  ipfix_set_id_length (2 /* set_id */ , (u8 *) f - (u8 *) s);
423 
424  /* message length in octets */
425  h->version_length = version_length ((u8 *) f - (u8 *) h);
426 
427  ip->length = clib_host_to_net_u16 ((u8 *) f - (u8 *) ip);
428  ip->checksum = ip4_header_checksum (ip);
429 
430  return rewrite;
431 }
432 
433 u8 *
435  flow_report_t * fr,
436  ip4_address_t * collector_address,
438  u16 collector_port,
440  u32 n_elts, u32 *stream_index)
441 {
442  return snat_template_rewrite (frm, fr, collector_address, src_address,
443  collector_port, NAT_ADDRESSES_EXHAUTED, 0);
444 }
445 
446 u8 *
448  flow_report_t * fr,
449  ip4_address_t * collector_address,
451  u16 collector_port,
453  u32 n_elts, u32 *stream_index)
454 {
455  return snat_template_rewrite (frm, fr, collector_address, src_address,
456  collector_port, NAT44_SESSION_CREATE, 0);
457 }
458 
459 u8 *
461  flow_report_t * fr,
462  ip4_address_t * collector_address,
464  u16 collector_port,
466  u32 n_elts, u32 *stream_index)
467 {
468  return snat_template_rewrite (frm, fr, collector_address, src_address,
469  collector_port, QUOTA_EXCEEDED,
471 }
472 
473 u8 *
475  flow_report_t * fr,
476  ip4_address_t * collector_address,
478  u16 collector_port,
480  u32 n_elts, u32 *stream_index)
481 {
482  return snat_template_rewrite (frm, fr, collector_address, src_address,
483  collector_port, QUOTA_EXCEEDED,
485 }
486 
487 u8 *
489  flow_report_t * fr,
490  ip4_address_t * collector_address,
492  u16 collector_port,
494  u32 n_elts, u32 *stream_index)
495 {
496  return snat_template_rewrite (frm, fr, collector_address, src_address,
497  collector_port, QUOTA_EXCEEDED,
499 }
500 
501 u8 *
503  flow_report_t * fr,
504  ip4_address_t * collector_address,
506  u16 collector_port,
508  u32 n_elts, u32 *stream_index)
509 {
510  return snat_template_rewrite (frm, fr, collector_address, src_address,
511  collector_port, QUOTA_EXCEEDED,
513 }
514 
515 u8 *
517  flow_report_t * fr,
518  ip4_address_t * collector_address,
520  u16 collector_port,
522  u32 n_elts, u32 *stream_index)
523 {
524  return snat_template_rewrite (frm, fr, collector_address, src_address,
525  collector_port, QUOTA_EXCEEDED,
527 }
528 
529 u8 *
531  flow_report_t * fr,
532  ip4_address_t * collector_address,
534  u16 collector_port,
536  u32 n_elts, u32 *stream_index)
537 {
538  return snat_template_rewrite (frm, fr, collector_address, src_address,
539  collector_port, NAT64_BIB_CREATE, 0);
540 }
541 
542 u8 *
544  flow_report_t * fr,
545  ip4_address_t * collector_address,
547  u16 collector_port,
549  u32 n_elts, u32 *stream_index)
550 {
551  return snat_template_rewrite (frm, fr, collector_address, src_address,
552  collector_port, NAT64_SESSION_CREATE, 0);
553 }
554 
555 static inline void
557  vlib_buffer_t * b0, u32 * offset)
558 {
560  flow_report_stream_t *stream;
563  ipfix_set_header_t *s = 0;
564  u32 sequence_number;
565  u32 stream_index;
566  ip4_header_t *ip;
567  udp_header_t *udp;
568 
569  stream_index = clib_atomic_fetch_or(&silm->stream_index, 0);
570  stream = &frm->streams[stream_index];
571 
572  b0->current_data = 0;
573  b0->current_length = sizeof (*ip) + sizeof (*udp) + sizeof (*h) +
574  sizeof (*s);
575  b0->flags |= (VLIB_BUFFER_TOTAL_LENGTH_VALID | VNET_BUFFER_F_FLOW_REPORT);
576  vnet_buffer (b0)->sw_if_index[VLIB_RX] = 0;
577  vnet_buffer (b0)->sw_if_index[VLIB_TX] = frm->fib_index;
578  tp = vlib_buffer_get_current (b0);
579  ip = (ip4_header_t *) & tp->ip4;
580  udp = (udp_header_t *) (ip + 1);
581  h = (ipfix_message_header_t *) (udp + 1);
582  s = (ipfix_set_header_t *) (h + 1);
583 
584  ip->ip_version_and_header_length = 0x45;
585  ip->ttl = 254;
586  ip->protocol = IP_PROTOCOL_UDP;
590  udp->src_port = clib_host_to_net_u16 (stream->src_port);
591  udp->dst_port = clib_host_to_net_u16 (frm->collector_port);
592  udp->checksum = 0;
593 
594  h->export_time = clib_host_to_net_u32 ((u32)
595  (((f64) frm->unix_time_0) +
596  (vlib_time_now (frm->vlib_main) -
597  frm->vlib_time_0)));
598 
599  sequence_number = clib_atomic_fetch_add (&stream->sequence_number, 1);
600  h->sequence_number = clib_host_to_net_u32 (sequence_number);
601  h->domain_id = clib_host_to_net_u32 (stream->domain_id);
602 
603  *offset = (u32) (((u8 *) (s + 1)) - (u8 *) tp);
604 }
605 
606 static inline void
608  vlib_frame_t * f, vlib_buffer_t * b0, u16 template_id)
609 {
612  ipfix_set_header_t *s = 0;
613  ip4_header_t *ip;
614  udp_header_t *udp;
615  vlib_main_t *vm = frm->vlib_main;
616 
617  tp = vlib_buffer_get_current (b0);
618  ip = (ip4_header_t *) & tp->ip4;
619  udp = (udp_header_t *) (ip + 1);
620  h = (ipfix_message_header_t *) (udp + 1);
621  s = (ipfix_set_header_t *) (h + 1);
622 
623  s->set_id_length = ipfix_set_id_length (template_id,
624  b0->current_length -
625  (sizeof (*ip) + sizeof (*udp) +
626  sizeof (*h)));
628  (sizeof (*ip) + sizeof (*udp)));
629 
630  ip->length = clib_host_to_net_u16 (b0->current_length);
631  ip->checksum = ip4_header_checksum (ip);
632  udp->length = clib_host_to_net_u16 (b0->current_length - sizeof (*ip));
633 
634  if (frm->udp_checksum)
635  {
636  udp->checksum = ip4_tcp_udp_compute_checksum (vm, b0, ip);
637  if (udp->checksum == 0)
638  udp->checksum = 0xffff;
639  }
640 
641  ASSERT (ip->checksum == ip4_header_checksum (ip));
642 
644 }
645 
646 static void
647 snat_ipfix_logging_nat44_ses (u32 thread_index, u8 nat_event, u32 src_ip,
648  u32 nat_src_ip, snat_protocol_t snat_proto,
649  u16 src_port, u16 nat_src_port, u32 vrf_id,
650  int do_flush)
651 {
653  snat_ipfix_per_thread_data_t *sitd = &silm->per_thread_data[thread_index];
655  vlib_frame_t *f;
656  vlib_buffer_t *b0 = 0;
657  u32 bi0 = ~0;
658  u32 offset;
659  vlib_main_t *vm = frm->vlib_main;
660  u64 now;
661  u8 proto = ~0;
662  u16 template_id;
663 
664  proto = snat_proto_to_ip_proto (snat_proto);
665 
666  now = (u64) ((vlib_time_now (vm) - silm->vlib_time_0) * 1e3);
667  now += silm->milisecond_time_0;
668 
669  b0 = sitd->nat44_session_buffer;
670 
671  if (PREDICT_FALSE (b0 == 0))
672  {
673  if (do_flush)
674  return;
675 
676  if (vlib_buffer_alloc (vm, &bi0, 1) != 1)
677  {
678  nat_elog_err ("can't allocate buffer for NAT IPFIX event");
679  return;
680  }
681 
682  b0 = sitd->nat44_session_buffer = vlib_get_buffer (vm, bi0);
684  offset = 0;
685  }
686  else
687  {
688  bi0 = vlib_get_buffer_index (vm, b0);
689  offset = sitd->nat44_session_next_record_offset;
690  }
691 
692  f = sitd->nat44_session_frame;
693  if (PREDICT_FALSE (f == 0))
694  {
695  u32 *to_next;
696  f = vlib_get_frame_to_node (vm, ip4_lookup_node.index);
697  sitd->nat44_session_frame = f;
698  to_next = vlib_frame_vector_args (f);
699  to_next[0] = bi0;
700  f->n_vectors = 1;
701  }
702 
703  if (PREDICT_FALSE (offset == 0))
704  snat_ipfix_header_create (frm, b0, &offset);
705 
706  if (PREDICT_TRUE (do_flush == 0))
707  {
708  u64 time_stamp = clib_host_to_net_u64 (now);
709  clib_memcpy_fast (b0->data + offset, &time_stamp, sizeof (time_stamp));
710  offset += sizeof (time_stamp);
711 
712  clib_memcpy_fast (b0->data + offset, &nat_event, sizeof (nat_event));
713  offset += sizeof (nat_event);
714 
715  clib_memcpy_fast (b0->data + offset, &src_ip, sizeof (src_ip));
716  offset += sizeof (src_ip);
717 
718  clib_memcpy_fast (b0->data + offset, &nat_src_ip, sizeof (nat_src_ip));
719  offset += sizeof (nat_src_ip);
720 
721  clib_memcpy_fast (b0->data + offset, &proto, sizeof (proto));
722  offset += sizeof (proto);
723 
724  clib_memcpy_fast (b0->data + offset, &src_port, sizeof (src_port));
725  offset += sizeof (src_port);
726 
727  clib_memcpy_fast (b0->data + offset, &nat_src_port, sizeof (nat_src_port));
728  offset += sizeof (nat_src_port);
729 
730  clib_memcpy_fast (b0->data + offset, &vrf_id, sizeof (vrf_id));
731  offset += sizeof (vrf_id);
732 
734  }
735 
736  if (PREDICT_FALSE
737  (do_flush || (offset + NAT44_SESSION_CREATE_LEN) > frm->path_mtu))
738  {
739  template_id = clib_atomic_fetch_or (
741  0);
742  snat_ipfix_send (frm, f, b0, template_id);
743  sitd->nat44_session_frame = 0;
744  sitd->nat44_session_buffer = 0;
745  offset = 0;
746  }
748 }
749 
750 static void
751 snat_ipfix_logging_addr_exhausted (u32 thread_index, u32 pool_id, int do_flush)
752 {
754  snat_ipfix_per_thread_data_t *sitd = &silm->per_thread_data[thread_index];
756  vlib_frame_t *f;
757  vlib_buffer_t *b0 = 0;
758  u32 bi0 = ~0;
759  u32 offset;
760  vlib_main_t *vm = frm->vlib_main;
761  u64 now;
762  u8 nat_event = NAT_ADDRESSES_EXHAUTED;
763  u16 template_id;
764 
765  now = (u64) ((vlib_time_now (vm) - silm->vlib_time_0) * 1e3);
766  now += silm->milisecond_time_0;
767 
768  b0 = sitd->addr_exhausted_buffer;
769 
770  if (PREDICT_FALSE (b0 == 0))
771  {
772  if (do_flush)
773  return;
774 
775  if (vlib_buffer_alloc (vm, &bi0, 1) != 1)
776  {
777  nat_elog_err ("can't allocate buffer for NAT IPFIX event");
778  return;
779  }
780 
781  b0 = sitd->addr_exhausted_buffer = vlib_get_buffer (vm, bi0);
783  offset = 0;
784  }
785  else
786  {
787  bi0 = vlib_get_buffer_index (vm, b0);
788  offset = sitd->addr_exhausted_next_record_offset;
789  }
790 
791  f = sitd->addr_exhausted_frame;
792  if (PREDICT_FALSE (f == 0))
793  {
794  u32 *to_next;
795  f = vlib_get_frame_to_node (vm, ip4_lookup_node.index);
796  sitd->addr_exhausted_frame = f;
797  to_next = vlib_frame_vector_args (f);
798  to_next[0] = bi0;
799  f->n_vectors = 1;
800  }
801 
802  if (PREDICT_FALSE (offset == 0))
803  snat_ipfix_header_create (frm, b0, &offset);
804 
805  if (PREDICT_TRUE (do_flush == 0))
806  {
807  u64 time_stamp = clib_host_to_net_u64 (now);
808  clib_memcpy_fast (b0->data + offset, &time_stamp, sizeof (time_stamp));
809  offset += sizeof (time_stamp);
810 
811  clib_memcpy_fast (b0->data + offset, &nat_event, sizeof (nat_event));
812  offset += sizeof (nat_event);
813 
814  clib_memcpy_fast (b0->data + offset, &pool_id, sizeof (pool_id));
815  offset += sizeof (pool_id);
816 
818  }
819 
820  if (PREDICT_FALSE
821  (do_flush || (offset + NAT_ADDRESSES_EXHAUTED_LEN) > frm->path_mtu))
822  {
823  template_id = clib_atomic_fetch_or (
825  0);
826  snat_ipfix_send (frm, f, b0, template_id);
827  sitd->addr_exhausted_frame = 0;
828  sitd->addr_exhausted_buffer = 0;
829  offset = 0;
830  }
832 }
833 
834 static void
836  u32 limit, u32 src_ip, int do_flush)
837 {
839  snat_ipfix_per_thread_data_t *sitd = &silm->per_thread_data[thread_index];
841  vlib_frame_t *f;
842  vlib_buffer_t *b0 = 0;
843  u32 bi0 = ~0;
844  u32 offset;
845  vlib_main_t *vm = frm->vlib_main;
846  u64 now;
847  u8 nat_event = QUOTA_EXCEEDED;
848  u32 quota_event = MAX_ENTRIES_PER_USER;
849  u16 template_id;
850 
851  now = (u64) ((vlib_time_now (vm) - silm->vlib_time_0) * 1e3);
852  now += silm->milisecond_time_0;
853 
854  b0 = sitd->max_entries_per_user_buffer;
855 
856  if (PREDICT_FALSE (b0 == 0))
857  {
858  if (do_flush)
859  return;
860 
861  if (vlib_buffer_alloc (vm, &bi0, 1) != 1)
862  {
863  nat_elog_err ("can't allocate buffer for NAT IPFIX event");
864  return;
865  }
866 
867  b0 = sitd->max_entries_per_user_buffer = vlib_get_buffer (vm, bi0);
869  offset = 0;
870  }
871  else
872  {
873  bi0 = vlib_get_buffer_index (vm, b0);
875  }
876 
877  f = sitd->max_entries_per_user_frame;
878  if (PREDICT_FALSE (f == 0))
879  {
880  u32 *to_next;
881  f = vlib_get_frame_to_node (vm, ip4_lookup_node.index);
882  sitd->max_entries_per_user_frame = f;
883  to_next = vlib_frame_vector_args (f);
884  to_next[0] = bi0;
885  f->n_vectors = 1;
886  }
887 
888  if (PREDICT_FALSE (offset == 0))
889  snat_ipfix_header_create (frm, b0, &offset);
890 
891  if (PREDICT_TRUE (do_flush == 0))
892  {
893  u64 time_stamp = clib_host_to_net_u64 (now);
894  clib_memcpy_fast (b0->data + offset, &time_stamp, sizeof (time_stamp));
895  offset += sizeof (time_stamp);
896 
897  clib_memcpy_fast (b0->data + offset, &nat_event, sizeof (nat_event));
898  offset += sizeof (nat_event);
899 
900  clib_memcpy_fast (b0->data + offset, &quota_event, sizeof (quota_event));
901  offset += sizeof (quota_event);
902 
903  clib_memcpy_fast (b0->data + offset, &limit, sizeof (limit));
904  offset += sizeof (limit);
905 
906  clib_memcpy_fast (b0->data + offset, &src_ip, sizeof (src_ip));
907  offset += sizeof (src_ip);
908 
910  }
911 
912  if (PREDICT_FALSE
913  (do_flush || (offset + MAX_ENTRIES_PER_USER_LEN) > frm->path_mtu))
914  {
915  template_id = clib_atomic_fetch_or (
917  0);
918  snat_ipfix_send (frm, f, b0, template_id);
919  sitd->max_entries_per_user_frame = 0;
920  sitd->max_entries_per_user_buffer = 0;
921  offset = 0;
922  }
924 }
925 
926 static void
927 nat_ipfix_logging_max_ses (u32 thread_index, u32 limit, int do_flush)
928 {
930  snat_ipfix_per_thread_data_t *sitd = &silm->per_thread_data[thread_index];
932  vlib_frame_t *f;
933  vlib_buffer_t *b0 = 0;
934  u32 bi0 = ~0;
935  u32 offset;
936  vlib_main_t *vm = frm->vlib_main;
937  u64 now;
938  u8 nat_event = QUOTA_EXCEEDED;
939  u32 quota_event = MAX_SESSION_ENTRIES;
940  u16 template_id;
941 
942  now = (u64) ((vlib_time_now (vm) - silm->vlib_time_0) * 1e3);
943  now += silm->milisecond_time_0;
944 
945  b0 = sitd->max_sessions_buffer;
946 
947  if (PREDICT_FALSE (b0 == 0))
948  {
949  if (do_flush)
950  return;
951 
952  if (vlib_buffer_alloc (vm, &bi0, 1) != 1)
953  {
954  nat_elog_err ("can't allocate buffer for NAT IPFIX event");
955  return;
956  }
957 
958  b0 = sitd->max_sessions_buffer = vlib_get_buffer (vm, bi0);
960  offset = 0;
961  }
962  else
963  {
964  bi0 = vlib_get_buffer_index (vm, b0);
965  offset = sitd->max_sessions_next_record_offset;
966  }
967 
968  f = sitd->max_sessions_frame;
969  if (PREDICT_FALSE (f == 0))
970  {
971  u32 *to_next;
972  f = vlib_get_frame_to_node (vm, ip4_lookup_node.index);
973  sitd->max_sessions_frame = f;
974  to_next = vlib_frame_vector_args (f);
975  to_next[0] = bi0;
976  f->n_vectors = 1;
977  }
978 
979  if (PREDICT_FALSE (offset == 0))
980  snat_ipfix_header_create (frm, b0, &offset);
981 
982  if (PREDICT_TRUE (do_flush == 0))
983  {
984  u64 time_stamp = clib_host_to_net_u64 (now);
985  clib_memcpy_fast (b0->data + offset, &time_stamp, sizeof (time_stamp));
986  offset += sizeof (time_stamp);
987 
988  clib_memcpy_fast (b0->data + offset, &nat_event, sizeof (nat_event));
989  offset += sizeof (nat_event);
990 
991  clib_memcpy_fast (b0->data + offset, &quota_event, sizeof (quota_event));
992  offset += sizeof (quota_event);
993 
994  clib_memcpy_fast (b0->data + offset, &limit, sizeof (limit));
995  offset += sizeof (limit);
996 
998  }
999 
1000  if (PREDICT_FALSE
1001  (do_flush || (offset + MAX_SESSIONS_LEN) > frm->path_mtu))
1002  {
1003  template_id = clib_atomic_fetch_or (
1004  &silm->max_sessions_template_id,
1005  0);
1006  snat_ipfix_send (frm, f, b0, template_id);
1007  sitd->max_sessions_frame = 0;
1008  sitd->max_sessions_buffer = 0;
1009  offset = 0;
1010  }
1012 }
1013 
1014 static void
1015 nat_ipfix_logging_max_bib (u32 thread_index, u32 limit, int do_flush)
1016 {
1018  snat_ipfix_per_thread_data_t *sitd = &silm->per_thread_data[thread_index];
1020  vlib_frame_t *f;
1021  vlib_buffer_t *b0 = 0;
1022  u32 bi0 = ~0;
1023  u32 offset;
1024  vlib_main_t *vm = frm->vlib_main;
1025  u64 now;
1026  u8 nat_event = QUOTA_EXCEEDED;
1027  u32 quota_event = MAX_BIB_ENTRIES;
1028  u16 template_id;
1029 
1030  now = (u64) ((vlib_time_now (vm) - silm->vlib_time_0) * 1e3);
1031  now += silm->milisecond_time_0;
1032 
1033  b0 = sitd->max_bibs_buffer;
1034 
1035  if (PREDICT_FALSE (b0 == 0))
1036  {
1037  if (do_flush)
1038  return;
1039 
1040  if (vlib_buffer_alloc (vm, &bi0, 1) != 1)
1041  {
1042  nat_elog_err ("can't allocate buffer for NAT IPFIX event");
1043  return;
1044  }
1045 
1046  b0 = sitd->max_bibs_buffer = vlib_get_buffer (vm, bi0);
1048  offset = 0;
1049  }
1050  else
1051  {
1052  bi0 = vlib_get_buffer_index (vm, b0);
1053  offset = sitd->max_bibs_next_record_offset;
1054  }
1055 
1056  f = sitd->max_bibs_frame;
1057  if (PREDICT_FALSE (f == 0))
1058  {
1059  u32 *to_next;
1060  f = vlib_get_frame_to_node (vm, ip4_lookup_node.index);
1061  sitd->max_bibs_frame = f;
1062  to_next = vlib_frame_vector_args (f);
1063  to_next[0] = bi0;
1064  f->n_vectors = 1;
1065  }
1066 
1067  if (PREDICT_FALSE (offset == 0))
1068  snat_ipfix_header_create (frm, b0, &offset);
1069 
1070  if (PREDICT_TRUE (do_flush == 0))
1071  {
1072  u64 time_stamp = clib_host_to_net_u64 (now);
1073  clib_memcpy_fast (b0->data + offset, &time_stamp, sizeof (time_stamp));
1074  offset += sizeof (time_stamp);
1075 
1076  clib_memcpy_fast (b0->data + offset, &nat_event, sizeof (nat_event));
1077  offset += sizeof (nat_event);
1078 
1079  clib_memcpy_fast (b0->data + offset, &quota_event, sizeof (quota_event));
1080  offset += sizeof (quota_event);
1081 
1082  clib_memcpy_fast (b0->data + offset, &limit, sizeof (limit));
1083  offset += sizeof (limit);
1084 
1086  }
1087 
1088  if (PREDICT_FALSE
1089  (do_flush || (offset + MAX_BIBS_LEN) > frm->path_mtu))
1090  {
1091  template_id = clib_atomic_fetch_or (
1092  &silm->max_bibs_template_id,
1093  0);
1094  snat_ipfix_send (frm, f, b0, template_id);
1095  sitd->max_bibs_frame = 0;
1096  sitd->max_bibs_buffer = 0;
1097  offset = 0;
1098  }
1100 }
1101 
1102 static void
1104  u32 limit, u32 src, int do_flush)
1105 {
1107  snat_ipfix_per_thread_data_t *sitd = &silm->per_thread_data[thread_index];
1109  vlib_frame_t *f;
1110  vlib_buffer_t *b0 = 0;
1111  u32 bi0 = ~0;
1112  u32 offset;
1113  vlib_main_t *vm = frm->vlib_main;
1114  u64 now;
1115  u8 nat_event = QUOTA_EXCEEDED;
1116  u32 quota_event = MAX_FRAGMENTS_PENDING_REASSEMBLY;
1117  u16 template_id;
1118 
1119  now = (u64) ((vlib_time_now (vm) - silm->vlib_time_0) * 1e3);
1120  now += silm->milisecond_time_0;
1121 
1122  b0 = sitd->max_frags_ip4_buffer;
1123 
1124  if (PREDICT_FALSE (b0 == 0))
1125  {
1126  if (do_flush)
1127  return;
1128 
1129  if (vlib_buffer_alloc (vm, &bi0, 1) != 1)
1130  {
1131  nat_elog_err ("can't allocate buffer for NAT IPFIX event");
1132  return;
1133  }
1134 
1135  b0 = sitd->max_frags_ip4_buffer = vlib_get_buffer (vm, bi0);
1137  offset = 0;
1138  }
1139  else
1140  {
1141  bi0 = vlib_get_buffer_index (vm, b0);
1142  offset = sitd->max_frags_ip4_next_record_offset;
1143  }
1144 
1145  f = sitd->max_frags_ip4_frame;
1146  if (PREDICT_FALSE (f == 0))
1147  {
1148  u32 *to_next;
1149  f = vlib_get_frame_to_node (vm, ip4_lookup_node.index);
1150  sitd->max_frags_ip4_frame = f;
1151  to_next = vlib_frame_vector_args (f);
1152  to_next[0] = bi0;
1153  f->n_vectors = 1;
1154  }
1155 
1156  if (PREDICT_FALSE (offset == 0))
1157  snat_ipfix_header_create (frm, b0, &offset);
1158 
1159  if (PREDICT_TRUE (do_flush == 0))
1160  {
1161  u64 time_stamp = clib_host_to_net_u64 (now);
1162  clib_memcpy_fast (b0->data + offset, &time_stamp, sizeof (time_stamp));
1163  offset += sizeof (time_stamp);
1164 
1165  clib_memcpy_fast (b0->data + offset, &nat_event, sizeof (nat_event));
1166  offset += sizeof (nat_event);
1167 
1168  clib_memcpy_fast (b0->data + offset, &quota_event, sizeof (quota_event));
1169  offset += sizeof (quota_event);
1170 
1171  clib_memcpy_fast (b0->data + offset, &limit, sizeof (limit));
1172  offset += sizeof (limit);
1173 
1174  clib_memcpy_fast (b0->data + offset, &src, sizeof (src));
1175  offset += sizeof (src);
1176 
1178  }
1179 
1180  if (PREDICT_FALSE
1181  (do_flush || (offset + MAX_BIBS_LEN) > frm->path_mtu))
1182  {
1183  template_id = clib_atomic_fetch_or (
1185  0);
1186  snat_ipfix_send (frm, f, b0, template_id);
1187  sitd->max_frags_ip4_frame = 0;
1188  sitd->max_frags_ip4_buffer = 0;
1189  offset = 0;
1190  }
1192 }
1193 
1194 static void
1196  u32 limit, ip6_address_t * src, int do_flush)
1197 {
1199  snat_ipfix_per_thread_data_t *sitd = &silm->per_thread_data[thread_index];
1201  vlib_frame_t *f;
1202  vlib_buffer_t *b0 = 0;
1203  u32 bi0 = ~0;
1204  u32 offset;
1205  vlib_main_t *vm = frm->vlib_main;
1206  u64 now;
1207  u8 nat_event = QUOTA_EXCEEDED;
1208  u32 quota_event = MAX_FRAGMENTS_PENDING_REASSEMBLY;
1209  u16 template_id;
1210 
1211  now = (u64) ((vlib_time_now (vm) - silm->vlib_time_0) * 1e3);
1212  now += silm->milisecond_time_0;
1213 
1214  b0 = sitd->max_frags_ip6_buffer;
1215 
1216  if (PREDICT_FALSE (b0 == 0))
1217  {
1218  if (do_flush)
1219  return;
1220 
1221  if (vlib_buffer_alloc (vm, &bi0, 1) != 1)
1222  {
1223  nat_elog_err ("can't allocate buffer for NAT IPFIX event");
1224  return;
1225  }
1226 
1227  b0 = sitd->max_frags_ip6_buffer = vlib_get_buffer (vm, bi0);
1229  offset = 0;
1230  }
1231  else
1232  {
1233  bi0 = vlib_get_buffer_index (vm, b0);
1234  offset = sitd->max_frags_ip6_next_record_offset;
1235  }
1236 
1237  f = sitd->max_frags_ip6_frame;
1238  if (PREDICT_FALSE (f == 0))
1239  {
1240  u32 *to_next;
1241  f = vlib_get_frame_to_node (vm, ip4_lookup_node.index);
1242  sitd->max_frags_ip6_frame = f;
1243  to_next = vlib_frame_vector_args (f);
1244  to_next[0] = bi0;
1245  f->n_vectors = 1;
1246  }
1247 
1248  if (PREDICT_FALSE (offset == 0))
1249  snat_ipfix_header_create (frm, b0, &offset);
1250 
1251  if (PREDICT_TRUE (do_flush == 0))
1252  {
1253  u64 time_stamp = clib_host_to_net_u64 (now);
1254  clib_memcpy_fast (b0->data + offset, &time_stamp, sizeof (time_stamp));
1255  offset += sizeof (time_stamp);
1256 
1257  clib_memcpy_fast (b0->data + offset, &nat_event, sizeof (nat_event));
1258  offset += sizeof (nat_event);
1259 
1260  clib_memcpy_fast (b0->data + offset, &quota_event, sizeof (quota_event));
1261  offset += sizeof (quota_event);
1262 
1263  clib_memcpy_fast (b0->data + offset, &limit, sizeof (limit));
1264  offset += sizeof (limit);
1265 
1266  clib_memcpy_fast (b0->data + offset, src, sizeof (ip6_address_t));
1267  offset += sizeof (ip6_address_t);
1268 
1270  }
1271 
1272  if (PREDICT_FALSE
1273  (do_flush || (offset + MAX_BIBS_LEN) > frm->path_mtu))
1274  {
1275  template_id = clib_atomic_fetch_or (
1277  0);
1278  snat_ipfix_send (frm, f, b0, template_id);
1279  sitd->max_frags_ip6_frame = 0;
1280  sitd->max_frags_ip6_buffer = 0;
1281  offset = 0;
1282  }
1284 }
1285 
1286 static void
1287 nat_ipfix_logging_nat64_bibe (u32 thread_index, u8 nat_event,
1288  ip6_address_t * src_ip, u32 nat_src_ip,
1289  u8 proto, u16 src_port, u16 nat_src_port,
1290  u32 vrf_id, int do_flush)
1291 {
1293  snat_ipfix_per_thread_data_t *sitd = &silm->per_thread_data[thread_index];
1295  vlib_frame_t *f;
1296  vlib_buffer_t *b0 = 0;
1297  u32 bi0 = ~0;
1298  u32 offset;
1299  vlib_main_t *vm = frm->vlib_main;
1300  u64 now;
1301  u16 template_id;
1302 
1303  now = (u64) ((vlib_time_now (vm) - silm->vlib_time_0) * 1e3);
1304  now += silm->milisecond_time_0;
1305 
1306  b0 = sitd->nat64_bib_buffer;
1307 
1308  if (PREDICT_FALSE (b0 == 0))
1309  {
1310  if (do_flush)
1311  return;
1312 
1313  if (vlib_buffer_alloc (vm, &bi0, 1) != 1)
1314  {
1315  nat_elog_err ("can't allocate buffer for NAT IPFIX event");
1316  return;
1317  }
1318 
1319  b0 = sitd->nat64_bib_buffer = vlib_get_buffer (vm, bi0);
1321  offset = 0;
1322  }
1323  else
1324  {
1325  bi0 = vlib_get_buffer_index (vm, b0);
1326  offset = sitd->nat64_bib_next_record_offset;
1327  }
1328 
1329  f = sitd->nat64_bib_frame;
1330  if (PREDICT_FALSE (f == 0))
1331  {
1332  u32 *to_next;
1333  f = vlib_get_frame_to_node (vm, ip4_lookup_node.index);
1334  sitd->nat64_bib_frame = f;
1335  to_next = vlib_frame_vector_args (f);
1336  to_next[0] = bi0;
1337  f->n_vectors = 1;
1338  }
1339 
1340  if (PREDICT_FALSE (offset == 0))
1341  snat_ipfix_header_create (frm, b0, &offset);
1342 
1343  if (PREDICT_TRUE (do_flush == 0))
1344  {
1345  u64 time_stamp = clib_host_to_net_u64 (now);
1346  clib_memcpy_fast (b0->data + offset, &time_stamp, sizeof (time_stamp));
1347  offset += sizeof (time_stamp);
1348 
1349  clib_memcpy_fast (b0->data + offset, &nat_event, sizeof (nat_event));
1350  offset += sizeof (nat_event);
1351 
1352  clib_memcpy_fast (b0->data + offset, src_ip, sizeof (ip6_address_t));
1353  offset += sizeof (ip6_address_t);
1354 
1355  clib_memcpy_fast (b0->data + offset, &nat_src_ip, sizeof (nat_src_ip));
1356  offset += sizeof (nat_src_ip);
1357 
1358  clib_memcpy_fast (b0->data + offset, &proto, sizeof (proto));
1359  offset += sizeof (proto);
1360 
1361  clib_memcpy_fast (b0->data + offset, &src_port, sizeof (src_port));
1362  offset += sizeof (src_port);
1363 
1364  clib_memcpy_fast (b0->data + offset, &nat_src_port, sizeof (nat_src_port));
1365  offset += sizeof (nat_src_port);
1366 
1367  clib_memcpy_fast (b0->data + offset, &vrf_id, sizeof (vrf_id));
1368  offset += sizeof (vrf_id);
1369 
1371  }
1372 
1373  if (PREDICT_FALSE
1374  (do_flush || (offset + NAT64_BIB_LEN) > frm->path_mtu))
1375  {
1376  template_id = clib_atomic_fetch_or (
1377  &silm->nat64_bib_template_id,
1378  0);
1379  snat_ipfix_send (frm, f, b0, template_id);
1380  sitd->nat64_bib_frame = 0;
1381  sitd->nat64_bib_buffer = 0;
1382  offset = 0;
1383  }
1385 }
1386 
1387 static void
1388 nat_ipfix_logging_nat64_ses (u32 thread_index, u8 nat_event,
1389  ip6_address_t * src_ip, u32 nat_src_ip,
1390  u8 proto, u16 src_port, u16 nat_src_port,
1391  ip6_address_t * dst_ip, u32 nat_dst_ip,
1392  u16 dst_port, u16 nat_dst_port,
1393  u32 vrf_id, int do_flush)
1394 {
1396  snat_ipfix_per_thread_data_t *sitd = &silm->per_thread_data[thread_index];
1398  vlib_frame_t *f;
1399  vlib_buffer_t *b0 = 0;
1400  u32 bi0 = ~0;
1401  u32 offset;
1402  vlib_main_t *vm = frm->vlib_main;
1403  u64 now;
1404  u16 template_id;
1405 
1406  now = (u64) ((vlib_time_now (vm) - silm->vlib_time_0) * 1e3);
1407  now += silm->milisecond_time_0;
1408 
1409  b0 = sitd->nat64_ses_buffer;
1410 
1411  if (PREDICT_FALSE (b0 == 0))
1412  {
1413  if (do_flush)
1414  return;
1415 
1416  if (vlib_buffer_alloc (vm, &bi0, 1) != 1)
1417  {
1418  nat_elog_err ("can't allocate buffer for NAT IPFIX event");
1419  return;
1420  }
1421 
1422  b0 = sitd->nat64_ses_buffer = vlib_get_buffer (vm, bi0);
1424  offset = 0;
1425  }
1426  else
1427  {
1428  bi0 = vlib_get_buffer_index (vm, b0);
1429  offset = sitd->nat64_ses_next_record_offset;
1430  }
1431 
1432  f = sitd->nat64_ses_frame;
1433  if (PREDICT_FALSE (f == 0))
1434  {
1435  u32 *to_next;
1436  f = vlib_get_frame_to_node (vm, ip4_lookup_node.index);
1437  sitd->nat64_ses_frame = f;
1438  to_next = vlib_frame_vector_args (f);
1439  to_next[0] = bi0;
1440  f->n_vectors = 1;
1441  }
1442 
1443  if (PREDICT_FALSE (offset == 0))
1444  snat_ipfix_header_create (frm, b0, &offset);
1445 
1446  if (PREDICT_TRUE (do_flush == 0))
1447  {
1448  u64 time_stamp = clib_host_to_net_u64 (now);
1449  clib_memcpy_fast (b0->data + offset, &time_stamp, sizeof (time_stamp));
1450  offset += sizeof (time_stamp);
1451 
1452  clib_memcpy_fast (b0->data + offset, &nat_event, sizeof (nat_event));
1453  offset += sizeof (nat_event);
1454 
1455  clib_memcpy_fast (b0->data + offset, src_ip, sizeof (ip6_address_t));
1456  offset += sizeof (ip6_address_t);
1457 
1458  clib_memcpy_fast (b0->data + offset, &nat_src_ip, sizeof (nat_src_ip));
1459  offset += sizeof (nat_src_ip);
1460 
1461  clib_memcpy_fast (b0->data + offset, &proto, sizeof (proto));
1462  offset += sizeof (proto);
1463 
1464  clib_memcpy_fast (b0->data + offset, &src_port, sizeof (src_port));
1465  offset += sizeof (src_port);
1466 
1467  clib_memcpy_fast (b0->data + offset, &nat_src_port, sizeof (nat_src_port));
1468  offset += sizeof (nat_src_port);
1469 
1470  clib_memcpy_fast (b0->data + offset, dst_ip, sizeof (ip6_address_t));
1471  offset += sizeof (ip6_address_t);
1472 
1473  clib_memcpy_fast (b0->data + offset, &nat_dst_ip, sizeof (nat_dst_ip));
1474  offset += sizeof (nat_dst_ip);
1475 
1476  clib_memcpy_fast (b0->data + offset, &dst_port, sizeof (dst_port));
1477  offset += sizeof (dst_port);
1478 
1479  clib_memcpy_fast (b0->data + offset, &nat_dst_port, sizeof (nat_dst_port));
1480  offset += sizeof (nat_dst_port);
1481 
1482  clib_memcpy_fast (b0->data + offset, &vrf_id, sizeof (vrf_id));
1483  offset += sizeof (vrf_id);
1484 
1486  }
1487 
1488  if (PREDICT_FALSE
1489  (do_flush || (offset + NAT64_SES_LEN) > frm->path_mtu))
1490  {
1491  template_id = clib_atomic_fetch_or (
1492  &silm->nat64_ses_template_id,
1493  0);
1494  snat_ipfix_send (frm, f, b0, template_id);
1495  sitd->nat64_ses_frame = 0;
1496  sitd->nat64_ses_buffer = 0;
1497  offset = 0;
1498  }
1500 }
1501 
1502 void
1503 snat_ipfix_flush (u32 thread_index)
1504 {
1505  int do_flush = 1;
1506 
1507  snat_ipfix_logging_nat44_ses (thread_index,
1508  0, 0, 0, 0, 0, 0, 0, do_flush);
1509  snat_ipfix_logging_addr_exhausted (thread_index, 0, do_flush);
1510  snat_ipfix_logging_max_entries_per_usr (thread_index, 0, 0, do_flush);
1511  nat_ipfix_logging_max_ses (thread_index, 0, do_flush);
1512  nat_ipfix_logging_max_bib (thread_index, 0, do_flush);
1513  nat_ipfix_logging_max_frag_ip4 (thread_index, 0, 0, do_flush);
1514  nat_ipfix_logging_max_frag_ip6 (thread_index, 0, 0, do_flush);
1515  nat_ipfix_logging_nat64_bibe (thread_index,
1516  0, 0, 0, 0, 0, 0, 0, do_flush);
1517  nat_ipfix_logging_nat64_ses (thread_index,
1518  0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, do_flush);
1519 }
1520 
1521 void
1523 {
1525  vlib_main_t *worker_vm;
1526  int i;
1527 
1528  if (PREDICT_TRUE (!clib_atomic_fetch_or(&silm->enabled, 0)))
1529  return;
1530 
1531  if (PREDICT_FALSE (!silm->worker_vms))
1532  {
1533  for (i = 1; i < vec_len (vlib_mains); i++)
1534  {
1535  worker_vm = vlib_mains[i];
1536  if (worker_vm)
1537  vec_add1 (silm->worker_vms, worker_vm);
1538  }
1539  }
1540 
1541  /* Trigger flush for each worker thread */
1542  for (i = 0; i < vec_len (silm->worker_vms); i++)
1543  {
1544  worker_vm = silm->worker_vms[i];
1545  if (worker_vm)
1547  snat_ipfix_flush_node.index);
1548  }
1549 
1550  /* Finally flush main thread */
1551  snat_ipfix_flush (0);
1552 }
1553 
1554 /**
1555  * @brief Generate NAT44 session create event
1556  *
1557  * @param thread_index thread index
1558  * @param src_ip source IPv4 address
1559  * @param nat_src_ip transaltes source IPv4 address
1560  * @param snat_proto NAT transport protocol
1561  * @param src_port source port
1562  * @param nat_src_port translated source port
1563  * @param vrf_id VRF ID
1564  */
1565 void
1567  u32 src_ip,
1568  u32 nat_src_ip,
1569  snat_protocol_t snat_proto,
1570  u16 src_port,
1571  u16 nat_src_port, u32 vrf_id)
1572 {
1573  skip_if_disabled ();
1574 
1575  snat_ipfix_logging_nat44_ses (thread_index, NAT44_SESSION_CREATE, src_ip,
1576  nat_src_ip, snat_proto, src_port, nat_src_port,
1577  vrf_id, 0);
1578 }
1579 
1580 /**
1581  * @brief Generate NAT44 session delete event
1582  *
1583  * @param thread_index thread index
1584  * @param src_ip source IPv4 address
1585  * @param nat_src_ip transaltes source IPv4 address
1586  * @param snat_proto NAT transport protocol
1587  * @param src_port source port
1588  * @param nat_src_port translated source port
1589  * @param vrf_id VRF ID
1590  */
1591 void
1593  u32 src_ip,
1594  u32 nat_src_ip,
1595  snat_protocol_t snat_proto,
1596  u16 src_port,
1597  u16 nat_src_port, u32 vrf_id)
1598 {
1599  skip_if_disabled ();
1600 
1601  snat_ipfix_logging_nat44_ses (thread_index, NAT44_SESSION_DELETE, src_ip,
1602  nat_src_ip, snat_proto, src_port, nat_src_port,
1603  vrf_id, 0);
1604 }
1605 
1606 /**
1607  * @brief Generate NAT addresses exhausted event
1608  *
1609  * @param thread_index thread index
1610  * @param pool_id NAT pool ID
1611  */
1612 void
1614 {
1615  //TODO: This event SHOULD be rate limited
1616  skip_if_disabled ();
1617 
1618  snat_ipfix_logging_addr_exhausted (thread_index, pool_id, 0);
1619 }
1620 
1621 /**
1622  * @brief Generate maximum entries per user exceeded event
1623  *
1624  * @param thread_index thread index
1625  * @param limit maximum NAT entries that can be created per user
1626  * @param src_ip source IPv4 address
1627  */
1628 void
1630 {
1631  //TODO: This event SHOULD be rate limited
1632  skip_if_disabled ();
1633 
1634  snat_ipfix_logging_max_entries_per_usr (thread_index, limit, src_ip, 0);
1635 }
1636 
1637 vlib_frame_t *
1640  flow_report_t * fr,
1641  vlib_frame_t * f,
1642  u32 * to_next, u32 node_index)
1643 {
1645 
1646  return f;
1647 }
1648 
1649 /**
1650  * @brief Generate maximum session entries exceeded event
1651  *
1652  * @param thread_index thread index
1653  * @param limit configured limit
1654  */
1655 void
1657 {
1658  //TODO: This event SHOULD be rate limited
1659  skip_if_disabled ();
1660 
1661  nat_ipfix_logging_max_ses (thread_index, limit, 0);
1662 }
1663 
1664 /**
1665  * @brief Generate maximum BIB entries exceeded event
1666  *
1667  * @param thread_index thread index
1668  * @param limit configured limit
1669  */
1670 void
1671 nat_ipfix_logging_max_bibs (u32 thread_index, u32 limit)
1672 {
1673  //TODO: This event SHOULD be rate limited
1674  skip_if_disabled ();
1675 
1676  nat_ipfix_logging_max_bib (thread_index, limit, 0);
1677 }
1678 
1679 /**
1680  * @brief Generate maximum IPv4 fragments pending reassembly exceeded event
1681  *
1682  * @param thread_index thread index
1683  * @param limit configured limit
1684  * @param src source IPv4 address
1685  */
1686 void
1688  u32 limit, ip4_address_t * src)
1689 {
1690  //TODO: This event SHOULD be rate limited
1691  skip_if_disabled ();
1692 
1693  nat_ipfix_logging_max_frag_ip4 (thread_index, limit, src->as_u32, 0);
1694 }
1695 
1696 /**
1697  * @brief Generate maximum IPv6 fragments pending reassembly exceeded event
1698  *
1699  * @param thread_index thread index
1700  * @param limit configured limit
1701  * @param src source IPv6 address
1702  */
1703 void
1705  u32 limit, ip6_address_t * src)
1706 {
1707  //TODO: This event SHOULD be rate limited
1708  skip_if_disabled ();
1709 
1710  nat_ipfix_logging_max_frag_ip6 (thread_index, limit, src, 0);
1711 }
1712 
1713 /**
1714  * @brief Generate NAT64 BIB create and delete events
1715  *
1716  * @param thread_index thread index
1717  * @param src_ip source IPv6 address
1718  * @param nat_src_ip transaltes source IPv4 address
1719  * @param proto L4 protocol
1720  * @param src_port source port
1721  * @param nat_src_port translated source port
1722  * @param vrf_id VRF ID
1723  * @param is_create non-zero value if create event otherwise delete event
1724  */
1725 void
1727  ip4_address_t * nat_src_ip, u8 proto,
1728  u16 src_port, u16 nat_src_port, u32 vrf_id,
1729  u8 is_create)
1730 {
1731  u8 nat_event;
1732 
1733  skip_if_disabled ();
1734 
1735  nat_event = is_create ? NAT64_BIB_CREATE : NAT64_BIB_DELETE;
1736 
1737  nat_ipfix_logging_nat64_bibe (thread_index, nat_event, src_ip,
1738  nat_src_ip->as_u32, proto, src_port,
1739  nat_src_port, vrf_id, 0);
1740 }
1741 
1742 /**
1743  * @brief Generate NAT64 session create and delete events
1744  *
1745  * @param thread_index thread index
1746  * @param src_ip source IPv6 address
1747  * @param nat_src_ip transaltes source IPv4 address
1748  * @param proto L4 protocol
1749  * @param src_port source port
1750  * @param nat_src_port translated source port
1751  * @param dst_ip destination IPv6 address
1752  * @param nat_dst_ip destination IPv4 address
1753  * @param dst_port destination port
1754  * @param nat_dst_port translated destination port
1755  * @param vrf_id VRF ID
1756  * @param is_create non-zero value if create event otherwise delete event
1757  */
1758 void
1761  ip4_address_t * nat_src_ip, u8 proto,
1762  u16 src_port, u16 nat_src_port,
1764  ip4_address_t * nat_dst_ip, u16 dst_port,
1765  u16 nat_dst_port, u32 vrf_id, u8 is_create)
1766 {
1767  u8 nat_event;
1768 
1769  skip_if_disabled ();
1770 
1771  nat_event = is_create ? NAT64_SESSION_CREATE : NAT64_SESSION_DELETE;
1772 
1773  nat_ipfix_logging_nat64_ses (thread_index, nat_event, src_ip,
1774  nat_src_ip->as_u32, proto, src_port,
1775  nat_src_port, dst_ip, nat_dst_ip->as_u32,
1776  dst_port, nat_dst_port, vrf_id, 0);
1777 }
1778 
1779 vlib_frame_t *
1781  vlib_frame_t * f, u32 * to_next, u32 node_index)
1782 {
1784 
1785  if (PREDICT_FALSE (++silm->call_counter >= vec_len (frm->reports)))
1786  {
1788  silm->call_counter = 0;
1789  }
1790 
1791  return f;
1792 }
1793 
1794 /**
1795  * @brief Enable/disable NAT plugin IPFIX logging
1796  *
1797  * @param enable 1 if enable, 0 if disable
1798  * @param domain_id observation domain ID
1799  * @param src_port source port number
1800  *
1801  * @returns 0 if success
1802  */
1803 int
1805 {
1806  snat_main_t *sm = &snat_main;
1810  int rv;
1811  u8 e = enable ? 1 : 0;
1812 
1813  if (clib_atomic_cmp_and_swap (&silm->enabled, e ^ 1, e) == e)
1814  return 0;
1815 
1816  clib_memset (&a, 0, sizeof (a));
1817  a.is_add = enable;
1818  a.domain_id = domain_id ? domain_id : 1;
1819  a.src_port = src_port ? src_port : UDP_DST_PORT_ipfix;
1821 
1822  if (sm->deterministic)
1823  {
1825 
1826  rv = vnet_flow_report_add_del (frm, &a, NULL);
1827  if (rv)
1828  {
1829  nat_elog_warn_X1 ("vnet_flow_report_add_del returned %d", "i4", rv);
1830  return -1;
1831  }
1832  }
1833  else
1834  {
1836 
1837  rv = vnet_flow_report_add_del (frm, &a, NULL);
1838  if (rv)
1839  {
1840  nat_elog_warn_X1 ("vnet_flow_report_add_del returned %d", "i4", rv);
1841  return -1;
1842  }
1843 
1845 
1846  rv = vnet_flow_report_add_del (frm, &a, NULL);
1847  if (rv)
1848  {
1849  nat_elog_warn_X1 ("vnet_flow_report_add_del returned %d", "i4", rv);
1850  return -1;
1851  }
1852 
1854 
1855  rv = vnet_flow_report_add_del (frm, &a, NULL);
1856  if (rv)
1857  {
1858  nat_elog_warn_X1 ("vnet_flow_report_add_del returned %d", "i4", rv);
1859  return -1;
1860  }
1861 
1863 
1864  rv = vnet_flow_report_add_del (frm, &a, NULL);
1865  if (rv)
1866  {
1867  nat_elog_warn_X1 ("vnet_flow_report_add_del returned %d", "i4", rv);
1868  return -1;
1869  }
1870 
1872 
1873  rv = vnet_flow_report_add_del (frm, &a, NULL);
1874  if (rv)
1875  {
1876  nat_elog_warn_X1 ("vnet_flow_report_add_del returned %d", "i4", rv);
1877  return -1;
1878  }
1879 
1881 
1882  rv = vnet_flow_report_add_del (frm, &a, NULL);
1883  if (rv)
1884  {
1885  nat_elog_warn_X1 ("vnet_flow_report_add_del returned %d", "i4", rv);
1886  return -1;
1887  }
1888 
1890 
1891  rv = vnet_flow_report_add_del (frm, &a, NULL);
1892  if (rv)
1893  {
1894  nat_elog_warn_X1 ("vnet_flow_report_add_del returned %d", "i4", rv);
1895  return -1;
1896  }
1897 
1899 
1900  rv = vnet_flow_report_add_del (frm, &a, NULL);
1901  if (rv)
1902  {
1903  nat_elog_warn_X1 ("vnet_flow_report_add_del returned %d", "i4", rv);
1904  return -1;
1905  }
1906 
1907  if (sm->endpoint_dependent)
1908  {
1910 
1911  rv = vnet_flow_report_add_del (frm, &a, NULL);
1912  if (rv)
1913  {
1914  nat_elog_warn_X1 ("vnet_flow_report_add_del returned %d", "i4", rv);
1915  return -1;
1916  }
1917  }
1918  }
1919 
1920  return 0;
1921 }
1922 
1923 /**
1924  * @brief Initialize NAT plugin IPFIX logging
1925  *
1926  * @param vm vlib main
1927  */
1928 void
1930 {
1933 
1934  silm->enabled = 0;
1935  silm->worker_vms = 0;
1936  silm->call_counter = 0;
1937 
1938  /* Set up time reference pair */
1939  silm->vlib_time_0 = vlib_time_now (vm);
1940  silm->milisecond_time_0 = unix_time_now_nsec () * 1e-6;
1941 
1942  vec_validate (silm->per_thread_data, tm->n_vlib_mains - 1);
1943 }
1944 
1945 static uword
1947  vlib_node_runtime_t *rt,
1948  vlib_frame_t *f)
1949 {
1951  return 0;
1952 }
1953 
1954 /* *INDENT-OFF* */
1955 VLIB_REGISTER_NODE (snat_ipfix_flush_node) = {
1956  .function = ipfix_flush_process,
1957  .name = "snat-ipfix-flush",
1958  .type = VLIB_NODE_TYPE_INPUT,
1959  .state = VLIB_NODE_STATE_INTERRUPT,
1960 };
1961 /* *INDENT-ON* */
#define vec_validate(V, I)
Make sure vector is long enough for given index (no header, unspecified alignment) ...
Definition: vec.h:440
u32 flags
buffer flags: VLIB_BUFFER_FREE_LIST_INDEX_MASK: bits used to store free list index, VLIB_BUFFER_IS_TRACED: trace this buffer.
Definition: buffer.h:124
void snat_ipfix_logging_max_entries_per_user(u32 thread_index, u32 limit, u32 src_ip)
Generate maximum entries per user exceeded event.
u8 * snat_template_rewrite_addr_exhausted(flow_report_main_t *frm, flow_report_t *fr, ip4_address_t *collector_address, ip4_address_t *src_address, u16 collector_port, ipfix_report_element_t *elts, u32 n_elts, u32 *stream_index)
u8 proto
Definition: acl_types.api:47
a
Definition: bitmap.h:538
#define MAX_FRAGMENTS_IP6_LEN
ip4_address_t src_address
Definition: ip4_packet.h:170
u8 * nat_template_rewrite_max_sessions(flow_report_main_t *frm, flow_report_t *fr, ip4_address_t *collector_address, ip4_address_t *src_address, u16 collector_port, ipfix_report_element_t *elts, u32 n_elts, u32 *stream_index)
void snat_ipfix_flush_from_main(void)
#define PREDICT_TRUE(x)
Definition: clib.h:112
i16 current_data
signed offset in data[], pre_data[] that we are currently processing.
Definition: buffer.h:110
unsigned long u64
Definition: types.h:89
vlib_buffer_t * max_frags_ip4_buffer
static void vlib_node_set_interrupt_pending(vlib_main_t *vm, u32 node_index)
Definition: node_funcs.h:197
#define clib_memcpy_fast(a, b, c)
Definition: string.h:81
static u32 ipfix_e_id_length(int e, u16 id, u16 length)
Definition: ipfix_packet.h:77
vlib_buffer_t * addr_exhausted_buffer
#define NULL
Definition: clib.h:58
clib_memset(h->entries, 0, sizeof(h->entries[0]) *entries)
static f64 vlib_time_now(vlib_main_t *vm)
Definition: main.h:279
#define NAT44_SESSION_CREATE_FIELD_COUNT
u32 stream_index
Definition: flow_report.h:91
int vnet_flow_report_add_del(flow_report_main_t *frm, vnet_flow_report_add_del_args_t *a, u16 *template_id)
Definition: flow_report.c:334
u32 thread_index
Definition: main.h:218
u8 * nat_template_rewrite_max_bibs(flow_report_main_t *frm, flow_report_t *fr, ip4_address_t *collector_address, ip4_address_t *src_address, u16 collector_port, ipfix_report_element_t *elts, u32 n_elts, u32 *stream_index)
u16 current_length
Nbytes between current data and the end of this buffer.
Definition: buffer.h:113
u8 data[0]
Packet data.
Definition: buffer.h:181
#define vec_add1(V, E)
Add 1 element to end of vector (unspecified alignment).
Definition: vec.h:523
vl_api_address_t src
Definition: gre.api:60
int i
static uword ipfix_flush_process(vlib_main_t *vm, vlib_node_runtime_t *rt, vlib_frame_t *f)
ip4_address_t src_address
Definition: flow_report.h:119
static void nat_ipfix_logging_nat64_bibe(u32 thread_index, u8 nat_event, ip6_address_t *src_ip, u32 nat_src_ip, u8 proto, u16 src_port, u16 nat_src_port, u32 vrf_id, int do_flush)
u16 flags_and_fragment_offset
Definition: ip4_packet.h:151
u8 enabled
NAT plugin IPFIX logging enabled.
#define vec_validate_aligned(V, I, A)
Make sure vector is long enough for given index (no header, specified alignment)
Definition: vec.h:451
#define MAX_SESSIONS_FIELD_COUNT
vlib_main_t ** vlib_mains
Definition: buffer.c:332
snat_ipfix_per_thread_data_t * per_thread_data
unsigned char u8
Definition: types.h:56
u8 deterministic
Definition: nat.h:661
ip4_address_t ipfix_collector
Definition: flow_report.h:117
double f64
Definition: types.h:142
vlib_node_registration_t ip4_lookup_node
(constructor) VLIB_REGISTER_NODE (ip4_lookup_node)
Definition: ip4_forward.c:102
#define NAT64_SES_LEN
u8 * snat_template_rewrite_nat44_session(flow_report_main_t *frm, flow_report_t *fr, ip4_address_t *collector_address, ip4_address_t *src_address, u16 collector_port, ipfix_report_element_t *elts, u32 n_elts, u32 *stream_index)
u16 src_port
Definition: udp.api:41
flow_report_stream_t * streams
Definition: flow_report.h:114
static void nat_ipfix_logging_max_frag_ip4(u32 thread_index, u32 limit, u32 src, int do_flush)
#define update_template_id(old_id, new_id)
vlib_frame_t * deterministic_nat_data_callback(flow_report_main_t *frm, flow_report_t *fr, vlib_frame_t *f, u32 *to_next, u32 node_index)
void nat_ipfix_logging_max_bibs(u32 thread_index, u32 limit)
Generate maximum BIB entries exceeded event.
ip4_address_t dst_address
Definition: ip4_packet.h:170
vnet_flow_rewrite_callback_t * rewrite_callback
Definition: flow_report.h:149
snat_ipfix_logging_main_t snat_ipfix_logging_main
vlib_frame_t * vlib_get_frame_to_node(vlib_main_t *vm, u32 to_node_index)
Definition: main.c:185
#define clib_atomic_fetch_or(a, b)
Definition: atomics.h:27
void snat_ipfix_logging_init(vlib_main_t *vm)
Initialize NAT plugin IPFIX logging.
int snat_ipfix_logging_enable_disable(int enable, u32 domain_id, u16 src_port)
Enable/disable NAT plugin IPFIX logging.
#define NAT44_SESSION_CREATE_LEN
void snat_ipfix_logging_addresses_exhausted(u32 thread_index, u32 pool_id)
Generate NAT addresses exhausted event.
unsigned int u32
Definition: types.h:88
void nat_ipfix_logging_max_fragments_ip4(u32 thread_index, u32 limit, ip4_address_t *src)
Generate maximum IPv4 fragments pending reassembly exceeded event.
u8 * snat_template_rewrite_max_entries_per_usr(flow_report_main_t *frm, flow_report_t *fr, ip4_address_t *collector_address, ip4_address_t *src_address, u16 collector_port, ipfix_report_element_t *elts, u32 n_elts, u32 *stream_index)
static u8 * snat_template_rewrite(flow_report_main_t *frm, flow_report_t *fr, ip4_address_t *collector_address, ip4_address_t *src_address, u16 collector_port, nat_event_t event, quota_exceed_event_t quota_event)
Create an IPFIX template packet rewrite string.
static void snat_ipfix_send(flow_report_main_t *frm, vlib_frame_t *f, vlib_buffer_t *b0, u16 template_id)
void nat_ipfix_logging_max_sessions(u32 thread_index, u32 limit)
Generate maximum session entries exceeded event.
#define MAX_FRAGMENTS_FIELD_COUNT
static u32 vlib_get_buffer_index(vlib_main_t *vm, void *p)
Translate buffer pointer into buffer index.
Definition: buffer_funcs.h:257
flow_report_t * reports
Definition: flow_report.h:113
void snat_ipfix_flush(u32 thread_index)
static void nat_ipfix_logging_max_bib(u32 thread_index, u32 limit, int do_flush)
#define nat_elog_warn_X1(nat_elog_fmt_str, nat_elog_fmt_arg, nat_elog_val1)
Definition: nat.h:1036
flow_report_main_t flow_report_main
Definition: flow_report.c:21
quota_exceed_event_t
vlib_main_t ** worker_vms
vector of worker vlib mains
vlib_frame_t * data_callback(flow_report_main_t *frm, flow_report_t *fr, vlib_frame_t *f, u32 *to_next, u32 node_index)
#define NAT_ADDRESSES_EXHAUTED_LEN
unsigned short u16
Definition: types.h:57
void vlib_put_frame_to_node(vlib_main_t *vm, u32 to_node_index, vlib_frame_t *f)
Definition: main.c:194
static void * vlib_buffer_get_current(vlib_buffer_t *b)
Get pointer to current data to process.
Definition: buffer.h:229
#define PREDICT_FALSE(x)
Definition: clib.h:111
static void snat_ipfix_logging_nat44_ses(u32 thread_index, u8 nat_event, u32 src_ip, u32 nat_src_ip, snat_protocol_t snat_proto, u16 src_port, u16 nat_src_port, u32 vrf_id, int do_flush)
vlib_frame_t * max_entries_per_user_frame
void nat_ipfix_logging_max_fragments_ip6(u32 thread_index, u32 limit, ip6_address_t *src)
Generate maximum IPv6 fragments pending reassembly exceeded event.
vl_api_address_union_t src_address
Definition: ip_types.api:98
void nat_ipfix_logging_nat64_bib(u32 thread_index, ip6_address_t *src_ip, ip4_address_t *nat_src_ip, u8 proto, u16 src_port, u16 nat_src_port, u32 vrf_id, u8 is_create)
Generate NAT64 BIB create and delete events.
static u32 version_length(u16 length)
Definition: ipfix_packet.h:33
u16 call_counter
nat data callbacks call counter
vlib_main_t * vm
Definition: in2out_ed.c:1810
#define MAX_BIBS_LEN
u64 milisecond_time_0
Time reference pair.
vlib_node_registration_t snat_ipfix_flush_node
(constructor) VLIB_REGISTER_NODE (snat_ipfix_flush_node)
snat_main_t snat_main
Definition: nat.c:39
static void nat_ipfix_logging_nat64_ses(u32 thread_index, u8 nat_event, ip6_address_t *src_ip, u32 nat_src_ip, u8 proto, u16 src_port, u16 nat_src_port, ip6_address_t *dst_ip, u32 nat_dst_ip, u16 dst_port, u16 nat_dst_port, u32 vrf_id, int do_flush)
void snat_ipfix_logging_nat44_ses_delete(u32 thread_index, u32 src_ip, u32 nat_src_ip, snat_protocol_t snat_proto, u16 src_port, u16 nat_src_port, u32 vrf_id)
Generate NAT44 session delete event.
static void snat_ipfix_logging_addr_exhausted(u32 thread_index, u32 pool_id, int do_flush)
#define VLIB_REGISTER_NODE(x,...)
Definition: node.h:169
static u8 snat_proto_to_ip_proto(snat_protocol_t snat_proto)
Definition: nat_inlines.h:162
u16 n_vectors
Definition: node.h:397
vlib_buffer_t * max_entries_per_user_buffer
static u32 ipfix_id_count(u16 id, u16 count)
Definition: ipfix_packet.h:184
static void nat_ipfix_logging_max_ses(u32 thread_index, u32 limit, int do_flush)
static u64 unix_time_now_nsec(void)
Definition: time.h:264
void nat_ipfix_logging_nat64_session(u32 thread_index, ip6_address_t *src_ip, ip4_address_t *nat_src_ip, u8 proto, u16 src_port, u16 nat_src_port, ip6_address_t *dst_ip, ip4_address_t *nat_dst_ip, u16 dst_port, u16 nat_dst_port, u32 vrf_id, u8 is_create)
Generate NAT64 session create and delete events.
u16 nat44_session_template_id
template IDs
u8 * nat_template_rewrite_nat64_session(flow_report_main_t *frm, flow_report_t *fr, ip4_address_t *collector_address, ip4_address_t *src_address, u16 collector_port, ipfix_report_element_t *elts, u32 n_elts, u32 *stream_index)
#define clib_atomic_cmp_and_swap(addr, old, new)
Definition: atomics.h:37
#define MAX_BIBS_FIELD_COUNT
#define ASSERT(truth)
vlib_main_t * vlib_main
Definition: flow_report.h:136
u16 ip4_tcp_udp_compute_checksum(vlib_main_t *vm, vlib_buffer_t *p0, ip4_header_t *ip0)
Definition: ip4_forward.c:1302
#define MAX_FRAGMENTS_IP4_LEN
vlib_frame_t * nat44_session_frame
frames containing ipfix buffers
u16 template_id
Definition: flow_report.h:90
u8 * nat_template_rewrite_nat64_bib(flow_report_main_t *frm, flow_report_t *fr, ip4_address_t *collector_address, ip4_address_t *src_address, u16 collector_port, ipfix_report_element_t *elts, u32 n_elts, u32 *stream_index)
static void nat_ipfix_logging_max_frag_ip6(u32 thread_index, u32 limit, ip6_address_t *src, int do_flush)
#define clib_atomic_fetch_add(a, b)
Definition: atomics.h:23
vlib_buffer_t * nat44_session_buffer
ipfix buffers under construction
vl_api_address_t src_ip
Definition: udp.api:43
struct _vlib_node_registration vlib_node_registration_t
template key/value backing page structure
Definition: bihash_doc.h:44
static u32 ipfix_set_id_length(u16 set_id, u16 length)
Definition: ipfix_packet.h:121
u8 * nat_template_rewrite_max_frags_ip4(flow_report_main_t *frm, flow_report_t *fr, ip4_address_t *collector_address, ip4_address_t *src_address, u16 collector_port, ipfix_report_element_t *elts, u32 n_elts, u32 *stream_index)
Definition: defs.h:47
nat_event_t
#define nat_elog_err(nat_elog_str)
Definition: nat.h:1027
vl_api_address_t ip
Definition: l2.api:490
#define MAX_ENTRIES_PER_USER_LEN
#define MAX_ENTRIES_PER_USER_FIELD_COUNT
u32 nat44_session_next_record_offset
next record offset
#define vec_len(v)
Number of elements in vector (rvalue-only, NULL tolerant)
static void snat_ipfix_logging_max_entries_per_usr(u32 thread_index, u32 limit, u32 src_ip, int do_flush)
#define VLIB_BUFFER_TRACE_TRAJECTORY_INIT(b)
Definition: buffer.h:492
VLIB buffer representation.
Definition: buffer.h:102
#define skip_if_disabled()
u64 uword
Definition: types.h:112
static void * vlib_frame_vector_args(vlib_frame_t *f)
Get pointer to frame vector data.
Definition: node_funcs.h:244
snat_protocol_t
Definition: nat.h:189
vnet_flow_data_callback_t * flow_data_callback
Definition: flow_report.h:148
struct clib_bihash_value offset
template key/value backing page structure
vl_api_address_t dst_ip
Definition: udp.api:44
#define NAT_ADDRESSES_EXHAUTED_FIELD_COUNT
#define vnet_buffer(b)
Definition: buffer.h:408
#define NAT64_SES_FIELD_COUNT
static vlib_thread_main_t * vlib_get_thread_main()
Definition: global_funcs.h:32
#define NAT64_BIB_LEN
static void snat_ipfix_header_create(flow_report_main_t *frm, vlib_buffer_t *b0, u32 *offset)
vlib_buffer_t * max_frags_ip6_buffer
#define MAX_SESSIONS_LEN
u32 vrf_id
Definition: nat.api:821
u8 endpoint_dependent
Definition: nat.h:663
u16 dst_port
Definition: udp.api:42
u8 ip_version_and_header_length
Definition: ip4_packet.h:138
#define CLIB_CACHE_LINE_BYTES
Definition: cache.h:59
u8 * nat_template_rewrite_max_frags_ip6(flow_report_main_t *frm, flow_report_t *fr, ip4_address_t *collector_address, ip4_address_t *src_address, u16 collector_port, ipfix_report_element_t *elts, u32 n_elts, u32 *stream_index)
static u32 vlib_buffer_alloc(vlib_main_t *vm, u32 *buffers, u32 n_buffers)
Allocate buffers into supplied array.
Definition: buffer_funcs.h:630
static vlib_buffer_t * vlib_get_buffer(vlib_main_t *vm, u32 buffer_index)
Translate buffer index into buffer pointer.
Definition: buffer_funcs.h:85
static u16 ip4_header_checksum(ip4_header_t *i)
Definition: ip4_packet.h:247
Definition: defs.h:46
#define NAT64_BIB_FIELD_COUNT
void snat_ipfix_logging_nat44_ses_create(u32 thread_index, u32 src_ip, u32 nat_src_ip, snat_protocol_t snat_proto, u16 src_port, u16 nat_src_port, u32 vrf_id)
Generate NAT44 session create event.