- s = format (0, "SCRIPT: nat44_add_del_interface_addr ");
- s = format (s, "sw_if_index %d %s",
- clib_host_to_net_u32 (mp->sw_if_index),
- mp->is_add ? "" : "del");
-
- FINISH;
-}
-
-static void
-send_nat44_interface_addr_details (u32 sw_if_index,
- unix_shared_memory_queue_t * q,
- u32 context)
-{
- vl_api_nat44_interface_addr_details_t *rmp;
- snat_main_t *sm = &snat_main;
-
- rmp = vl_msg_api_alloc (sizeof (*rmp));
- memset (rmp, 0, sizeof (*rmp));
- rmp->_vl_msg_id =
- ntohs (VL_API_NAT44_INTERFACE_ADDR_DETAILS + sm->msg_id_base);
- rmp->sw_if_index = ntohl (sw_if_index);
- rmp->context = context;
-
- vl_msg_api_send_shmem (q, (u8 *) & rmp);
-}
-
-static void
-vl_api_nat44_interface_addr_dump_t_handler (vl_api_nat44_interface_addr_dump_t
- * mp)
-{
- unix_shared_memory_queue_t *q;
- snat_main_t *sm = &snat_main;
- u32 *i;
-
- q = vl_api_client_index_to_input_queue (mp->client_index);
- if (q == 0)
- return;
-
- /* *INDENT-OFF* */
- vec_foreach (i, sm->auto_add_sw_if_indices)
- send_nat44_interface_addr_details(*i, q, mp->context);
- /* *INDENT-ON* */
-}
-
-static void *
-vl_api_nat44_interface_addr_dump_t_print (vl_api_nat44_interface_addr_dump_t *
- mp, void *handle)
-{
- u8 *s;
-
- s = format (0, "SCRIPT: nat44_interface_addr_dump ");
-
- FINISH;
-}
-
-static void
-send_nat44_user_details (snat_user_t * u, unix_shared_memory_queue_t * q,
- u32 context)
-{
- vl_api_nat44_user_details_t *rmp;
- snat_main_t *sm = &snat_main;
- fib_table_t *fib = fib_table_get (u->fib_index, FIB_PROTOCOL_IP4);
-
- rmp = vl_msg_api_alloc (sizeof (*rmp));
- memset (rmp, 0, sizeof (*rmp));
- rmp->_vl_msg_id = ntohs (VL_API_NAT44_USER_DETAILS + sm->msg_id_base);
-
- rmp->vrf_id = ntohl (fib->ft_table_id);
-
- clib_memcpy (rmp->ip_address, &(u->addr), 4);
- rmp->nsessions = ntohl (u->nsessions);
- rmp->nstaticsessions = ntohl (u->nstaticsessions);
- rmp->context = context;
-
- vl_msg_api_send_shmem (q, (u8 *) & rmp);
-}
-
-static void
-vl_api_nat44_user_dump_t_handler (vl_api_nat44_user_dump_t * mp)
-{
- unix_shared_memory_queue_t *q;
- snat_main_t *sm = &snat_main;
- snat_main_per_thread_data_t *tsm;
- snat_user_t *u;
-
- q = vl_api_client_index_to_input_queue (mp->client_index);
- if (q == 0)
- return;
-
- /* *INDENT-OFF* */
- vec_foreach (tsm, sm->per_thread_data)
- vec_foreach (u, tsm->users)
- send_nat44_user_details (u, q, mp->context);
- /* *INDENT-ON* */
-}
-
-static void *
-vl_api_nat44_user_dump_t_print (vl_api_nat44_user_dump_t * mp, void *handle)
-{
- u8 *s;
-
- s = format (0, "SCRIPT: nat44_user_dump ");
-
- FINISH;
-}
-
-static void
-send_nat44_user_session_details (snat_session_t * s,
- unix_shared_memory_queue_t * q, u32 context)
-{
- vl_api_nat44_user_session_details_t *rmp;
- snat_main_t *sm = &snat_main;
-
- rmp = vl_msg_api_alloc (sizeof (*rmp));
- memset (rmp, 0, sizeof (*rmp));
- rmp->_vl_msg_id =
- ntohs (VL_API_NAT44_USER_SESSION_DETAILS + sm->msg_id_base);
- clib_memcpy (rmp->outside_ip_address, (&s->out2in.addr), 4);
- clib_memcpy (rmp->inside_ip_address, (&s->in2out.addr), 4);
- rmp->is_static = s->flags & SNAT_SESSION_FLAG_STATIC_MAPPING ? 1 : 0;
- rmp->last_heard = clib_host_to_net_u64 ((u64) s->last_heard);
- rmp->total_bytes = clib_host_to_net_u64 (s->total_bytes);
- rmp->total_pkts = ntohl (s->total_pkts);
- rmp->context = context;
- if (snat_is_unk_proto_session (s))
- {
- rmp->outside_port = 0;
- rmp->inside_port = 0;
- rmp->protocol = ntohs (s->in2out.port);
- }
- else
- {
- rmp->outside_port = s->out2in.port;
- rmp->inside_port = s->in2out.port;
- rmp->protocol = ntohs (snat_proto_to_ip_proto (s->in2out.protocol));
- }
-
- vl_msg_api_send_shmem (q, (u8 *) & rmp);
-}
-
-static void
-vl_api_nat44_user_session_dump_t_handler (vl_api_nat44_user_session_dump_t *
- mp)
-{
- unix_shared_memory_queue_t *q;
- snat_main_t *sm = &snat_main;
- snat_main_per_thread_data_t *tsm;
- snat_session_t *s;
- clib_bihash_kv_8_8_t key, value;
- snat_user_key_t ukey;
- snat_user_t *u;
- u32 session_index, head_index, elt_index;
- dlist_elt_t *head, *elt;
-
- q = vl_api_client_index_to_input_queue (mp->client_index);
- if (q == 0)
- return;
-
- clib_memcpy (&ukey.addr, mp->ip_address, 4);
- ukey.fib_index = fib_table_find (FIB_PROTOCOL_IP4, ntohl (mp->vrf_id));
- key.key = ukey.as_u64;
- if (!clib_bihash_search_8_8 (&sm->worker_by_in, &key, &value))
- tsm = vec_elt_at_index (sm->per_thread_data, value.value);
- else
- tsm = vec_elt_at_index (sm->per_thread_data, sm->num_workers);
- if (clib_bihash_search_8_8 (&tsm->user_hash, &key, &value))
- return;
- u = pool_elt_at_index (tsm->users, value.value);
- if (!u->nsessions && !u->nstaticsessions)
- return;
-
- head_index = u->sessions_per_user_list_head_index;
- head = pool_elt_at_index (tsm->list_pool, head_index);
- elt_index = head->next;
- elt = pool_elt_at_index (tsm->list_pool, elt_index);
- session_index = elt->value;
- while (session_index != ~0)
- {
- s = pool_elt_at_index (tsm->sessions, session_index);
-
- send_nat44_user_session_details (s, q, mp->context);
-
- elt_index = elt->next;
- elt = pool_elt_at_index (tsm->list_pool, elt_index);
- session_index = elt->value;
- }
-}
-
-static void *
-vl_api_nat44_user_session_dump_t_print (vl_api_nat44_user_session_dump_t * mp,
- void *handle)
-{
- u8 *s;
-
- s = format (0, "SCRIPT: nat44_user_session_dump ");
- s = format (s, "ip_address %U vrf_id %d\n",
- format_ip4_address, mp->ip_address,
- clib_net_to_host_u32 (mp->vrf_id));
-
- FINISH;
-}
-
-static nat44_lb_addr_port_t *
-unformat_nat44_lb_addr_port (vl_api_nat44_lb_addr_port_t * addr_port_pairs,
- u8 addr_port_pair_num)
-{
- u8 i;
- nat44_lb_addr_port_t *lb_addr_port_pairs = 0, lb_addr_port;
- vl_api_nat44_lb_addr_port_t *ap;
-
- for (i = 0; i < addr_port_pair_num; i++)
- {
- ap = &addr_port_pairs[i];
- memset (&lb_addr_port, 0, sizeof (lb_addr_port));
- clib_memcpy (&lb_addr_port.addr, ap->addr, 4);
- lb_addr_port.port = clib_net_to_host_u16 (ap->port);
- lb_addr_port.probability = ap->probability;
- vec_add1 (lb_addr_port_pairs, lb_addr_port);
- }
-
- return lb_addr_port_pairs;
-}
-
-static void
- vl_api_nat44_add_del_lb_static_mapping_t_handler
- (vl_api_nat44_add_del_lb_static_mapping_t * mp)
-{
- snat_main_t *sm = &snat_main;
- vl_api_nat44_add_del_lb_static_mapping_reply_t *rmp;
- int rv = 0;
- nat44_lb_addr_port_t *locals = 0;
- ip4_address_t e_addr;
- snat_protocol_t proto;
-
- locals = unformat_nat44_lb_addr_port (mp->locals, mp->local_num);
- clib_memcpy (&e_addr, mp->external_addr, 4);
- proto = ip_proto_to_snat_proto (mp->protocol);
-
- rv =
- nat44_add_del_lb_static_mapping (e_addr,
- clib_net_to_host_u16 (mp->external_port),
- proto, clib_net_to_host_u32 (mp->vrf_id),
- locals, mp->is_add);
-
- vec_free (locals);
-
- REPLY_MACRO (VL_API_NAT44_ADD_DEL_LB_STATIC_MAPPING_REPLY);
-}
-
-static void *vl_api_nat44_add_del_lb_static_mapping_t_print
- (vl_api_nat44_add_del_lb_static_mapping_t * mp, void *handle)
-{
- u8 *s;
-
- s = format (0, "SCRIPT: nat44_add_del_lb_static_mapping ");
- s = format (s, "is_add %d\n", mp->is_add);
-
- FINISH;
-}
-
-static void
-send_nat44_lb_static_mapping_details (snat_static_mapping_t * m,
- unix_shared_memory_queue_t * q,
- u32 context)
-{
- vl_api_nat44_lb_static_mapping_details_t *rmp;
- snat_main_t *sm = &snat_main;
- nat44_lb_addr_port_t *ap;
- vl_api_nat44_lb_addr_port_t *locals;
-
- rmp =
- vl_msg_api_alloc (sizeof (*rmp) +
- (vec_len (m->locals) * sizeof (nat44_lb_addr_port_t)));
- memset (rmp, 0, sizeof (*rmp));
- rmp->_vl_msg_id =
- ntohs (VL_API_NAT44_LB_STATIC_MAPPING_DETAILS + sm->msg_id_base);
-
- clib_memcpy (rmp->external_addr, &(m->external_addr), 4);
- rmp->external_port = ntohs (m->external_port);
- rmp->protocol = snat_proto_to_ip_proto (m->proto);
- rmp->vrf_id = ntohl (m->vrf_id);
- rmp->context = context;
-
- locals = (vl_api_nat44_lb_addr_port_t *) rmp->locals;
- vec_foreach (ap, m->locals)
- {
- clib_memcpy (locals->addr, &(ap->addr), 4);
- locals->port = htons (ap->port);
- locals->probability = ap->probability;
- locals++;
- rmp->local_num++;
- }
-
- vl_msg_api_send_shmem (q, (u8 *) & rmp);
-}
-
-static void
- vl_api_nat44_lb_static_mapping_dump_t_handler
- (vl_api_nat44_lb_static_mapping_dump_t * mp)
-{
- unix_shared_memory_queue_t *q;
- snat_main_t *sm = &snat_main;
- snat_static_mapping_t *m;
-
- q = vl_api_client_index_to_input_queue (mp->client_index);
- if (q == 0)
- return;
-
- /* *INDENT-OFF* */
- pool_foreach (m, sm->static_mappings,
- ({
- if (vec_len(m->locals))
- send_nat44_lb_static_mapping_details (m, q, mp->context);
- }));
- /* *INDENT-ON* */
-}
-
-static void *vl_api_nat44_lb_static_mapping_dump_t_print
- (vl_api_nat44_lb_static_mapping_dump_t * mp, void *handle)
-{
- u8 *s;
-
- s = format (0, "SCRIPT: nat44_lb_static_mapping_dump ");
-
- FINISH;
-}
-
-/*******************************/
-/*** Deterministic NAT (CGN) ***/
-/*******************************/
-
-static void
-vl_api_nat_det_add_del_map_t_handler (vl_api_nat_det_add_del_map_t * mp)
-{
- snat_main_t *sm = &snat_main;
- vl_api_nat_det_add_del_map_reply_t *rmp;
- int rv = 0;
- ip4_address_t in_addr, out_addr;
-
- if (!mp->is_nat44)
- {
- rv = VNET_API_ERROR_UNIMPLEMENTED;
- goto send_reply;
- }
-
- clib_memcpy (&in_addr, mp->in_addr, 4);
- clib_memcpy (&out_addr, mp->out_addr, 4);
- rv = snat_det_add_map (sm, &in_addr, mp->in_plen, &out_addr,
- mp->out_plen, mp->is_add);
-
-send_reply:
- REPLY_MACRO (VL_API_NAT_DET_ADD_DEL_MAP_REPLY);
-}
-
-static void *
-vl_api_nat_det_add_del_map_t_print (vl_api_nat_det_add_del_map_t * mp,
- void *handle)
-{
- u8 *s;
-
- s = format (0, "SCRIPT: nat_det_add_del_map ");
- s = format (s, "inside address %U/%d outside address %U/%d\n",
- format_ip4_address, mp->in_addr, mp->in_plen,
- format_ip4_address, mp->out_addr, mp->out_plen);
-
- FINISH;
-}
-
-static void
-vl_api_nat_det_forward_t_handler (vl_api_nat_det_forward_t * mp)
-{
- snat_main_t *sm = &snat_main;
- vl_api_nat_det_forward_reply_t *rmp;
- int rv = 0;
- u16 lo_port = 0, hi_port = 0;
- snat_det_map_t *dm;
- ip4_address_t in_addr, out_addr;
-
- if (!mp->is_nat44)
- {
- out_addr.as_u32 = 0;
- rv = VNET_API_ERROR_UNIMPLEMENTED;
- goto send_reply;
- }
-
- out_addr.as_u32 = 0;
- clib_memcpy (&in_addr, mp->in_addr, 4);
- dm = snat_det_map_by_user (sm, &in_addr);
- if (!dm)
- {
- rv = VNET_API_ERROR_NO_SUCH_ENTRY;
- goto send_reply;
- }
-
- snat_det_forward (dm, &in_addr, &out_addr, &lo_port);
- hi_port = lo_port + dm->ports_per_host - 1;
-
-send_reply:
- /* *INDENT-OFF* */
- REPLY_MACRO2 (VL_API_NAT_DET_FORWARD_REPLY,
- ({
- rmp->out_port_lo = ntohs (lo_port);
- rmp->out_port_hi = ntohs (hi_port);
- clib_memcpy (rmp->out_addr, &out_addr, 4);
- }))
- /* *INDENT-ON* */
-}
-
-static void *
-vl_api_nat_det_forward_t_print (vl_api_nat_det_forward_t * mp, void *handle)
-{
- u8 *s;
-
- s = format (0, "SCRIPT: nat_det_forward");
- s = format (s, "inside ip address %U\n", format_ip4_address, mp->in_addr);
-
- FINISH;
-}
-
-static void
-vl_api_nat_det_reverse_t_handler (vl_api_nat_det_reverse_t * mp)
-{
- snat_main_t *sm = &snat_main;
- vl_api_nat_det_reverse_reply_t *rmp;
- int rv = 0;
- ip4_address_t out_addr, in_addr;
- snat_det_map_t *dm;
-
- in_addr.as_u32 = 0;
- clib_memcpy (&out_addr, mp->out_addr, 4);
- dm = snat_det_map_by_out (sm, &out_addr);
- if (!dm)