X-Git-Url: https://gerrit.fd.io/r/gitweb?a=blobdiff_plain;f=src%2Fvnet%2Fmpls%2Fmpls_api.c;h=c47e94dd34af4aac602222e187af8c803394f124;hb=054c03ac9c20a5e38121590b83f01fd91f82acf0;hp=22fb7d43a31eff4e83abfa214dd940b9baa4ac20;hpb=57b5860f013953ce161d05302e05370db9cd6ee2;p=vpp.git diff --git a/src/vnet/mpls/mpls_api.c b/src/vnet/mpls/mpls_api.c index 22fb7d43a31..c47e94dd34a 100644 --- a/src/vnet/mpls/mpls_api.c +++ b/src/vnet/mpls/mpls_api.c @@ -50,6 +50,7 @@ #define foreach_vpe_api_msg \ _(MPLS_IP_BIND_UNBIND, mpls_ip_bind_unbind) \ _(MPLS_ROUTE_ADD_DEL, mpls_route_add_del) \ +_(MPLS_TABLE_ADD_DEL, mpls_table_add_del) \ _(MPLS_TUNNEL_ADD_DEL, mpls_tunnel_add_del) \ _(MPLS_TUNNEL_DUMP, mpls_tunnel_dump) \ _(MPLS_FIB_DUMP, mpls_fib_dump) @@ -57,6 +58,49 @@ _(MPLS_FIB_DUMP, mpls_fib_dump) extern void stats_dslock_with_hint (int hint, int tag); extern void stats_dsunlock (void); +void +mpls_table_delete (u32 table_id, u8 is_api) +{ + u32 fib_index; + + /* + * The MPLS defult table must also be explicitly created via the API. + * So in contrast to IP, it gets no special treatment here. + * + * The API holds only one lock on the table. + * i.e. it can be added many times via the API but needs to be + * deleted only once. + */ + fib_index = fib_table_find (FIB_PROTOCOL_MPLS, table_id); + + if (~0 != fib_index) + { + fib_table_unlock (fib_index, + FIB_PROTOCOL_MPLS, + (is_api ? FIB_SOURCE_API : FIB_SOURCE_CLI)); + } +} + +void +vl_api_mpls_table_add_del_t_handler (vl_api_mpls_table_add_del_t * mp) +{ + vl_api_mpls_table_add_del_reply_t *rmp; + vnet_main_t *vnm; + int rv = 0; + + vnm = vnet_get_main (); + vnm->api_errno = 0; + + if (mp->mt_is_add) + mpls_table_create (ntohl (mp->mt_table_id), 1, mp->mt_name); + else + mpls_table_delete (ntohl (mp->mt_table_id), 1); + + // NB: Nothing sets rv; none of the above returns an error + + REPLY_MACRO (VL_API_MPLS_TABLE_ADD_DEL_REPLY); +} + static int mpls_ip_bind_unbind_handler (vnet_main_t * vnm, vl_api_mpls_ip_bind_unbind_t * mp) @@ -68,14 +112,7 @@ mpls_ip_bind_unbind_handler (vnet_main_t * vnm, if (~0 == mpls_fib_index) { - if (mp->mb_create_table_if_needed) - { - mpls_fib_index = - fib_table_find_or_create_and_lock (FIB_PROTOCOL_MPLS, - ntohl (mp->mb_mpls_table_id)); - } - else - return VNET_API_ERROR_NO_SUCH_FIB; + return VNET_API_ERROR_NO_SUCH_FIB; } ip_fib_index = fib_table_find ((mp->mb_is_ip4 ? @@ -144,14 +181,7 @@ mpls_route_add_del_t_handler (vnet_main_t * vnm, }; if (pfx.fp_eos) { - if (mp->mr_next_hop_proto_is_ip4) - { - pfx.fp_payload_proto = DPO_PROTO_IP4; - } - else - { - pfx.fp_payload_proto = DPO_PROTO_IP6; - } + pfx.fp_payload_proto = mp->mr_next_hop_proto; } else { @@ -161,9 +191,8 @@ mpls_route_add_del_t_handler (vnet_main_t * vnm, rv = add_del_route_check (FIB_PROTOCOL_MPLS, mp->mr_table_id, mp->mr_next_hop_sw_if_index, - dpo_proto_to_fib (pfx.fp_payload_proto), + pfx.fp_payload_proto, mp->mr_next_hop_table_id, - mp->mr_create_table_if_needed, mp->mr_is_rpf_id, &fib_index, &next_hop_fib_index); @@ -173,9 +202,9 @@ mpls_route_add_del_t_handler (vnet_main_t * vnm, ip46_address_t nh; memset (&nh, 0, sizeof (nh)); - if (mp->mr_next_hop_proto_is_ip4) + if (DPO_PROTO_IP4 == mp->mr_next_hop_proto) memcpy (&nh.ip4, mp->mr_next_hop, sizeof (nh.ip4)); - else + else if (DPO_PROTO_IP6 == mp->mr_next_hop_proto) memcpy (&nh.ip6, mp->mr_next_hop, sizeof (nh.ip6)); n_labels = mp->mr_next_hop_n_out_labels; @@ -190,25 +219,30 @@ mpls_route_add_del_t_handler (vnet_main_t * vnm, label_stack[ii] = ntohl (mp->mr_next_hop_out_label_stack[ii]); } - return (add_del_route_t_handler (mp->mr_is_multipath, mp->mr_is_add, 0, // mp->is_drop, + /* *INDENT-OFF* */ + return (add_del_route_t_handler (mp->mr_is_multipath, mp->mr_is_add, + 0, // mp->is_drop, 0, // mp->is_unreach, 0, // mp->is_prohibit, 0, // mp->is_local, mp->mr_is_multicast, - mp->mr_is_classify, - mp->mr_classify_table_index, - mp->mr_is_resolve_host, - mp->mr_is_resolve_attached, - mp->mr_is_interface_rx, - mp->mr_is_rpf_id, + mp->mr_is_classify, + mp->mr_classify_table_index, + mp->mr_is_resolve_host, + mp->mr_is_resolve_attached, + mp->mr_is_interface_rx, + mp->mr_is_rpf_id, + 0, // l2_bridged + 0, // is source_lookup fib_index, &pfx, - mp->mr_next_hop_proto_is_ip4, + mp->mr_next_hop_proto, &nh, ntohl (mp->mr_next_hop_sw_if_index), next_hop_fib_index, mp->mr_next_hop_weight, mp->mr_next_hop_preference, ntohl (mp->mr_next_hop_via_label), label_stack)); + /* *INDENT-ON* */ } void @@ -228,6 +262,33 @@ vl_api_mpls_route_add_del_t_handler (vl_api_mpls_route_add_del_t * mp) REPLY_MACRO (VL_API_MPLS_ROUTE_ADD_DEL_REPLY); } +void +mpls_table_create (u32 table_id, u8 is_api, const u8 * name) +{ + u32 fib_index; + + /* + * The MPLS defult table must also be explicitly created via the API. + * So in contrast to IP, it gets no special treatment here. + */ + + /* + * The API holds only one lock on the table. + * i.e. it can be added many times via the API but needs to be + * deleted only once. + */ + fib_index = fib_table_find (FIB_PROTOCOL_MPLS, table_id); + + if (~0 == fib_index) + { + fib_table_find_or_create_and_lock_w_name (FIB_PROTOCOL_MPLS, + table_id, + (is_api ? + FIB_SOURCE_API : + FIB_SOURCE_CLI), name); + } +} + static void vl_api_mpls_tunnel_add_del_t_handler (vl_api_mpls_tunnel_add_del_t * mp) { @@ -243,13 +304,13 @@ vl_api_mpls_tunnel_add_del_t_handler (vl_api_mpls_tunnel_add_del_t * mp) if (mp->mt_next_hop_proto_is_ip4) { - rpath.frp_proto = FIB_PROTOCOL_IP4; + rpath.frp_proto = DPO_PROTO_IP4; clib_memcpy (&rpath.frp_addr.ip4, mp->mt_next_hop, sizeof (rpath.frp_addr.ip4)); } else { - rpath.frp_proto = FIB_PROTOCOL_IP6; + rpath.frp_proto = DPO_PROTO_IP6; clib_memcpy (&rpath.frp_addr.ip6, mp->mt_next_hop, sizeof (rpath.frp_addr.ip6)); } @@ -334,7 +395,8 @@ send_mpls_tunnel_entry (u32 mti, void *arg) { memset (fp, 0, sizeof (*fp)); - fp->weight = htonl (api_rpath->rpath.frp_weight); + fp->weight = api_rpath->rpath.frp_weight; + fp->preference = api_rpath->rpath.frp_preference; fp->sw_if_index = htonl (api_rpath->rpath.frp_sw_if_index); copy_fib_next_hop (api_rpath, fp); fp++; @@ -368,7 +430,8 @@ vl_api_mpls_tunnel_dump_t_handler (vl_api_mpls_tunnel_dump_t * mp) static void send_mpls_fib_details (vpe_api_main_t * am, unix_shared_memory_queue_t * q, - u32 table_id, u32 label, u32 eos, + const fib_table_t * table, + u32 label, u32 eos, fib_route_path_encode_t * api_rpaths, u32 context) { vl_api_mpls_fib_details_t *mp; @@ -384,7 +447,9 @@ send_mpls_fib_details (vpe_api_main_t * am, mp->_vl_msg_id = ntohs (VL_API_MPLS_FIB_DETAILS); mp->context = context; - mp->table_id = htonl (table_id); + mp->table_id = htonl (table->ft_table_id); + memcpy (mp->table_name, table->ft_desc, + clib_min (vec_len (table->ft_desc), sizeof (mp->table_name))); mp->eos_bit = eos; mp->label = htonl (label); @@ -393,7 +458,8 @@ send_mpls_fib_details (vpe_api_main_t * am, vec_foreach (api_rpath, api_rpaths) { memset (fp, 0, sizeof (*fp)); - fp->weight = htonl (api_rpath->rpath.frp_weight); + fp->weight = api_rpath->rpath.frp_weight; + fp->preference = api_rpath->rpath.frp_preference; fp->sw_if_index = htonl (api_rpath->rpath.frp_sw_if_index); copy_fib_next_hop (api_rpath, fp); fp++; @@ -455,8 +521,8 @@ vl_api_mpls_fib_dump_t_handler (vl_api_mpls_fib_dump_t * mp) api_rpaths = NULL; fib_entry_encode (*lfeip, &api_rpaths); send_mpls_fib_details (am, q, - fib_table->ft_table_id, - pfx.fp_label, pfx.fp_eos, api_rpaths, mp->context); + fib_table, pfx.fp_label, + pfx.fp_eos, api_rpaths, mp->context); vec_free (api_rpaths); }