NAT44: add support for session timeout (VPP-1272)
[vpp.git] / src / plugins / nat / nat44_cli.c
index f61f59b..e51f6d6 100644 (file)
 #include <nat/nat.h>
 #include <nat/nat_ipfix_logging.h>
 #include <nat/nat_det.h>
+#include <nat/nat64.h>
+#include <nat/nat_inlines.h>
 #include <vnet/fib/fib_table.h>
 
+#define UNSUPPORTED_IN_DET_MODE_STR \
+  "This command is unsupported in deterministic mode"
+#define SUPPORTED_ONLY_IN_DET_MODE_STR \
+  "This command is supported only in deterministic mode"
+
 static clib_error_t *
 set_workers_command_fn (vlib_main_t * vm,
                        unformat_input_t * input, vlib_cli_command_t * cmd)
 {
   unformat_input_t _line_input, *line_input = &_line_input;
+  snat_main_t *sm = &snat_main;
   uword *bitmap = 0;
   int rv = 0;
   clib_error_t *error = 0;
 
+  if (sm->deterministic)
+    return clib_error_return (0, UNSUPPORTED_IN_DET_MODE_STR);
+
   /* Get a line of input. */
   if (!unformat_user (input, unformat_line_input, line_input))
     return 0;
@@ -83,6 +94,9 @@ nat_show_workers_commnad_fn (vlib_main_t * vm, unformat_input_t * input,
   snat_main_t *sm = &snat_main;
   u32 *worker;
 
+  if (sm->deterministic)
+    return clib_error_return (0, UNSUPPORTED_IN_DET_MODE_STR);
+
   if (sm->num_workers > 1)
     {
       vlib_cli_output (vm, "%d workers", vec_len (sm->workers));
@@ -145,15 +159,61 @@ done:
   return error;
 }
 
+static clib_error_t *
+nat44_show_hash_commnad_fn (vlib_main_t * vm, unformat_input_t * input,
+                           vlib_cli_command_t * cmd)
+{
+  snat_main_t *sm = &snat_main;
+  snat_main_per_thread_data_t *tsm;
+  int i;
+  int verbose = 0;
+
+  if (unformat (input, "detail"))
+    verbose = 1;
+  else if (unformat (input, "verbose"))
+    verbose = 2;
+
+  vlib_cli_output (vm, "%U", format_bihash_8_8, &sm->static_mapping_by_local,
+                  verbose);
+  vlib_cli_output (vm, "%U",
+                  format_bihash_8_8, &sm->static_mapping_by_external,
+                  verbose);
+  vec_foreach_index (i, sm->per_thread_data)
+  {
+    tsm = vec_elt_at_index (sm->per_thread_data, i);
+    vlib_cli_output (vm, "-------- thread %d %s --------\n",
+                    i, vlib_worker_threads[i].name);
+    if (sm->endpoint_dependent)
+      {
+       vlib_cli_output (vm, "%U", format_bihash_16_8, &tsm->in2out_ed,
+                        verbose);
+       vlib_cli_output (vm, "%U", format_bihash_16_8, &tsm->out2in_ed,
+                        verbose);
+      }
+    else
+      {
+       vlib_cli_output (vm, "%U", format_bihash_8_8, &tsm->in2out, verbose);
+       vlib_cli_output (vm, "%U", format_bihash_8_8, &tsm->out2in, verbose);
+      }
+    vlib_cli_output (vm, "%U", format_bihash_8_8, &tsm->user_hash, verbose);
+  }
+
+  return 0;
+}
+
 static clib_error_t *
 nat44_set_alloc_addr_and_port_alg_command_fn (vlib_main_t * vm,
                                              unformat_input_t * input,
                                              vlib_cli_command_t * cmd)
 {
   unformat_input_t _line_input, *line_input = &_line_input;
+  snat_main_t *sm = &snat_main;
   clib_error_t *error = 0;
   u32 psid, psid_offset, psid_length;
 
+  if (sm->deterministic)
+    return clib_error_return (0, UNSUPPORTED_IN_DET_MODE_STR);
+
   /* Get a line of input. */
   if (!unformat_user (input, unformat_line_input, line_input))
     return 0;
@@ -197,6 +257,9 @@ add_address_command_fn (vlib_main_t * vm,
   clib_error_t *error = 0;
   u8 twice_nat = 0;
 
+  if (sm->deterministic)
+    return clib_error_return (0, UNSUPPORTED_IN_DET_MODE_STR);
+
   /* Get a line of input. */
   if (!unformat_user (input, unformat_line_input, line_input))
     return 0;
@@ -241,7 +304,7 @@ add_address_command_fn (vlib_main_t * vm,
   count = (end_host_order - start_host_order) + 1;
 
   if (count > 1024)
-    clib_warning ("%U - %U, %d addresses...",
+    nat_log_info ("%U - %U, %d addresses...",
                  format_ip4_address, &start_addr,
                  format_ip4_address, &end_addr, count);
 
@@ -250,18 +313,26 @@ add_address_command_fn (vlib_main_t * vm,
   for (i = 0; i < count; i++)
     {
       if (is_add)
-       snat_add_address (sm, &this_addr, vrf_id, twice_nat);
+       rv = snat_add_address (sm, &this_addr, vrf_id, twice_nat);
       else
        rv = snat_del_address (sm, this_addr, 0, twice_nat);
 
       switch (rv)
        {
+       case VNET_API_ERROR_VALUE_EXIST:
+         error = clib_error_return (0, "NAT address already in use.");
+         goto done;
        case VNET_API_ERROR_NO_SUCH_ENTRY:
-         error = clib_error_return (0, "S-NAT address not exist.");
+         error = clib_error_return (0, "NAT address not exist.");
          goto done;
        case VNET_API_ERROR_UNSPECIFIED:
          error =
-           clib_error_return (0, "S-NAT address used in static mapping.");
+           clib_error_return (0, "NAT address used in static mapping.");
+         goto done;
+       case VNET_API_ERROR_FEATURE_DISABLED:
+         error =
+           clib_error_return (0,
+                              "twice NAT available only for endpoint-dependent mode.");
          goto done;
        default:
          break;
@@ -286,6 +357,9 @@ nat44_show_addresses_command_fn (vlib_main_t * vm, unformat_input_t * input,
   snat_main_t *sm = &snat_main;
   snat_address_t *ap;
 
+  if (sm->deterministic)
+    return clib_error_return (0, UNSUPPORTED_IN_DET_MODE_STR);
+
   vlib_cli_output (vm, "NAT44 pool addresses:");
   /* *INDENT-OFF* */
   vec_foreach (ap, sm->addresses)
@@ -468,6 +542,7 @@ add_static_mapping_command_fn (vlib_main_t * vm,
                               vlib_cli_command_t * cmd)
 {
   unformat_input_t _line_input, *line_input = &_line_input;
+  snat_main_t *sm = &snat_main;
   clib_error_t *error = 0;
   ip4_address_t l_addr, e_addr;
   u32 l_port = 0, e_port = 0, vrf_id = ~0;
@@ -478,9 +553,12 @@ add_static_mapping_command_fn (vlib_main_t * vm,
   int rv;
   snat_protocol_t proto = ~0;
   u8 proto_set = 0;
-  u8 twice_nat = 0;
+  twice_nat_type_t twice_nat = TWICE_NAT_DISABLED;
   u8 out2in_only = 0;
 
+  if (sm->deterministic)
+    return clib_error_return (0, UNSUPPORTED_IN_DET_MODE_STR);
+
   /* Get a line of input. */
   if (!unformat_user (input, unformat_line_input, line_input))
     return 0;
@@ -512,7 +590,9 @@ add_static_mapping_command_fn (vlib_main_t * vm,
       else if (unformat (line_input, "%U", unformat_snat_protocol, &proto))
        proto_set = 1;
       else if (unformat (line_input, "twice-nat"))
-       twice_nat = 1;
+       twice_nat = TWICE_NAT;
+      else if (unformat (line_input, "self-twice-nat"))
+       twice_nat = TWICE_NAT_SELF;
       else if (unformat (line_input, "out2in-only"))
        out2in_only = 1;
       else if (unformat (line_input, "del"))
@@ -558,6 +638,11 @@ add_static_mapping_command_fn (vlib_main_t * vm,
     case VNET_API_ERROR_VALUE_EXIST:
       error = clib_error_return (0, "Mapping already exist.");
       goto done;
+    case VNET_API_ERROR_FEATURE_DISABLED:
+      error =
+       clib_error_return (0,
+                          "twice-nat/out2in-only available only for endpoint-dependent mode.");
+      goto done;
     default:
       break;
     }
@@ -574,6 +659,7 @@ add_identity_mapping_command_fn (vlib_main_t * vm,
                                 vlib_cli_command_t * cmd)
 {
   unformat_input_t _line_input, *line_input = &_line_input;
+  snat_main_t *sm = &snat_main;
   clib_error_t *error = 0;
   ip4_address_t addr;
   u32 port = 0, vrf_id = ~0;
@@ -584,6 +670,9 @@ add_identity_mapping_command_fn (vlib_main_t * vm,
   int rv;
   snat_protocol_t proto;
 
+  if (sm->deterministic)
+    return clib_error_return (0, UNSUPPORTED_IN_DET_MODE_STR);
+
   addr.as_u32 = 0;
 
   /* Get a line of input. */
@@ -649,6 +738,7 @@ add_lb_static_mapping_command_fn (vlib_main_t * vm,
                                  vlib_cli_command_t * cmd)
 {
   unformat_input_t _line_input, *line_input = &_line_input;
+  snat_main_t *sm = &snat_main;
   clib_error_t *error = 0;
   ip4_address_t l_addr, e_addr;
   u32 l_port = 0, e_port = 0, vrf_id = 0, probability = 0;
@@ -657,9 +747,12 @@ add_lb_static_mapping_command_fn (vlib_main_t * vm,
   snat_protocol_t proto;
   u8 proto_set = 0;
   nat44_lb_addr_port_t *locals = 0, local;
-  u8 twice_nat = 0;
+  twice_nat_type_t twice_nat = TWICE_NAT_DISABLED;
   u8 out2in_only = 0;
 
+  if (sm->deterministic)
+    return clib_error_return (0, UNSUPPORTED_IN_DET_MODE_STR);
+
   /* Get a line of input. */
   if (!unformat_user (input, unformat_line_input, line_input))
     return 0;
@@ -675,16 +768,27 @@ add_lb_static_mapping_command_fn (vlib_main_t * vm,
          local.probability = (u8) probability;
          vec_add1 (locals, local);
        }
+      else if (unformat (line_input, "local %U:%u vrf %u probability %u",
+                        unformat_ip4_address, &l_addr, &l_port, &vrf_id,
+                        &probability))
+       {
+         memset (&local, 0, sizeof (local));
+         local.addr = l_addr;
+         local.port = (u16) l_port;
+         local.probability = (u8) probability;
+         local.vrf_id = vrf_id;
+         vec_add1 (locals, local);
+       }
       else if (unformat (line_input, "external %U:%u", unformat_ip4_address,
                         &e_addr, &e_port))
        ;
-      else if (unformat (line_input, "vrf %u", &vrf_id))
-       ;
       else if (unformat (line_input, "protocol %U", unformat_snat_protocol,
                         &proto))
        proto_set = 1;
       else if (unformat (line_input, "twice-nat"))
-       twice_nat = 1;
+       twice_nat = TWICE_NAT;
+      else if (unformat (line_input, "self-twice-nat"))
+       twice_nat = TWICE_NAT_SELF;
       else if (unformat (line_input, "out2in-only"))
        out2in_only = 1;
       else if (unformat (line_input, "del"))
@@ -709,9 +813,8 @@ add_lb_static_mapping_command_fn (vlib_main_t * vm,
       goto done;
     }
 
-  rv = nat44_add_del_lb_static_mapping (e_addr, (u16) e_port, proto, vrf_id,
-                                       locals, is_add, twice_nat,
-                                       out2in_only, 0);
+  rv = nat44_add_del_lb_static_mapping (e_addr, (u16) e_port, proto, locals,
+                                       is_add, twice_nat, out2in_only, 0);
 
   switch (rv)
     {
@@ -727,6 +830,10 @@ add_lb_static_mapping_command_fn (vlib_main_t * vm,
     case VNET_API_ERROR_VALUE_EXIST:
       error = clib_error_return (0, "Mapping already exist.");
       goto done;
+    case VNET_API_ERROR_FEATURE_DISABLED:
+      error =
+       clib_error_return (0, "Available only for endpoint-dependent mode.");
+      goto done;
     default:
       break;
     }
@@ -747,6 +854,9 @@ nat44_show_static_mappings_command_fn (vlib_main_t * vm,
   snat_static_mapping_t *m;
   snat_static_map_resolve_t *rp;
 
+  if (sm->deterministic)
+    return clib_error_return (0, UNSUPPORTED_IN_DET_MODE_STR);
+
   vlib_cli_output (vm, "NAT44 static mappings:");
   /* *INDENT-OFF* */
   pool_foreach (m, sm->static_mappings,
@@ -773,6 +883,9 @@ snat_add_interface_address_command_fn (vlib_main_t * vm,
   clib_error_t *error = 0;
   u8 twice_nat = 0;
 
+  if (sm->deterministic)
+    return clib_error_return (0, UNSUPPORTED_IN_DET_MODE_STR);
+
   /* Get a line of input. */
   if (!unformat_user (input, unformat_line_input, line_input))
     return 0;
@@ -822,6 +935,9 @@ nat44_show_interface_address_command_fn (vlib_main_t * vm,
   vnet_main_t *vnm = vnet_get_main ();
   u32 *sw_if_index;
 
+  if (sm->deterministic)
+    return clib_error_return (0, UNSUPPORTED_IN_DET_MODE_STR);
+
   /* *INDENT-OFF* */
   vlib_cli_output (vm, "NAT44 pool address interfaces:");
   vec_foreach (sw_if_index, sm->auto_add_sw_if_indices)
@@ -850,6 +966,9 @@ nat44_show_sessions_command_fn (vlib_main_t * vm, unformat_input_t * input,
   snat_user_t *u;
   int i = 0;
 
+  if (sm->deterministic)
+    return clib_error_return (0, UNSUPPORTED_IN_DET_MODE_STR);
+
   if (unformat (input, "detail"))
     verbose = 1;
 
@@ -860,6 +979,9 @@ nat44_show_sessions_command_fn (vlib_main_t * vm, unformat_input_t * input,
     {
       tsm = vec_elt_at_index (sm->per_thread_data, i);
 
+      vlib_cli_output (vm, "-------- thread %d %s: %d sessions --------\n",
+                       i, vlib_worker_threads[i].name,
+                       pool_elts (tsm->sessions));
       pool_foreach (u, tsm->users,
       ({
         vlib_cli_output (vm, "  %U", format_snat_user, tsm, u, verbose);
@@ -877,13 +999,16 @@ nat44_del_session_command_fn (vlib_main_t * vm,
 {
   snat_main_t *sm = &snat_main;
   unformat_input_t _line_input, *line_input = &_line_input;
-  int is_in = 0;
+  int is_in = 0, is_ed = 0;
   clib_error_t *error = 0;
-  ip4_address_t addr;
-  u32 port = 0, vrf_id = sm->outside_vrf_id;
+  ip4_address_t addr, eh_addr;
+  u32 port = 0, eh_port = 0, vrf_id = sm->outside_vrf_id;
   snat_protocol_t proto;
   int rv;
 
+  if (sm->deterministic)
+    return clib_error_return (0, UNSUPPORTED_IN_DET_MODE_STR);
+
   /* Get a line of input. */
   if (!unformat_user (input, unformat_line_input, line_input))
     return 0;
@@ -899,8 +1024,18 @@ nat44_del_session_command_fn (vlib_main_t * vm,
          is_in = 1;
          vrf_id = sm->inside_vrf_id;
        }
+      else if (unformat (line_input, "out"))
+       {
+         is_in = 0;
+         vrf_id = sm->outside_vrf_id;
+       }
       else if (unformat (line_input, "vrf %u", &vrf_id))
        ;
+      else
+       if (unformat
+           (line_input, "external-host %U:%u", unformat_ip4_address,
+            &eh_addr, &eh_port))
+       is_ed = 1;
       else
        {
          error = clib_error_return (0, "unknown input '%U'",
@@ -909,7 +1044,12 @@ nat44_del_session_command_fn (vlib_main_t * vm,
        }
     }
 
-  rv = nat44_del_session (sm, &addr, port, proto, vrf_id, is_in);
+  if (is_ed)
+    rv =
+      nat44_del_ed_session (sm, &addr, port, &eh_addr, eh_port,
+                           snat_proto_to_ip_proto (proto), vrf_id, is_in);
+  else
+    rv = nat44_del_session (sm, &addr, port, proto, vrf_id, is_in);
 
   switch (rv)
     {
@@ -938,6 +1078,9 @@ snat_forwarding_set_command_fn (vlib_main_t * vm,
   u8 forwarding_enable_set = 0;
   clib_error_t *error = 0;
 
+  if (sm->deterministic)
+    return clib_error_return (0, UNSUPPORTED_IN_DET_MODE_STR);
+
   /* Get a line of input. */
   if (!unformat_user (input, unformat_line_input, line_input))
     return clib_error_return (0, "'enable' or 'disable' expected");
@@ -987,6 +1130,9 @@ snat_det_map_command_fn (vlib_main_t * vm,
   int is_add = 1, rv;
   clib_error_t *error = 0;
 
+  if (!sm->deterministic)
+    return clib_error_return (0, SUPPORTED_ONLY_IN_DET_MODE_STR);
+
   /* Get a line of input. */
   if (!unformat_user (input, unformat_line_input, line_input))
     return 0;
@@ -1034,6 +1180,9 @@ nat44_det_show_mappings_command_fn (vlib_main_t * vm,
   snat_main_t *sm = &snat_main;
   snat_det_map_t *dm;
 
+  if (!sm->deterministic)
+    return clib_error_return (0, SUPPORTED_ONLY_IN_DET_MODE_STR);
+
   vlib_cli_output (vm, "NAT44 deterministic mappings:");
   /* *INDENT-OFF* */
   pool_foreach (dm, sm->det_maps,
@@ -1064,6 +1213,9 @@ snat_det_forward_command_fn (vlib_main_t * vm,
   snat_det_map_t *dm;
   clib_error_t *error = 0;
 
+  if (!sm->deterministic)
+    return clib_error_return (0, SUPPORTED_ONLY_IN_DET_MODE_STR);
+
   /* Get a line of input. */
   if (!unformat_user (input, unformat_line_input, line_input))
     return 0;
@@ -1108,6 +1260,9 @@ snat_det_reverse_command_fn (vlib_main_t * vm,
   snat_det_map_t *dm;
   clib_error_t *error = 0;
 
+  if (!sm->deterministic)
+    return clib_error_return (0, SUPPORTED_ONLY_IN_DET_MODE_STR);
+
   /* Get a line of input. */
   if (!unformat_user (input, unformat_line_input, line_input))
     return 0;
@@ -1161,21 +1316,54 @@ set_timeout_command_fn (vlib_main_t * vm,
   while (unformat_check_input (line_input) != UNFORMAT_END_OF_INPUT)
     {
       if (unformat (line_input, "udp %u", &sm->udp_timeout))
-       ;
+       {
+         if (nat64_set_udp_timeout (sm->udp_timeout))
+           {
+             error = clib_error_return (0, "Invalid UDP timeout value");
+             goto done;
+           }
+       }
       else if (unformat (line_input, "tcp-established %u",
                         &sm->tcp_established_timeout))
-       ;
+       {
+         if (nat64_set_tcp_timeouts
+             (sm->tcp_transitory_timeout, sm->tcp_established_timeout))
+           {
+             error =
+               clib_error_return (0,
+                                  "Invalid TCP established timeouts value");
+             goto done;
+           }
+       }
       else if (unformat (line_input, "tcp-transitory %u",
                         &sm->tcp_transitory_timeout))
-       ;
+       {
+         if (nat64_set_tcp_timeouts
+             (sm->tcp_transitory_timeout, sm->tcp_established_timeout))
+           {
+             error =
+               clib_error_return (0,
+                                  "Invalid TCP transitory timeouts value");
+             goto done;
+           }
+       }
       else if (unformat (line_input, "icmp %u", &sm->icmp_timeout))
-       ;
+       {
+         if (nat64_set_icmp_timeout (sm->icmp_timeout))
+           {
+             error = clib_error_return (0, "Invalid ICMP timeout value");
+             goto done;
+           }
+       }
       else if (unformat (line_input, "reset"))
        {
          sm->udp_timeout = SNAT_UDP_TIMEOUT;
          sm->tcp_established_timeout = SNAT_TCP_ESTABLISHED_TIMEOUT;
          sm->tcp_transitory_timeout = SNAT_TCP_TRANSITORY_TIMEOUT;
          sm->icmp_timeout = SNAT_ICMP_TIMEOUT;
+         nat64_set_udp_timeout (0);
+         nat64_set_icmp_timeout (0);
+         nat64_set_tcp_timeouts (0, 0);
        }
       else
        {
@@ -1192,9 +1380,9 @@ done:
 }
 
 static clib_error_t *
-nat44_det_show_timeouts_command_fn (vlib_main_t * vm,
-                                   unformat_input_t * input,
-                                   vlib_cli_command_t * cmd)
+nat_show_timeouts_command_fn (vlib_main_t * vm,
+                             unformat_input_t * input,
+                             vlib_cli_command_t * cmd)
 {
   snat_main_t *sm = &snat_main;
 
@@ -1218,6 +1406,9 @@ nat44_det_show_sessions_command_fn (vlib_main_t * vm,
   snat_det_session_t *ses;
   int i;
 
+  if (!sm->deterministic)
+    return clib_error_return (0, SUPPORTED_ONLY_IN_DET_MODE_STR);
+
   vlib_cli_output (vm, "NAT44 deterministic sessions:");
   /* *INDENT-OFF* */
   pool_foreach (dm, sm->det_maps,
@@ -1247,6 +1438,9 @@ snat_det_close_session_out_fn (vlib_main_t * vm,
   snat_det_out_key_t key;
   clib_error_t *error = 0;
 
+  if (!sm->deterministic)
+    return clib_error_return (0, SUPPORTED_ONLY_IN_DET_MODE_STR);
+
   /* Get a line of input. */
   if (!unformat_user (input, unformat_line_input, line_input))
     return 0;
@@ -1303,6 +1497,9 @@ snat_det_close_session_in_fn (vlib_main_t * vm,
   snat_det_out_key_t key;
   clib_error_t *error = 0;
 
+  if (!sm->deterministic)
+    return clib_error_return (0, SUPPORTED_ONLY_IN_DET_MODE_STR);
+
   /* Get a line of input. */
   if (!unformat_user (input, unformat_line_input, line_input))
     return 0;
@@ -1374,6 +1571,40 @@ VLIB_CLI_COMMAND (nat_show_workers_command, static) = {
   .function = nat_show_workers_commnad_fn,
 };
 
+/*?
+ * @cliexpar
+ * @cliexstart{set nat timeout}
+ * Set values of timeouts for NAT sessions (in seconds), use:
+ *  vpp# set nat timeout udp 120 tcp-established 7500 tcp-transitory 250 icmp 90
+ * To reset default values use:
+ *  vpp# set nat44 deterministic timeout reset
+ * @cliexend
+?*/
+VLIB_CLI_COMMAND (set_timeout_command, static) = {
+  .path = "set nat timeout",
+  .function = set_timeout_command_fn,
+  .short_help =
+    "set nat timeout [udp <sec> | tcp-established <sec> "
+    "tcp-transitory <sec> | icmp <sec> | reset]",
+};
+
+/*?
+ * @cliexpar
+ * @cliexstart{show nat timeouts}
+ * Show values of timeouts for NAT sessions.
+ * vpp# show nat timeouts
+ * udp timeout: 300sec
+ * tcp-established timeout: 7440sec
+ * tcp-transitory timeout: 240sec
+ * icmp timeout: 60sec
+ * @cliexend
+?*/
+VLIB_CLI_COMMAND (nat_show_timeouts_command, static) = {
+  .path = "show nat timeouts",
+  .short_help = "show nat timeouts",
+  .function = nat_show_timeouts_command_fn,
+};
+
 /*?
  * @cliexpar
  * @cliexstart{snat ipfix logging}
@@ -1405,6 +1636,18 @@ VLIB_CLI_COMMAND (nat44_set_alloc_addr_and_port_alg_command, static) = {
     .function = nat44_set_alloc_addr_and_port_alg_command_fn,
 };
 
+/*?
+ * @cliexpar
+ * @cliexstart{show nat44 hash tables}
+ * Show NAT44 hash tables
+ * @cliexend
+?*/
+VLIB_CLI_COMMAND (nat44_show_hash, static) = {
+  .path = "show nat44 hash tables",
+  .short_help = "show nat44 hash tables [detail|verbose]",
+  .function = nat44_show_hash_commnad_fn,
+};
+
 /*?
  * @cliexpar
  * @cliexstart{nat44 add address}
@@ -1505,7 +1748,8 @@ VLIB_CLI_COMMAND (add_static_mapping_command, static) = {
   .function = add_static_mapping_command_fn,
   .short_help =
     "nat44 add static mapping tcp|udp|icmp local <addr> [<port>] "
-    "external <addr> [<port>] [vrf <table-id>] [twice-nat] [out2in-only] [del]",
+    "external <addr> [<port>] [vrf <table-id>] [twice-nat|self-twice-nat] "
+    "[out2in-only] [del]",
 };
 
 /*?
@@ -1543,8 +1787,8 @@ VLIB_CLI_COMMAND (add_lb_static_mapping_command, static) = {
   .function = add_lb_static_mapping_command_fn,
   .short_help =
     "nat44 add load-balancing static mapping protocol tcp|udp "
-    "external <addr>:<port> local <addr>:<port> probability <n> [twice-nat] "
-    "[vrf <table-id>] [out2in-only] [del]",
+    "external <addr>:<port> local <addr>:<port> [vrf <table-id>] "
+    "probability <n> [twice-nat|self-twice-nat] [out2in-only] [del]",
 };
 
 /*?
@@ -1622,7 +1866,7 @@ VLIB_CLI_COMMAND (nat44_show_sessions_command, static) = {
 ?*/
 VLIB_CLI_COMMAND (nat44_del_session_command, static) = {
     .path = "nat44 del session",
-    .short_help = "nat44 del session in|out <addr>:<port> tcp|udp|icmp [vrf <id>]",
+    .short_help = "nat44 del session in|out <addr>:<port> tcp|udp|icmp [vrf <id>] [external-host <addr>:<port>]",
     .function = nat44_del_session_command_fn,
 };
 
@@ -1710,41 +1954,6 @@ VLIB_CLI_COMMAND (snat_det_reverse_command, static) = {
     .function = snat_det_reverse_command_fn,
 };
 
-/*?
- * @cliexpar
- * @cliexstart{set nat44 deterministic timeout}
- * Set values of timeouts for deterministic NAT (in seconds), use:
- *  vpp# set nat44 deterministic timeout udp 120 tcp-established 7500
- *  tcp-transitory 250 icmp 90
- * To reset default values use:
- *  vpp# set nat44 deterministic timeout reset
- * @cliexend
-?*/
-VLIB_CLI_COMMAND (set_timeout_command, static) = {
-  .path = "set nat44 deterministic timeout",
-  .function = set_timeout_command_fn,
-  .short_help =
-    "set nat44 deterministic timeout [udp <sec> | tcp-established <sec> "
-    "tcp-transitory <sec> | icmp <sec> | reset]",
-};
-
-/*?
- * @cliexpar
- * @cliexstart{show nat44 deterministic timeouts}
- * Show values of timeouts for deterministic NAT.
- * vpp# show nat44 deterministic timeouts
- * udp timeout: 300sec
- * tcp-established timeout: 7440sec
- * tcp-transitory timeout: 240sec
- * icmp timeout: 60sec
- * @cliexend
-?*/
-VLIB_CLI_COMMAND (nat44_det_show_timeouts_command, static) = {
-  .path = "show nat44 deterministic timeouts",
-  .short_help = "show nat44 deterministic timeouts",
-  .function = nat44_det_show_timeouts_command_fn,
-};
-
 /*?
  * @cliexpar
  * @cliexstart{show nat44 deterministic sessions}