LCOV - code coverage report
Current view: top level - root/contrail/vrouter/utils - vr_util.c (source / functions) Hit Total Coverage
Test: OpenSDN C/C++ coverage (all TARGET_SET jobs) Lines: 449 1547 29.0 %
Date: 2026-08-03 02:19:58 Functions: 28 99 28.3 %
Legend: Lines: hit not hit

          Line data    Source code
       1             : /*
       2             :  * vr_util.c -- common functions used by utilities in a library form
       3             :  *
       4             :  * Copyright (c) 2015, Juniper Networks, Inc.
       5             :  * All rights reserved
       6             :  */
       7             : #include <ctype.h>
       8             : #include <stdio.h>
       9             : #include <stdlib.h>
      10             : #include <unistd.h>
      11             : #include <errno.h>
      12             : #include <stdbool.h>
      13             : #include <stdint.h>
      14             : #include <ctype.h>
      15             : #include <inttypes.h>
      16             : #include <fcntl.h>
      17             : #include <time.h>
      18             : 
      19             : #include <sys/types.h>
      20             : #include <sys/stat.h>
      21             : #include <sys/socket.h>
      22             : #include <sys/mman.h>
      23             : #if defined(__linux__)
      24             : #include <linux/netlink.h>
      25             : #include <linux/rtnetlink.h>
      26             : #include <linux/if_ether.h>
      27             : #include <linux/dcbnl.h>
      28             : #endif
      29             : 
      30             : #include <net/if.h>
      31             : #include <netinet/in.h>
      32             : 
      33             : #include "vr_types.h"
      34             : #include "nl_util.h"
      35             : #include "vr_message.h"
      36             : #include "vr_genetlink.h"
      37             : #include "vr_interface.h"
      38             : #include "vr_packet.h"
      39             : #include "vr_nexthop.h"
      40             : #include "vr_route.h"
      41             : #include "vr_bridge.h"
      42             : #include "vr_mem.h"
      43             : #include "ini_parser.h"
      44             : 
      45             : /* Suppress NetLink error messages */
      46             : bool vr_ignore_nl_errors = false;
      47             : int genetlink_group_id = 0;
      48             : static bool vr_header_include = 0;
      49             : 
      50             : char *
      51           0 : vr_extract_token(char *string, char token_separator)
      52             : {
      53             :     int ret;
      54             :     unsigned int length;
      55             : 
      56             :     char *sep;
      57             : 
      58             :     /* skip over leading white spaces */
      59           0 :     while ((*string == ' ') && string++);
      60             : 
      61             :     /* if there is nothing left after the spaces, return */
      62           0 :     if (!(length = strlen(string))) {
      63           0 :         return NULL;
      64             :     }
      65             : 
      66             :     /* If first character is a separator its a malforned request */
      67           0 :     if (*string == token_separator) {
      68           0 :         printf("Malformed request: separator used incorrectly \n");
      69           0 :         return NULL;
      70             :     }
      71             : 
      72             :     /* start searching for the token */
      73           0 :     sep = strchr(string, token_separator);
      74           0 :     if (sep) {
      75           0 :         length = sep - string;
      76             :         /* terminate the token with NULL */
      77           0 :         string[sep - string] = '\0';
      78           0 :         length = strlen(string);
      79             :     }
      80             : 
      81             :     /* remove trailing spaces */
      82           0 :     length -= 1;
      83           0 :     while ((*(string + length) == ' ') && --length);
      84           0 :     *(string + length + 1) = '\0';
      85             : 
      86             :     /*
      87             :      * reset the separator to space, since a space at the beginning
      88             :      * will be snipped
      89             :      */
      90           0 :     if (sep && (((sep - string)) != strlen(string)))
      91           0 :         string[sep - string] = ' ';
      92             : 
      93           0 :     return string;
      94             : }
      95             : 
      96             : bool
      97           0 : vr_valid_ipv6_address(const char *addr)
      98             : {
      99           0 :     unsigned int i = 0, j = 0, sep_count = 0;
     100             : 
     101             :     /* a '*' is treated as a valid address */
     102           0 :     if (!strncmp(addr, "*", 1) && (strlen(addr) == 1))
     103           0 :         return true;
     104             : 
     105           0 :     while (*(addr + i)) {
     106           0 :         if (isalnum(*(addr + i))) {
     107           0 :             j++;
     108           0 :         } else if (*(addr + i) == ':') {
     109           0 :             j = 0;
     110           0 :             sep_count++;
     111             :         } else {
     112           0 :             printf("match: \"%s\" is not a valid ipv6 address format\n", addr);
     113           0 :             return false;
     114             :         }
     115             : 
     116           0 :         if ((j > 4) || (sep_count > 7)) {
     117           0 :             printf("match: \"%s\" is not a valid ipv6 address format\n", addr);
     118           0 :             return false;
     119             :         }
     120             : 
     121           0 :         i++;
     122             :     }
     123             : 
     124           0 :     return true;
     125             : }
     126             : 
     127             : bool
     128           0 : vr_valid_ipv4_address(const char *addr)
     129             : {
     130           0 :     unsigned int i = 0, j = 0, sep_count = 0;
     131             : 
     132             :     /* a '*' is treated as a valid address */
     133           0 :     if (!strncmp(addr, "*", 1) && (strlen(addr) == 1))
     134           0 :         return true;
     135             : 
     136             :     /* every character should be either a digit or a '.' */
     137           0 :     while (*(addr + i)) {
     138           0 :         if (isdigit(*(addr + i))) {
     139           0 :             j++;
     140           0 :         } else if (i && (*(addr + i) == '.')) {
     141           0 :             j = 0;
     142           0 :             ++sep_count;
     143             :         } else {
     144           0 :             printf("match: \"%s\" is not a valid ipv4 address format\n", addr);
     145           0 :             return false;
     146             :         }
     147             : 
     148           0 :         if ((j > 3) || (sep_count > 3)) {
     149           0 :             printf("match: \"%s\" is not a valid ipv4 address format\n", addr);
     150           0 :             return false;
     151             :         }
     152             : 
     153           0 :         i++;
     154             :     }
     155             : 
     156           0 :     if (sep_count != 3) {
     157           0 :         printf("match: \"%s\" is not a valid ipv4 address format\n", addr);
     158           0 :         return false;
     159             :     }
     160             : 
     161           0 :     return true;
     162             : }
     163             : 
     164             : bool
     165          10 : vr_valid_mac_address(const char *mac)
     166             : {
     167          10 :     uint8_t null_mac[VR_ETHER_ALEN] = { 0 };
     168             : 
     169          10 :     if (!mac || !memcmp(mac, null_mac, VR_ETHER_ALEN))
     170          10 :         return false;
     171             : 
     172           0 :     return true;
     173             : }
     174             : 
     175             : char *
     176           5 : vr_proto_string(unsigned short proto)
     177             : {
     178           5 :     switch (proto) {
     179           2 :     case VR_IP_PROTO_TCP:
     180           2 :         return "TCP";
     181             :         break;
     182             : 
     183           0 :     case VR_IP_PROTO_UDP:
     184           0 :         return "UDP";
     185             :         break;
     186             : 
     187           3 :     case VR_IP_PROTO_ICMP:
     188           3 :         return "ICMP";
     189             :         break;
     190             : 
     191           0 :     case VR_IP_PROTO_SCTP:
     192           0 :         return "SCTP";
     193             :         break;
     194             : 
     195           0 :     case VR_IP_PROTO_ICMP6:
     196           0 :         return "ICMPv6";
     197             :         break;
     198             : 
     199             : 
     200           0 :     default:
     201           0 :         return "UNKNOWN";
     202             :     }
     203             : 
     204             :     return "UNKNOWN";
     205             : }
     206             : 
     207             : /* send and receive */
     208             : int
     209        2862 : vr_recvmsg_generic(struct nl_client *cl, bool dump, bool msg_wait)
     210             : {
     211        2862 :     int ret = 0;
     212        2862 :     bool pending = true;
     213             :     struct nl_response *resp;
     214             :     struct nlmsghdr *nlh;
     215             : 
     216        2863 :     while (pending) {
     217        2863 :         if (msg_wait) {
     218           0 :             ret = nl_recvmsg_waitall(cl);
     219             :         } else {
     220        2863 :             ret = nl_recvmsg(cl);
     221             :         }
     222        2863 :         if (ret > 0) {
     223        2863 :             if (dump) {
     224           2 :                 pending = true;
     225             :             } else {
     226        2861 :                 pending = false;
     227             :             }
     228             : 
     229        2863 :             resp = nl_parse_reply(cl);
     230        2863 :             if (resp->nl_op == SANDESH_REQUEST) {
     231        2863 :                 sandesh_decode(resp->nl_data, resp->nl_len,
     232             :                         vr_find_sandesh_info, &ret);
     233           0 :             } else if (resp->nl_type == NL_MSG_TYPE_DONE) {
     234           0 :                 pending = false;
     235             :             }
     236             :         } else {
     237           0 :             return ret;
     238             :         }
     239             : 
     240        2863 :         nlh = (struct nlmsghdr *)cl->cl_buf;
     241        2863 :         if (!nlh || !nlh->nlmsg_flags)
     242             :             break;
     243             :     }
     244             : 
     245        2862 :     return ret;
     246             : }
     247             : 
     248             : int
     249        2862 : vr_recvmsg(struct nl_client *cl, bool dump)
     250             : {
     251        2862 :     return vr_recvmsg_generic(cl, dump, false);
     252             : }
     253             : 
     254             : int
     255           0 : vr_recvmsg_waitall(struct nl_client *cl, bool dump)
     256             : {
     257           0 :     return vr_recvmsg_generic(cl, dump, true);
     258             : }
     259             : 
     260             : int
     261        2862 : vr_sendmsg(struct nl_client *cl, void *request,
     262             :         char *request_string)
     263             : {
     264             :     int ret, error, attr_len;
     265             : 
     266             :     /* nlmsg header */
     267        2862 :     ret = nl_build_nlh(cl, cl->cl_genl_family_id, NLM_F_REQUEST);
     268        2862 :     if (ret)
     269           0 :         return ret;
     270             : 
     271             :     /* Generic nlmsg header */
     272        2862 :     ret = nl_build_genlh(cl, SANDESH_REQUEST, 0);
     273        2862 :     if (ret)
     274           0 :         return ret;
     275             : 
     276        2862 :     attr_len = nl_get_attr_hdr_size();
     277        5724 :     ret = sandesh_encode(request, request_string, vr_find_sandesh_info,
     278        2862 :                              (nl_get_buf_ptr(cl) + attr_len),
     279        2862 :                              (nl_get_buf_len(cl) - attr_len), &error);
     280        2862 :     if (ret <= 0)
     281           0 :         return ret;
     282             : 
     283             :     /* Add sandesh attribute */
     284        2862 :     nl_build_attr(cl, ret, NL_ATTR_VR_MESSAGE_PROTOCOL);
     285        2862 :     nl_update_nlh(cl);
     286             : 
     287        2862 :     return nl_sendmsg(cl);
     288             : }
     289             : 
     290             : struct nl_client *
     291        2951 : vr_get_nl_client(int proto)
     292             : {
     293             :     int ret;
     294        2951 :     int sock_proto = proto;
     295             :     struct nl_client *cl;
     296             : 
     297        2951 :     cl = nl_register_client();
     298        2951 :     if (!cl)
     299           0 :         return NULL;
     300             : 
     301        2951 :     parse_ini_file();
     302             : 
     303        2951 :     if (proto == VR_NETLINK_PROTO_DEFAULT)
     304        2951 :         sock_proto = get_protocol();
     305             : 
     306        2951 :     ret = nl_socket(cl, get_domain(), get_type(), sock_proto);
     307        2951 :     if (ret <= 0)
     308           0 :         goto fail;
     309             : 
     310        2951 :     ret = nl_connect(cl, get_ip(), get_port(), genetlink_group_id);
     311        2951 :     if (ret < 0)
     312           0 :         goto fail;
     313             : 
     314        5902 :     if ((proto == VR_NETLINK_PROTO_DEFAULT) &&
     315        2951 :           (get_platform() != VTEST_PLATFORM) &&
     316           0 :             (vrouter_obtain_family_id(cl) <= 0))
     317           0 :         goto fail;
     318             : 
     319        2951 :     return cl;
     320             : 
     321           0 : fail:
     322           0 :     if (cl)
     323           0 :         nl_free_client(cl);
     324             : 
     325           0 :     return NULL;
     326             : }
     327             : 
     328             : int
     329           0 : vr_send_get_bridge_table_data(struct nl_client *cl)
     330             : {
     331             :     int ret;
     332             :     vr_bridge_table_data req;
     333             : 
     334           0 :     memset(&req, 0, sizeof(req));
     335           0 :     req.btable_op = SANDESH_OP_GET;
     336           0 :     req.btable_rid = 0;
     337             : 
     338           0 :     return vr_sendmsg(cl, &req, "vr_bridge_table_data");
     339             : }
     340             : 
     341             : int
     342           0 : vr_send_set_dcb_state(struct nl_client *cl, uint8_t *ifname, uint8_t state)
     343             : {
     344             :     int ret;
     345             : 
     346           0 :     ret = nl_build_set_dcb_state_msg(cl, ifname, state);
     347           0 :     if (ret < 0)
     348           0 :         return ret;
     349             : 
     350           0 :     ret = nl_dcb_sendmsg(cl, DCB_CMD_SSTATE, NULL);
     351           0 :     if (ret <= 0)
     352           0 :         return ret;
     353             : 
     354           0 :     if (ret != state) {
     355           0 :         printf("vRouter: Set DCB State failed (Req/Resp: %u/%d)\n",
     356             :                 state, ret);
     357           0 :         return -1;
     358             :     }
     359             : 
     360           0 :     return 0;
     361             : }
     362             : 
     363             : int
     364           0 : vr_send_get_dcb_state(struct nl_client *cl, uint8_t *ifname)
     365             : {
     366             :     int ret;
     367             : 
     368           0 :     ret = nl_build_get_dcb_state_msg(cl, ifname);
     369           0 :     if (ret < 0)
     370           0 :         return ret;
     371             : 
     372           0 :     return nl_dcb_sendmsg(cl, DCB_CMD_GSTATE, NULL);
     373             : }
     374             : 
     375             : int
     376           0 : vr_send_set_dcbx(struct nl_client *cl, uint8_t *ifname, uint8_t dcbx)
     377             : {
     378             :     int ret;
     379             : 
     380           0 :     ret = nl_build_set_dcbx(cl, ifname, dcbx);
     381           0 :     if (ret < 0)
     382           0 :         return ret;
     383             : 
     384           0 :     ret = nl_dcb_sendmsg(cl, DCB_CMD_SDCBX, NULL);
     385           0 :     if (ret < 0)
     386           0 :         return ret;
     387             : 
     388           0 :     if (ret) {
     389           0 :         printf("vRouter: Set DCBX failed (Req/Resp: %u/%d)\n",
     390             :             dcbx, ret);
     391           0 :         return -1;
     392             :     }
     393             : 
     394           0 :     return 0;
     395             : }
     396             : 
     397             : int
     398           0 : vr_send_get_dcbx(struct nl_client *cl, uint8_t *ifname)
     399             : {
     400             :     int ret;
     401             : 
     402           0 :     ret = nl_build_get_dcbx(cl, ifname);
     403           0 :     if (ret < 0)
     404           0 :         return ret;
     405             : 
     406           0 :     return nl_dcb_sendmsg(cl, DCB_CMD_GDCBX, NULL);
     407             : }
     408             : 
     409             : int
     410           0 : vr_send_get_priority_config(struct nl_client *cl, uint8_t *ifname,
     411             :         struct priority *p)
     412             : {
     413             :     int ret;
     414             : 
     415           0 :     ret = nl_build_get_priority_config_msg(cl, ifname);
     416           0 :     if (ret < 0)
     417           0 :         return ret;
     418             : 
     419           0 :     ret = nl_dcb_sendmsg(cl, DCB_CMD_PGTX_GCFG, p);
     420           0 :     if (ret < 0)
     421           0 :         return ret;
     422             : 
     423           0 :     return 0;
     424             : }
     425             : 
     426             : int
     427           0 : vr_send_set_priority_config(struct nl_client *cl, uint8_t *ifname,
     428             :         struct priority *p)
     429             : {
     430             :     int ret;
     431             : 
     432           0 :     ret = nl_build_set_priority_config_msg(cl, ifname, p);
     433           0 :     if (ret < 0)
     434           0 :         return ret;
     435             : 
     436           0 :     ret = nl_dcb_sendmsg(cl, DCB_CMD_PGTX_SCFG, NULL);
     437           0 :     if (ret < 0)
     438           0 :         return ret;
     439             : 
     440           0 :     return 0;
     441             : }
     442             : 
     443             : int
     444           0 : vr_send_set_dcb_all(struct nl_client *cl, uint8_t *ifname)
     445             : {
     446             :     int ret;
     447             : 
     448           0 :     ret = nl_build_set_dcb_all(cl, ifname);
     449           0 :     if (ret < 0)
     450           0 :         return ret;
     451             : 
     452           0 :     return nl_dcb_sendmsg(cl, DCB_CMD_SET_ALL, NULL);
     453             : }
     454             : 
     455             : int
     456           0 : vr_send_get_ieee_ets(struct nl_client *cl, uint8_t *ifname,
     457             :         struct priority *p)
     458             : {
     459             :     int ret;
     460             : 
     461           0 :     ret = nl_build_get_ieee_ets(cl, ifname, p);
     462           0 :     if (ret < 0)
     463           0 :         return ret;
     464             : 
     465           0 :     return nl_dcb_sendmsg(cl, DCB_CMD_IEEE_GET, p);
     466             : }
     467             : 
     468             : int
     469           0 : vr_send_set_ieee_ets(struct nl_client *cl, uint8_t *ifname,
     470             :         struct priority *p)
     471             : {
     472             :     int ret;
     473             : 
     474           0 :     ret = nl_build_set_ieee_ets(cl, ifname, p);
     475           0 :     if (ret < 0)
     476           0 :         return ret;
     477             : 
     478           0 :     return nl_dcb_sendmsg(cl, DCB_CMD_IEEE_SET, NULL);
     479             : }
     480             : 
     481             : void
     482           1 : vr_print_drop_stats(vr_drop_stats_req *stats, int core)
     483             : {
     484           1 :     int platform = get_platform();
     485             : 
     486           1 :     if (core != (unsigned)-1)
     487           0 :         printf("Statistics for core %u\n\n", core);
     488             : 
     489           1 :     if (stats->vds_pcpu_stats_failure_status)
     490           0 :        printf("Failed to maintain PerCPU stats for this interface\n\n");
     491             : 
     492           1 :     PRINT_DROP_STAT("Invalid IF", stats->vds_invalid_if);
     493           1 :     PRINT_DROP_STAT("Invalid ARP", stats->vds_invalid_arp);
     494           1 :     PRINT_DROP_STAT("Trap No IF", stats->vds_trap_no_if);
     495           1 :     PRINT_DROP_STAT("IF TX Discard", stats->vds_interface_tx_discard);
     496           1 :     PRINT_DROP_STAT("IF Drop", stats->vds_interface_drop);
     497           1 :     PRINT_DROP_STAT("IF RX Discard", stats->vds_interface_rx_discard);
     498           1 :     PRINT_DROP_STAT("Flow Unusable", stats->vds_flow_unusable);
     499           1 :     PRINT_DROP_STAT("Flow No Memory",stats->vds_flow_no_memory);
     500           1 :     PRINT_DROP_STAT("Flow Table Full", stats->vds_flow_table_full);
     501           1 :     PRINT_DROP_STAT("Flow NAT no rflow", stats->vds_flow_nat_no_rflow);
     502           1 :     PRINT_DROP_STAT("Flow Action Drop", stats->vds_flow_action_drop);
     503           1 :     PRINT_DROP_STAT("Flow Action Invalid", stats->vds_flow_action_invalid);
     504           1 :     PRINT_DROP_STAT("Flow Invalid Protocol", stats->vds_flow_invalid_protocol);
     505           1 :     PRINT_DROP_STAT("Flow Queue Limit Exceeded", stats->vds_flow_queue_limit_exceeded);
     506           1 :     PRINT_DROP_STAT("New Flow Drops", stats->vds_drop_new_flow);
     507           1 :     PRINT_DROP_STAT("Flow Unusable (Eviction)", stats->vds_flow_evict);
     508           1 :     PRINT_DROP_STAT("Original Packet Trapped", stats->vds_trap_original);
     509           1 :     PRINT_DROP_STAT("Discards", stats->vds_discard);
     510           1 :     PRINT_DROP_STAT("TTL Exceeded", stats->vds_ttl_exceeded);
     511           1 :     PRINT_DROP_STAT("Mcast Clone Fail", stats->vds_mcast_clone_fail);
     512           1 :     PRINT_DROP_STAT("Invalid NH", stats->vds_invalid_nh);
     513           1 :     PRINT_DROP_STAT("Invalid Label", stats->vds_invalid_label);
     514           1 :     PRINT_DROP_STAT("Invalid Protocol", stats->vds_invalid_protocol);
     515           1 :     PRINT_DROP_STAT("Etree Leaf to Leaf", stats->vds_leaf_to_leaf);
     516           1 :     PRINT_DROP_STAT("Bmac/ISID Mismatch", stats->vds_bmac_isid_mismatch);
     517           1 :     PRINT_DROP_STAT("Rewrite Fail", stats->vds_rewrite_fail);
     518           1 :     PRINT_DROP_STAT("Invalid Mcast Source", stats->vds_invalid_mcast_source);
     519           1 :     PRINT_DROP_STAT("Packet Loop", stats->vds_pkt_loop);
     520           1 :     PRINT_DROP_STAT("Push Fails", stats->vds_push);
     521           1 :     PRINT_DROP_STAT("Pull Fails", stats->vds_pull);
     522           1 :     PRINT_DROP_STAT("Duplicate", stats->vds_duplicated);
     523           1 :     PRINT_DROP_STAT("Head Alloc Fails", stats->vds_head_alloc_fail);
     524           1 :     PRINT_DROP_STAT("PCOW fails", stats->vds_pcow_fail);
     525           1 :     PRINT_DROP_STAT("Invalid Packets", stats->vds_invalid_packet);
     526           1 :     PRINT_DROP_STAT("Misc", stats->vds_misc);
     527           1 :     PRINT_DROP_STAT("Nowhere to go", stats->vds_nowhere_to_go);
     528           1 :     PRINT_DROP_STAT("Checksum errors", stats->vds_cksum_err);
     529           1 :     PRINT_DROP_STAT("No Fmd", stats->vds_no_fmd);
     530           1 :     PRINT_DROP_STAT("Invalid VNID", stats->vds_invalid_vnid);
     531           1 :     PRINT_DROP_STAT("Fragment errors", stats->vds_frag_err);
     532           1 :     PRINT_DROP_STAT("Invalid Source", stats->vds_invalid_source);
     533           1 :     PRINT_DROP_STAT("Jumbo Mcast Pkt with DF Bit", stats->vds_mcast_df_bit);
     534           1 :     PRINT_DROP_STAT("No L2 Route", stats->vds_l2_no_route);
     535           1 :     PRINT_DROP_STAT("Memory Failures", stats->vds_no_memory);
     536           1 :     PRINT_DROP_STAT("Fragment Queueing Failures", stats->vds_fragment_queue_fail);
     537           1 :     PRINT_DROP_STAT("No Encrypt Path Failures", stats->vds_no_crypt_path);
     538           1 :     PRINT_DROP_STAT("Invalid HBS received packet", stats->vds_invalid_hbs_pkt);
     539           1 :     PRINT_DROP_STAT("No Fragment Entries", stats->vds_no_frag_entry);
     540           1 :     PRINT_DROP_STAT("ICMP errors", stats->vds_icmp_error);
     541           1 :     PRINT_DROP_STAT("Clone Failures", stats->vds_clone_fail);
     542           1 :     PRINT_DROP_STAT("Invalid underlay ECMP", stats->vds_invalid_underlay_ecmp);
     543             : 
     544           1 :     if (platform == DPDK_PLATFORM)
     545             :     {
     546           0 :         PRINT_DROP_STAT("VLAN fwd intf failed TX", stats->vds_vlan_fwd_tx);
     547           0 :         PRINT_DROP_STAT("VLAN fwd intf failed enq", stats->vds_vlan_fwd_enq);
     548             :     }
     549           1 :     return;
     550             : }
     551             : 
     552             : void
     553           0 : vr_print_drop_dbg_stats(vr_drop_stats_req *stats, int core)
     554             : {
     555           0 :     printf("Cloned Original               %" PRIu64 "\n",
     556             :             stats->vds_cloned_original);
     557           0 :     return;
     558             : }
     559             : 
     560             : const char *
     561           0 : vr_pkt_vp_type_rsn(unsigned char vp_type)
     562             : {
     563           0 :     switch(vp_type) {
     564           0 :     case VP_TYPE_ARP:    return "ARP";
     565           0 :     case VP_TYPE_IP :    return "IP";
     566           0 :     case VP_TYPE_IP6:    return "IP6";
     567           0 :     case VP_TYPE_IPOIP:  return "IPOIP";
     568           0 :     case VP_TYPE_IP6OIP: return "IP6OIP";
     569           0 :     case VP_TYPE_AGENT:  return "AGENT";
     570           0 :     case VP_TYPE_PBB:    return "PBB";
     571           0 :     default:             return "UNKNOWN";
     572             :     }
     573             : }
     574             : 
     575             : const char *
     576           0 : vr_pkt_droplog_rsn(unsigned short drop_reason)
     577             : {
     578           0 :     switch(drop_reason) {
     579           0 :     case VP_DROP_DISCARD:
     580           0 :         return "Discards";
     581           0 :     case VP_DROP_PULL:
     582           0 :         return "Pull Fails";
     583           0 :     case VP_DROP_INVALID_IF:
     584           0 :         return "Invalid IF";
     585           0 :     case VP_DROP_INVALID_ARP:
     586           0 :         return "Invalid ARP";
     587           0 :     case VP_DROP_TRAP_NO_IF:
     588           0 :         return "Trap No IF";
     589           0 :     case VP_DROP_NOWHERE_TO_GO:
     590           0 :         return "Nowhere to go";
     591           0 :     case VP_DROP_FLOW_QUEUE_LIMIT_EXCEEDED:
     592           0 :         return "Flow Queue Limit Exceeded";
     593           0 :     case VP_DROP_FLOW_NO_MEMORY:
     594           0 :         return "Flow No Memory";
     595           0 :     case VP_DROP_FLOW_INVALID_PROTOCOL:
     596           0 :         return "Flow Invalid Protocol";
     597           0 :     case VP_DROP_FLOW_NAT_NO_RFLOW:
     598           0 :         return "Flow NAT no rflow";
     599           0 :     case VP_DROP_FLOW_ACTION_DROP:
     600           0 :         return "Flow Action Drop";
     601           0 :     case VP_DROP_FLOW_ACTION_INVALID:
     602           0 :         return "Flow Action Invalid";
     603           0 :     case VP_DROP_FLOW_UNUSABLE:
     604           0 :         return "Flow Unusable";
     605           0 :     case VP_DROP_FLOW_TABLE_FULL:
     606           0 :         return "Flow Table Full";
     607           0 :     case VP_DROP_INTERFACE_TX_DISCARD:
     608           0 :         return "IF TX Discard";
     609           0 :     case VP_DROP_INTERFACE_DROP:
     610           0 :         return "IF Drop";
     611           0 :     case VP_DROP_DUPLICATED:
     612           0 :         return "Duplicate";
     613           0 :     case VP_DROP_PUSH:
     614           0 :         return "Push Fails";
     615           0 :     case VP_DROP_TTL_EXCEEDED:
     616           0 :         return "TTL Exceeded";
     617           0 :     case VP_DROP_INVALID_NH:
     618           0 :         return "Invalid NH";
     619           0 :     case VP_DROP_INVALID_LABEL:
     620           0 :         return "Invalid Label";
     621           0 :     case VP_DROP_INVALID_PROTOCOL:
     622           0 :         return "Invalid Protocol";
     623           0 :     case VP_DROP_INTERFACE_RX_DISCARD:
     624           0 :         return "IF RX Discard";
     625           0 :     case VP_DROP_INVALID_MCAST_SOURCE:
     626           0 :         return "Invalid Mcast Source";
     627           0 :     case VP_DROP_HEAD_ALLOC_FAIL:
     628           0 :         return "Head Alloc Fails";
     629           0 :     case VP_DROP_PCOW_FAIL:
     630           0 :         return "PCOW fails";
     631           0 :     case VP_DROP_MCAST_DF_BIT:
     632           0 :         return "Jumbo Mcast Pkt with DF Bit";
     633           0 :     case VP_DROP_MCAST_CLONE_FAIL:
     634           0 :         return "Mcast Clone Fail";
     635           0 :     case VP_DROP_NO_MEMORY:
     636           0 :         return "Memory Failures";
     637           0 :     case VP_DROP_REWRITE_FAIL:
     638           0 :         return "Rewrite Fail";
     639           0 :     case VP_DROP_MISC:
     640           0 :         return "Misc";
     641           0 :     case VP_DROP_INVALID_PACKET:
     642           0 :         return "Invalid Packets";
     643           0 :     case VP_DROP_CKSUM_ERR:
     644           0 :         return "Checksum errors";
     645           0 :     case VP_DROP_NO_FMD:
     646           0 :         return "No Fmd";
     647           0 :     case VP_DROP_CLONED_ORIGINAL:
     648           0 :         return "Cloned Original";
     649           0 :     case VP_DROP_INVALID_VNID:
     650           0 :         return "Invalid VNID";
     651           0 :     case VP_DROP_FRAGMENTS:
     652           0 :         return "Fragment errors";
     653           0 :     case VP_DROP_INVALID_SOURCE:
     654           0 :         return "Invalid Source";
     655           0 :     case VP_DROP_L2_NO_ROUTE:
     656           0 :         return "No L2 Route";
     657           0 :     case VP_DROP_FRAGMENT_QUEUE_FAIL:
     658           0 :         return "Fragment Queueing Failures";
     659           0 :     case VP_DROP_VLAN_FWD_TX:
     660           0 :         return "VLAN fwd intf failed TX";
     661           0 :     case VP_DROP_VLAN_FWD_ENQ:
     662           0 :         return "VLAN fwd intf failed enq";
     663           0 :     case VP_DROP_NEW_FLOWS:
     664           0 :         return "New Flow Drops";
     665           0 :     case VP_DROP_FLOW_EVICT:
     666           0 :         return "Flow Unusable (Eviction)";
     667           0 :     case VP_DROP_TRAP_ORIGINAL:
     668           0 :         return "Original Packet Trapped";
     669           0 :     case VP_DROP_LEAF_TO_LEAF:
     670           0 :         return "Etree Leaf to Leaf";
     671           0 :     case VP_DROP_BMAC_ISID_MISMATCH:
     672           0 :         return "Bmac/ISID Mismatch";
     673           0 :     case VP_DROP_PKT_LOOP:
     674           0 :         return "Packet Loop";
     675           0 :     case VP_DROP_NO_CRYPT_PATH:
     676           0 :         return "No Encrypt Path Failures";
     677           0 :     case VP_DROP_INVALID_HBS_PKT:
     678           0 :         return "Invalid HBS received packet";
     679           0 :     case VP_DROP_NO_FRAG_ENTRY:
     680           0 :         return "No Fragment Entries";
     681           0 :     case VP_DROP_ICMP_ERROR:
     682           0 :         return "ICMP errors";
     683           0 :     case VP_DROP_CLONE_FAIL:
     684           0 :         return "Clone Failures";
     685           0 :     case VP_DROP_INVALID_UNDERLAY_ECMP:
     686           0 :         return "Invalid underlay ECMP";
     687           0 :     default:
     688           0 :         return "Unknow";
     689             :     }
     690             : 
     691             : }
     692           0 : void vr_print_pkt_drop_log_data(vr_pkt_drop_log_req *pkt_log, int i,
     693             :                                 uint8_t show_pkt_drop_type)
     694             : {
     695           0 :     int j = 0;
     696           0 :     vr_pkt_drop_log_t *pkt_log_utils =
     697             :         (vr_pkt_drop_log_t*)pkt_log->vdl_pkt_droplog_arr;
     698             :     struct tm *ptr_time;
     699           0 :     char ipv6_addr[INET6_ADDRSTRLEN] = "";
     700             : 
     701             :     /* String mapping for packet drop log */
     702           0 :     char vr_pkt_droplog_str[][50] = {
     703             :         FILE_MAP(string)
     704             :     };
     705             : 
     706           0 :     if (!pkt_log_utils[i].vp_type)
     707           0 :         return;
     708             : 
     709           0 :     if ((show_pkt_drop_type != VP_DROP_MAX) &&
     710           0 :         (show_pkt_drop_type != pkt_log_utils[i].drop_reason))
     711           0 :         return;
     712             : 
     713           0 :     if((pkt_log->vdl_log_idx+i < VR_PKT_DROP_LOG_MAX) &&
     714           0 :         (!vr_header_include))
     715             :     {
     716           0 :         vr_print_pkt_drop_log_header(pkt_log);
     717           0 :         vr_header_include = 1;
     718             :     }
     719             : 
     720           0 :     ptr_time = localtime(&(pkt_log_utils[i].timestamp));
     721             : 
     722           0 :     printf("sl no: %d  ", pkt_log->vdl_log_idx+i);
     723           0 :     printf("Epoch Time: %ld ", pkt_log_utils[i].timestamp);
     724           0 :     printf("Local Time: %s ", asctime(ptr_time));
     725           0 :     printf("Packet Type: %s  ", vr_pkt_vp_type_rsn(pkt_log_utils[i].vp_type));
     726           0 :     if(pkt_log_utils[i].drop_reason)
     727           0 :         printf("Drop reason: %s  ", vr_pkt_droplog_rsn(pkt_log_utils[i].drop_reason));
     728           0 :     PRINT_PKT_LOG("Vif idx:",    pkt_log_utils[i].vif_idx);
     729           0 :     PRINT_PKT_LOG("Nexthop id:", pkt_log_utils[i].nh_id);
     730           0 :     if(pkt_log_utils[i].vp_type == VP_TYPE_IP)
     731             :     {
     732           0 :         printf("Src IP: %s  ", inet_ntoa(pkt_log_utils[i].src.ipv4));
     733           0 :         printf("Dst IP: %s  ", inet_ntoa(pkt_log_utils[i].dst.ipv4));
     734             :     }
     735           0 :     else if (pkt_log_utils[i].vp_type == VP_TYPE_IP6)
     736             :     {
     737           0 :         inet_ntop(AF_INET6, &pkt_log_utils[i].src.ipv6, ipv6_addr, INET6_ADDRSTRLEN);
     738           0 :         printf("Src IPv6: %s  ", ipv6_addr);
     739           0 :         inet_ntop(AF_INET6, &pkt_log_utils[i].dst.ipv6, ipv6_addr, INET6_ADDRSTRLEN);
     740           0 :         printf("Dst IPv6: %s  ", ipv6_addr);
     741             :     }
     742             : 
     743           0 :     PRINT_PKT_LOG("Source port:", pkt_log_utils[i].sport);
     744           0 :     PRINT_PKT_LOG("Dest port:",   pkt_log_utils[i].dport);
     745           0 :     if(pkt_log_utils[i].drop_loc.file)
     746           0 :         printf("file: %s  ", vr_pkt_droplog_str[pkt_log_utils[i].drop_loc.file]);
     747           0 :     printf("line no: %d  ", pkt_log_utils[i].drop_loc.line);
     748             : 
     749           0 :     if(pkt_log_utils[i].pkt_len)
     750             :     {
     751           0 :         printf("Packet Length: %d  ", pkt_log_utils[i].pkt_len);
     752           0 :         printf("Packet Data: ");
     753             : 
     754           0 :         if(pkt_log_utils[i].pkt_len > 100)
     755           0 :             for(j = 0; j < 100; j++)
     756           0 :                 printf("%02X  ", pkt_log_utils[i].pkt_header[j]);
     757             :         else
     758           0 :             for(j=0;j<pkt_log_utils[i].pkt_len;j++)
     759           0 :                 printf("%02X  ", pkt_log_utils[i].pkt_header[j]);
     760             :     }
     761           0 :     printf("\n\n");
     762             : }
     763           0 : void vr_print_pkt_drop_log_header(vr_pkt_drop_log_req *pkt_log)
     764             : {
     765           0 :     printf("**********PKT DROP LOG**********\n");
     766           0 :     printf("Total No. of CPU's %d\n", pkt_log->vdl_max_num_cores);
     767             :     /* When requested for core 0, it will try to log for all cores
     768             :      * so here manually printing as core 1 */
     769           0 :     if(pkt_log->vdl_core == 0)
     770           0 :         printf("Pkt Drop Log for Core 1\n\n");
     771             :     else
     772           0 :         printf("Pkt Drop Log for Core %d\n\n", pkt_log->vdl_core);
     773           0 : }
     774             : void
     775           0 : vr_print_pkt_drop_log(vr_pkt_drop_log_req *pkt_log, uint8_t show_pkt_drop_type)
     776             : {
     777           0 :     int i = 0, log_buffer_iter = 0;
     778             :     static bool vr_header_include = 0;
     779             : 
     780             :     /* When configured pkt buffer size is than MAX_ALLOWED_BUFFER_SIZE */
     781           0 :     if(pkt_log->vdl_pkt_droplog_max_bufsz - pkt_log->vdl_log_idx  <
     782             :             VR_PKT_DROPLOG_MAX_ALLOW_BUFSZ)
     783             :     {
     784           0 :         log_buffer_iter = pkt_log->vdl_pkt_droplog_max_bufsz - pkt_log->vdl_log_idx;
     785             :     }
     786             :     else
     787           0 :         log_buffer_iter = VR_PKT_DROPLOG_MAX_ALLOW_BUFSZ;
     788             : 
     789           0 :     for(i = 0; i < log_buffer_iter; i++)
     790           0 :         vr_print_pkt_drop_log_data(pkt_log, i, show_pkt_drop_type);
     791             : 
     792             :     /* On Every VR_PKT_DROP_LOG_MAX count time need to check this
     793             :      * flag to print PKT DROP header
     794             :      */
     795           0 :     if((pkt_log->vdl_log_idx + log_buffer_iter == VR_PKT_DROP_LOG_MAX) &&
     796             :         (vr_header_include))
     797             :     {
     798           0 :         vr_header_include = 0;
     799             :     }
     800           0 :     return;
     801             : }
     802             : 
     803             : int
     804          17 : vr_response_common_process(vr_response *resp, bool *dump_pending)
     805             : {
     806          17 :     int ret = 0;
     807             : 
     808          17 :     if (dump_pending)
     809          17 :         *dump_pending = false;
     810             : 
     811          17 :     if (resp->resp_code < 0) {
     812           4 :         if (!vr_ignore_nl_errors) {
     813           4 :             printf("vRouter(Response): %s (%d)\n", strerror(-resp->resp_code),
     814           4 :                     -resp->resp_code);
     815             :         }
     816           4 :         ret = resp->resp_code;
     817             :     } else {
     818          13 :         if ((resp->resp_code & VR_MESSAGE_DUMP_INCOMPLETE) &&
     819             :                 dump_pending)
     820           0 :             *dump_pending = true;
     821             :     }
     822             : 
     823          17 :     return ret;
     824             : }
     825             : 
     826             : /* dropstats start */
     827             : uint64_t
     828           5 : vr_sum_drop_stats(vr_drop_stats_req *req)
     829             : {
     830           5 :     uint64_t sum = 0;
     831             : 
     832           5 :     sum += req->vds_discard;
     833           5 :     sum += req->vds_pull;
     834           5 :     sum += req->vds_invalid_if;
     835           5 :     sum += req->vds_invalid_arp;
     836           5 :     sum += req->vds_trap_no_if;
     837           5 :     sum += req->vds_nowhere_to_go;
     838           5 :     sum += req->vds_flow_queue_limit_exceeded;
     839           5 :     sum += req->vds_flow_no_memory;
     840           5 :     sum += req->vds_flow_invalid_protocol;
     841           5 :     sum += req->vds_flow_nat_no_rflow;
     842           5 :     sum += req->vds_flow_action_drop;
     843           5 :     sum += req->vds_flow_action_invalid;
     844           5 :     sum += req->vds_flow_unusable;
     845           5 :     sum += req->vds_flow_table_full;
     846           5 :     sum += req->vds_interface_tx_discard;
     847           5 :     sum += req->vds_interface_drop;
     848           5 :     sum += req->vds_duplicated;
     849           5 :     sum += req->vds_push;
     850           5 :     sum += req->vds_ttl_exceeded;
     851           5 :     sum += req->vds_invalid_nh;
     852           5 :     sum += req->vds_invalid_label;
     853           5 :     sum += req->vds_invalid_protocol;
     854           5 :     sum += req->vds_interface_rx_discard;
     855           5 :     sum += req->vds_invalid_mcast_source;
     856           5 :     sum += req->vds_head_alloc_fail;
     857           5 :     sum += req->vds_pcow_fail;
     858           5 :     sum += req->vds_mcast_df_bit;
     859           5 :     sum += req->vds_mcast_clone_fail;
     860           5 :     sum += req->vds_no_memory;
     861           5 :     sum += req->vds_rewrite_fail;
     862           5 :     sum += req->vds_misc;
     863           5 :     sum += req->vds_invalid_packet;
     864           5 :     sum += req->vds_cksum_err;
     865           5 :     sum += req->vds_no_fmd;
     866           5 :     sum += req->vds_cloned_original;
     867           5 :     sum += req->vds_invalid_vnid;
     868           5 :     sum += req->vds_frag_err;
     869           5 :     sum += req->vds_invalid_source;
     870           5 :     sum += req->vds_l2_no_route;
     871           5 :     sum += req->vds_fragment_queue_fail;
     872           5 :     sum += req->vds_vlan_fwd_tx;
     873           5 :     sum += req->vds_vlan_fwd_enq;
     874           5 :     sum += req->vds_drop_new_flow;
     875           5 :     sum += req->vds_trap_original;
     876           5 :     sum += req->vds_pkt_loop;
     877           5 :     sum += req->vds_no_crypt_path;
     878           5 :     sum += req->vds_invalid_underlay_ecmp;
     879             : 
     880           5 :     return sum;
     881             : }
     882             : 
     883             : void
     884           5 : vr_drop_stats_req_destroy(vr_drop_stats_req *req)
     885             : {
     886           5 :     if (!req)
     887           0 :         return;
     888             : 
     889           5 :     free(req);
     890           5 :     return;
     891             : }
     892             : 
     893             : vr_drop_stats_req *
     894           5 : vr_drop_stats_req_get_copy(vr_drop_stats_req *src)
     895             : {
     896             :     vr_drop_stats_req *dst;
     897             : 
     898           5 :     if (!src)
     899           0 :         return NULL;
     900             : 
     901           5 :     dst = malloc(sizeof(*dst));
     902           5 :     if (!dst)
     903           0 :         return NULL;
     904             : 
     905           5 :     *dst = *src;
     906           5 :     return dst;
     907             : }
     908             : 
     909             : int
     910           6 : vr_send_drop_stats_get(struct nl_client *cl, unsigned int router_id,
     911             :         short core)
     912             : {
     913             :     vr_drop_stats_req req;
     914             : 
     915           6 :     memset(&req, 0, sizeof(req));
     916           6 :     req.h_op = SANDESH_OP_GET;
     917           6 :     req.vds_rid = router_id;
     918           6 :     req.vds_core = core;
     919             : 
     920           6 :     return vr_sendmsg(cl, &req, "vr_drop_stats_req");
     921             : }
     922             : 
     923             : 
     924             : int
     925           1 : vr_send_info_dump(struct nl_client *cl, unsigned int router_id,
     926             :         int marker, int buff_table_id, vr_info_msg_en msginfo, int buffsz,
     927             :         uint8_t *vr_info_inbuf)
     928             : {
     929             :     vr_info_req req;
     930             : 
     931           1 :     memset(&req, 0, sizeof(req));
     932           1 :     req.h_op = SANDESH_OP_DUMP;
     933           1 :     req.vdu_rid = router_id;
     934           1 :     req.vdu_marker = marker;
     935           1 :     req.vdu_buff_table_id = buff_table_id;
     936           1 :     req.vdu_msginfo = msginfo;
     937           1 :     req.vdu_outbufsz = buffsz;
     938           1 :     if(vr_info_inbuf != NULL) {
     939           1 :         req.vdu_inbuf_size = strlen(vr_info_inbuf);
     940           1 :         req.vdu_inbuf = vr_info_inbuf;
     941             :     }
     942           1 :     return vr_sendmsg(cl, &req, "vr_info_req");
     943             : }
     944             : 
     945             : int
     946           0 : vr_pkt_drop_log_reset(struct nl_client *cl)
     947             : {
     948             :     vr_pkt_drop_log_req req;
     949             : 
     950           0 :     memset(&req, 0, sizeof(req));
     951           0 :     req.h_op = SANDESH_OP_RESET;
     952             : 
     953           0 :     return vr_sendmsg(cl, &req, "vr_pkt_drop_log_req");
     954             : }
     955             : 
     956             : int
     957           0 : vr_drop_stats_reset(struct nl_client *cl)
     958             : {
     959             :     vr_drop_stats_req req;
     960             : 
     961           0 :     memset(&req, 0, sizeof(req));
     962           0 :     req.h_op = SANDESH_OP_RESET;
     963             : 
     964           0 :     return vr_sendmsg(cl, &req, "vr_drop_stats_req");
     965             : }
     966             : 
     967             : int
     968           0 : vr_drop_type_set(struct nl_client *cl, uint8_t pkt_drop_log_type)
     969             : {
     970             :     vr_pkt_drop_log_req req;
     971             : 
     972           0 :     memset(&req, 0, sizeof(req));
     973           0 :     req.h_op                 = SANDESH_OP_ADD;
     974           0 :     req.vdl_pkt_droplog_type = pkt_drop_log_type;
     975             : 
     976             :     /* this flag is to indentify bettwn min log config and drop type set
     977             :        if 1 used for drop type config
     978             :        if 0 used for min log config
     979             :     */
     980           0 :     req.vdl_pkt_droplog_config = true;
     981             : 
     982           0 :     return vr_sendmsg(cl, &req, "vr_pkt_drop_log_req");
     983             : }
     984             : 
     985             : int
     986           0 : vr_min_log_enable(struct nl_client *cl, bool min_log)
     987             : {
     988             :     vr_pkt_drop_log_req req;
     989             : 
     990           0 :     memset(&req, 0, sizeof(req));
     991           0 :     req.h_op                          = SANDESH_OP_ADD;
     992           0 :     req.vdl_pkt_droplog_min_sysctl_en = min_log;
     993             : 
     994             :     /* this flag is to indentify between min log config and drop type set
     995             :        if 1 used for drop type config
     996             :        if 0 used for min log config
     997             :     */
     998           0 :     req.vdl_pkt_droplog_config = false;
     999           0 :     return vr_sendmsg(cl, &req, "vr_pkt_drop_log_req");
    1000             : }
    1001             : 
    1002           0 : int vr_pkt_drop_log_request(struct nl_client *cl, unsigned int router_id,
    1003             :         unsigned int core, int log_idx )
    1004             : {
    1005           0 :     int ret = 0;
    1006             :     vr_pkt_drop_log_req req;
    1007             : 
    1008           0 :     memset(&req, 0, sizeof(req));
    1009             : 
    1010           0 :     req.vdl_pkt_droplog_arr = (char *)malloc(1);
    1011             : 
    1012           0 :     req.h_op = SANDESH_OP_GET;
    1013           0 :     req.vdl_rid = router_id;
    1014           0 :     req.vdl_core = core;
    1015           0 :     req.vdl_log_idx = log_idx;
    1016             : 
    1017           0 :     ret =  vr_sendmsg(cl, &req, "vr_pkt_drop_log_req");
    1018             : 
    1019           0 :     free(req.vdl_pkt_droplog_arr);
    1020             : 
    1021           0 :     return ret;
    1022             : }
    1023             : /* dropstats end */
    1024             : 
    1025             : /* Interface start */
    1026             : void
    1027          25 : vr_interface_req_destroy(vr_interface_req *req)
    1028             : {
    1029          25 :     if (!req)
    1030          18 :         return;
    1031             : 
    1032           7 :     if (req->vifr_name) {
    1033           7 :         free(req->vifr_name);
    1034           7 :         req->vifr_name = NULL;
    1035             :     }
    1036             : 
    1037           7 :     if (req->vifr_queue_ierrors_to_lcore_size &&
    1038           7 :             req->vifr_queue_ierrors_to_lcore) {
    1039           7 :         free(req->vifr_queue_ierrors_to_lcore);
    1040           7 :         req->vifr_queue_ierrors_to_lcore = NULL;
    1041           7 :         req->vifr_queue_ierrors_to_lcore_size = 0;
    1042             :     }
    1043             : 
    1044             : 
    1045           7 :     if (req->vifr_mac && req->vifr_mac_size) {
    1046           7 :         free(req->vifr_mac);
    1047           7 :         req->vifr_mac = NULL;
    1048           7 :         req->vifr_mac_size = 0;
    1049             :     }
    1050             : 
    1051           7 :     if (req->vifr_src_mac && req->vifr_src_mac_size) {
    1052           0 :         free(req->vifr_src_mac);
    1053           0 :         req->vifr_src_mac = NULL;
    1054           0 :         req->vifr_src_mac_size = 0;
    1055             :     }
    1056             : 
    1057           7 :     if (req->vifr_fat_flow_protocol_port_size &&
    1058           0 :             req->vifr_fat_flow_protocol_port) {
    1059           0 :         free(req->vifr_fat_flow_protocol_port);
    1060           0 :         req->vifr_fat_flow_protocol_port = NULL;
    1061           0 :         req->vifr_fat_flow_protocol_port_size = 0;
    1062             :     }
    1063             : 
    1064           7 :     if (req->vifr_fat_flow_src_prefix_h &&
    1065           0 :         req->vifr_fat_flow_src_prefix_h_size) {
    1066           0 :         free(req->vifr_fat_flow_src_prefix_h);
    1067           0 :         req->vifr_fat_flow_src_prefix_h = NULL;
    1068           0 :         req->vifr_fat_flow_src_prefix_h_size = 0;
    1069             :     }
    1070           7 :     if (req->vifr_fat_flow_src_prefix_l &&
    1071           0 :         req->vifr_fat_flow_src_prefix_l_size) {
    1072           0 :         free(req->vifr_fat_flow_src_prefix_l);
    1073           0 :         req->vifr_fat_flow_src_prefix_l = NULL;
    1074           0 :         req->vifr_fat_flow_src_prefix_l_size = 0;
    1075             :     }
    1076           7 :     if (req->vifr_fat_flow_src_prefix_mask &&
    1077           0 :         req->vifr_fat_flow_src_prefix_mask_size) {
    1078           0 :         free(req->vifr_fat_flow_src_prefix_mask);
    1079           0 :         req->vifr_fat_flow_src_prefix_mask = NULL;
    1080           0 :         req->vifr_fat_flow_src_prefix_mask_size = 0;
    1081             :     }
    1082           7 :     if (req->vifr_fat_flow_src_aggregate_plen &&
    1083           0 :         req->vifr_fat_flow_src_aggregate_plen_size) {
    1084           0 :         free(req->vifr_fat_flow_src_aggregate_plen);
    1085           0 :         req->vifr_fat_flow_src_aggregate_plen = NULL;
    1086           0 :         req->vifr_fat_flow_src_aggregate_plen_size = 0;
    1087             :     }
    1088           7 :     if (req->vifr_fat_flow_dst_prefix_h &&
    1089           0 :         req->vifr_fat_flow_dst_prefix_h_size) {
    1090           0 :         free(req->vifr_fat_flow_dst_prefix_h);
    1091           0 :         req->vifr_fat_flow_dst_prefix_h = NULL;
    1092           0 :         req->vifr_fat_flow_dst_prefix_h_size = 0;
    1093             :     }
    1094           7 :     if (req->vifr_fat_flow_dst_prefix_l &&
    1095           0 :         req->vifr_fat_flow_dst_prefix_l_size) {
    1096           0 :         free(req->vifr_fat_flow_dst_prefix_l);
    1097           0 :         req->vifr_fat_flow_dst_prefix_l = NULL;
    1098           0 :         req->vifr_fat_flow_dst_prefix_l_size = 0;
    1099             :     }
    1100           7 :     if (req->vifr_fat_flow_dst_prefix_mask &&
    1101           0 :         req->vifr_fat_flow_dst_prefix_mask_size) {
    1102           0 :         free(req->vifr_fat_flow_dst_prefix_mask);
    1103           0 :         req->vifr_fat_flow_dst_prefix_mask = NULL;
    1104           0 :         req->vifr_fat_flow_dst_prefix_mask_size = 0;
    1105             :     }
    1106           7 :     if (req->vifr_fat_flow_dst_aggregate_plen &&
    1107           0 :         req->vifr_fat_flow_dst_aggregate_plen_size) {
    1108           0 :         free(req->vifr_fat_flow_dst_aggregate_plen);
    1109           0 :         req->vifr_fat_flow_dst_aggregate_plen = NULL;
    1110           0 :         req->vifr_fat_flow_dst_aggregate_plen_size = 0;
    1111             :     }
    1112             : 
    1113           7 :     if (req->vifr_fat_flow_exclude_ip_list_size &&
    1114           0 :            req->vifr_fat_flow_exclude_ip_list) {
    1115           0 :         free(req->vifr_fat_flow_exclude_ip_list);
    1116           0 :         req->vifr_fat_flow_exclude_ip_list = NULL;
    1117           0 :         req->vifr_fat_flow_exclude_ip_list_size = 0;
    1118             :     }
    1119           7 :     if (req->vifr_fat_flow_exclude_ip6_u_list_size &&
    1120           0 :            req->vifr_fat_flow_exclude_ip6_u_list) {
    1121           0 :         free(req->vifr_fat_flow_exclude_ip6_u_list);
    1122           0 :         req->vifr_fat_flow_exclude_ip6_u_list = NULL;
    1123           0 :         req->vifr_fat_flow_exclude_ip6_u_list_size = 0;
    1124             :     }
    1125           7 :     if (req->vifr_fat_flow_exclude_ip6_l_list_size &&
    1126           0 :            req->vifr_fat_flow_exclude_ip6_l_list) {
    1127           0 :         free(req->vifr_fat_flow_exclude_ip6_l_list);
    1128           0 :         req->vifr_fat_flow_exclude_ip6_l_list = NULL;
    1129           0 :         req->vifr_fat_flow_exclude_ip6_l_list_size = 0;
    1130             :     }
    1131             : 
    1132           7 :     free(req);
    1133           7 :     return;
    1134             : }
    1135             : 
    1136             : 
    1137             : vr_interface_req *
    1138           7 : vr_interface_req_get_copy(vr_interface_req *src)
    1139             : {
    1140             :     vr_interface_req *dst;
    1141             : 
    1142           7 :     dst = malloc(sizeof(*dst));
    1143           7 :     if (!dst)
    1144           0 :         return NULL;
    1145             : 
    1146           7 :     *dst = *src;
    1147           7 :     dst->vifr_name = NULL;
    1148           7 :     dst->vifr_queue_ierrors_to_lcore_size = 0;
    1149           7 :     dst->vifr_queue_ierrors_to_lcore = NULL;
    1150           7 :     dst->vifr_mac_size = 0;
    1151           7 :     dst->vifr_mac = NULL;
    1152           7 :     dst->vifr_src_mac_size = 0;
    1153           7 :     dst->vifr_src_mac = NULL;
    1154           7 :     dst->vifr_fat_flow_protocol_port_size = 0;
    1155           7 :     dst->vifr_fat_flow_protocol_port = NULL;
    1156           7 :     dst->vifr_fat_flow_src_prefix_h = NULL;
    1157           7 :     dst->vifr_fat_flow_src_prefix_h_size = 0;
    1158           7 :     dst->vifr_fat_flow_src_prefix_l = NULL;
    1159           7 :     dst->vifr_fat_flow_src_prefix_l_size = 0;
    1160           7 :     dst->vifr_fat_flow_src_prefix_mask = NULL;
    1161           7 :     dst->vifr_fat_flow_src_prefix_mask_size = 0;
    1162           7 :     dst->vifr_fat_flow_src_aggregate_plen = NULL;
    1163           7 :     dst->vifr_fat_flow_src_aggregate_plen_size = 0;
    1164           7 :     dst->vifr_fat_flow_dst_prefix_h = NULL;
    1165           7 :     dst->vifr_fat_flow_dst_prefix_h_size = 0;
    1166           7 :     dst->vifr_fat_flow_dst_prefix_l = NULL;
    1167           7 :     dst->vifr_fat_flow_dst_prefix_l_size = 0;
    1168           7 :     dst->vifr_fat_flow_dst_prefix_mask = NULL;
    1169           7 :     dst->vifr_fat_flow_dst_prefix_mask_size = 0;
    1170           7 :     dst->vifr_fat_flow_dst_aggregate_plen = NULL;
    1171           7 :     dst->vifr_fat_flow_dst_aggregate_plen_size = 0;
    1172           7 :     dst->vifr_fat_flow_exclude_ip_list_size = 0;
    1173           7 :     dst->vifr_fat_flow_exclude_ip_list = NULL;
    1174           7 :     dst->vifr_fat_flow_exclude_ip6_u_list_size = 0;
    1175           7 :     dst->vifr_fat_flow_exclude_ip6_u_list = NULL;
    1176           7 :     dst->vifr_fat_flow_exclude_ip6_l_list_size = 0;
    1177           7 :     dst->vifr_fat_flow_exclude_ip6_l_list = NULL;
    1178             : 
    1179           7 :     if (src->vifr_name) {
    1180           7 :         dst->vifr_name = malloc(strlen(src->vifr_name) + 1);
    1181           7 :         if (!dst->vifr_name)
    1182           0 :             goto free_vif;
    1183           7 :         memcpy(dst->vifr_name, src->vifr_name, strlen(src->vifr_name) + 1);
    1184             :     }
    1185             : 
    1186           7 :     if (src->vifr_queue_ierrors_to_lcore_size &&
    1187           7 :             src->vifr_queue_ierrors_to_lcore) {
    1188           7 :         dst->vifr_queue_ierrors_to_lcore =
    1189           7 :             malloc(src->vifr_queue_ierrors_to_lcore_size * sizeof(uint64_t));
    1190           7 :         if (!dst->vifr_queue_ierrors_to_lcore)
    1191           0 :             goto free_vif;
    1192             : 
    1193           7 :         memcpy(dst->vifr_queue_ierrors_to_lcore,
    1194           7 :                 src->vifr_queue_ierrors_to_lcore,
    1195           7 :                 src->vifr_queue_ierrors_to_lcore_size);
    1196           7 :         dst->vifr_queue_ierrors_to_lcore_size =
    1197           7 :             src->vifr_queue_ierrors_to_lcore_size;
    1198             :     }
    1199             : 
    1200           7 :     if (src->vifr_mac && src->vifr_mac_size) {
    1201           7 :         dst->vifr_mac = malloc(src->vifr_mac_size);
    1202           7 :         if (!dst->vifr_mac)
    1203           0 :             goto free_vif;
    1204             : 
    1205           7 :         memcpy(dst->vifr_mac, src->vifr_mac, src->vifr_mac_size);
    1206           7 :         dst->vifr_mac_size = src->vifr_mac_size;
    1207             :     }
    1208             : 
    1209           7 :     if (src->vifr_src_mac && src->vifr_src_mac_size) {
    1210           0 :         dst->vifr_src_mac = malloc(src->vifr_src_mac_size);
    1211           0 :         if (!dst->vifr_src_mac)
    1212           0 :             goto free_vif;
    1213             : 
    1214           0 :         memcpy(dst->vifr_src_mac, src->vifr_src_mac, src->vifr_src_mac_size);
    1215           0 :         dst->vifr_src_mac_size = src->vifr_src_mac_size;
    1216             :     }
    1217             : 
    1218             : 
    1219           7 :     if (src->vifr_fat_flow_protocol_port_size &&
    1220           0 :             src->vifr_fat_flow_protocol_port) {
    1221           0 :         dst->vifr_fat_flow_protocol_port =
    1222           0 :             malloc(src->vifr_fat_flow_protocol_port_size * sizeof(uint32_t));
    1223           0 :         if (!dst->vifr_fat_flow_protocol_port)
    1224           0 :             goto free_vif;
    1225             : 
    1226           0 :         memcpy(dst->vifr_fat_flow_protocol_port,
    1227           0 :                 src->vifr_fat_flow_protocol_port,
    1228           0 :                 src->vifr_fat_flow_protocol_port_size);
    1229           0 :         dst->vifr_fat_flow_protocol_port_size =
    1230           0 :             src->vifr_fat_flow_protocol_port_size;
    1231             :     }
    1232             : 
    1233           7 :     if (src->vifr_fat_flow_src_prefix_h_size &&
    1234           0 :         src->vifr_fat_flow_src_prefix_h) {
    1235           0 :         dst->vifr_fat_flow_src_prefix_h =
    1236           0 :                    malloc(src->vifr_fat_flow_src_prefix_h_size * sizeof(uint64_t));
    1237           0 :         if (!dst->vifr_fat_flow_src_prefix_h)
    1238           0 :             goto free_vif;
    1239           0 :         memcpy(dst->vifr_fat_flow_src_prefix_h, src->vifr_fat_flow_src_prefix_h,
    1240           0 :                src->vifr_fat_flow_src_prefix_h_size);
    1241           0 :         dst->vifr_fat_flow_src_prefix_h_size = src->vifr_fat_flow_src_prefix_h_size;
    1242             :     }
    1243             : 
    1244           7 :     if (src->vifr_fat_flow_src_prefix_l_size &&
    1245           0 :         src->vifr_fat_flow_src_prefix_l) {
    1246           0 :         dst->vifr_fat_flow_src_prefix_l =
    1247           0 :                   malloc(src->vifr_fat_flow_src_prefix_l_size * sizeof(uint64_t));
    1248           0 :         if (!dst->vifr_fat_flow_src_prefix_l)
    1249           0 :             goto free_vif;
    1250           0 :         memcpy(dst->vifr_fat_flow_src_prefix_l, src->vifr_fat_flow_src_prefix_l,
    1251           0 :                src->vifr_fat_flow_src_prefix_l_size);
    1252           0 :         dst->vifr_fat_flow_src_prefix_l_size = src->vifr_fat_flow_src_prefix_l_size;
    1253             :     }
    1254           7 :     if (src->vifr_fat_flow_src_prefix_mask_size &&
    1255           0 :         src->vifr_fat_flow_src_prefix_mask) {
    1256           0 :         dst->vifr_fat_flow_src_prefix_mask =
    1257           0 :                    malloc(src->vifr_fat_flow_src_prefix_mask_size * sizeof(uint8_t));
    1258           0 :         if (!dst->vifr_fat_flow_src_prefix_mask)
    1259           0 :             goto free_vif;
    1260           0 :         memcpy(dst->vifr_fat_flow_src_prefix_mask, src->vifr_fat_flow_src_prefix_mask,
    1261           0 :                src->vifr_fat_flow_src_prefix_mask_size);
    1262           0 :         dst->vifr_fat_flow_src_prefix_mask_size = src->vifr_fat_flow_src_prefix_mask_size;
    1263             :     }
    1264           7 :     if (src->vifr_fat_flow_src_aggregate_plen_size &&
    1265           0 :         src->vifr_fat_flow_src_aggregate_plen) {
    1266           0 :         dst->vifr_fat_flow_src_aggregate_plen =
    1267           0 :                    malloc(src->vifr_fat_flow_src_aggregate_plen_size * sizeof(uint8_t));
    1268           0 :         if (!dst->vifr_fat_flow_src_aggregate_plen)
    1269           0 :             goto free_vif;
    1270           0 :         memcpy(dst->vifr_fat_flow_src_aggregate_plen, src->vifr_fat_flow_src_aggregate_plen,
    1271           0 :                src->vifr_fat_flow_src_aggregate_plen_size);
    1272           0 :         dst->vifr_fat_flow_src_aggregate_plen_size = src->vifr_fat_flow_src_aggregate_plen_size;
    1273             :     }
    1274           7 :     if (src->vifr_fat_flow_dst_prefix_h_size &&
    1275           0 :         src->vifr_fat_flow_dst_prefix_h) {
    1276           0 :         dst->vifr_fat_flow_dst_prefix_h =
    1277           0 :                 malloc(src->vifr_fat_flow_dst_prefix_h_size * sizeof(uint64_t));
    1278           0 :         if (!dst->vifr_fat_flow_dst_prefix_h)
    1279           0 :             goto free_vif;
    1280           0 :         memcpy(dst->vifr_fat_flow_dst_prefix_h, src->vifr_fat_flow_dst_prefix_h,
    1281           0 :                src->vifr_fat_flow_dst_prefix_h_size);
    1282           0 :         dst->vifr_fat_flow_dst_prefix_h_size = src->vifr_fat_flow_dst_prefix_h_size;
    1283             :     }
    1284           7 :     if (src->vifr_fat_flow_dst_prefix_l_size &&
    1285           0 :         src->vifr_fat_flow_dst_prefix_l) {
    1286           0 :         dst->vifr_fat_flow_dst_prefix_l =
    1287           0 :                  malloc(src->vifr_fat_flow_dst_prefix_l_size * sizeof(uint64_t));
    1288           0 :         if (!dst->vifr_fat_flow_dst_prefix_l)
    1289           0 :             goto free_vif;
    1290           0 :         memcpy(dst->vifr_fat_flow_dst_prefix_l, src->vifr_fat_flow_dst_prefix_l,
    1291           0 :                src->vifr_fat_flow_dst_prefix_l_size);
    1292           0 :         dst->vifr_fat_flow_dst_prefix_l_size = src->vifr_fat_flow_dst_prefix_l_size;
    1293             :     }
    1294           7 :     if (src->vifr_fat_flow_dst_prefix_mask_size &&
    1295           0 :         src->vifr_fat_flow_dst_prefix_mask) {
    1296           0 :         dst->vifr_fat_flow_dst_prefix_mask =
    1297           0 :                  malloc(src->vifr_fat_flow_dst_prefix_mask_size * sizeof(uint8_t));
    1298           0 :         if (!dst->vifr_fat_flow_dst_prefix_mask)
    1299           0 :             goto free_vif;
    1300           0 :         memcpy(dst->vifr_fat_flow_dst_prefix_mask, src->vifr_fat_flow_dst_prefix_mask,
    1301           0 :                src->vifr_fat_flow_dst_prefix_mask_size);
    1302           0 :         dst->vifr_fat_flow_dst_prefix_mask_size = src->vifr_fat_flow_dst_prefix_mask_size;
    1303             :     }
    1304           7 :     if (src->vifr_fat_flow_dst_aggregate_plen_size &&
    1305           0 :         src->vifr_fat_flow_dst_aggregate_plen) {
    1306           0 :         dst->vifr_fat_flow_dst_aggregate_plen =
    1307           0 :                   malloc(src->vifr_fat_flow_dst_aggregate_plen_size * sizeof(uint8_t));
    1308           0 :         if (!dst->vifr_fat_flow_dst_aggregate_plen)
    1309           0 :             goto free_vif;
    1310           0 :         memcpy(dst->vifr_fat_flow_dst_aggregate_plen, src->vifr_fat_flow_dst_aggregate_plen,
    1311           0 :                src->vifr_fat_flow_dst_aggregate_plen_size);
    1312           0 :         dst->vifr_fat_flow_dst_aggregate_plen_size = src->vifr_fat_flow_dst_aggregate_plen_size;
    1313             :     }
    1314             : 
    1315           7 :     if (src->vifr_fat_flow_exclude_ip_list_size &&
    1316           0 :              src->vifr_fat_flow_exclude_ip_list) {
    1317           0 :         dst->vifr_fat_flow_exclude_ip_list = malloc(src->vifr_fat_flow_exclude_ip_list_size * sizeof(uint64_t));
    1318           0 :         if (!dst->vifr_fat_flow_exclude_ip_list) {
    1319           0 :             goto free_vif;
    1320             :         }
    1321           0 :         memcpy(dst->vifr_fat_flow_exclude_ip_list, src->vifr_fat_flow_exclude_ip_list,
    1322           0 :                src->vifr_fat_flow_exclude_ip_list_size * sizeof(uint64_t));
    1323           0 :         dst->vifr_fat_flow_exclude_ip_list_size = src->vifr_fat_flow_exclude_ip_list_size;
    1324             :     }
    1325             : 
    1326           7 :     if (src->vifr_fat_flow_exclude_ip6_u_list_size &&
    1327           0 :             src->vifr_fat_flow_exclude_ip6_u_list) {
    1328           0 :         dst->vifr_fat_flow_exclude_ip6_u_list = malloc(src->vifr_fat_flow_exclude_ip6_u_list_size * sizeof(uint64_t));
    1329           0 :         if (!dst->vifr_fat_flow_exclude_ip6_u_list) {
    1330           0 :             goto free_vif;
    1331             :         }
    1332           0 :         memcpy(dst->vifr_fat_flow_exclude_ip6_u_list, src->vifr_fat_flow_exclude_ip6_u_list,
    1333           0 :                src->vifr_fat_flow_exclude_ip6_u_list_size * sizeof(uint64_t));
    1334           0 :         dst->vifr_fat_flow_exclude_ip6_u_list_size = src->vifr_fat_flow_exclude_ip6_u_list_size;
    1335             :     }
    1336           7 :     if (src->vifr_fat_flow_exclude_ip6_l_list_size &&
    1337           0 :             src->vifr_fat_flow_exclude_ip6_l_list) {
    1338           0 :         dst->vifr_fat_flow_exclude_ip6_l_list = malloc(src->vifr_fat_flow_exclude_ip6_l_list_size * sizeof(uint64_t));
    1339           0 :         if (!dst->vifr_fat_flow_exclude_ip6_l_list) {
    1340           0 :             goto free_vif;
    1341             :         }
    1342           0 :         memcpy(dst->vifr_fat_flow_exclude_ip6_l_list, src->vifr_fat_flow_exclude_ip6_l_list,
    1343           0 :                src->vifr_fat_flow_exclude_ip6_l_list_size * sizeof(uint64_t));
    1344           0 :         dst->vifr_fat_flow_exclude_ip6_l_list_size = src->vifr_fat_flow_exclude_ip6_l_list_size;
    1345             :     }
    1346             : 
    1347           7 :     return dst;
    1348             : 
    1349           0 : free_vif:
    1350           0 :     vr_interface_req_destroy(dst);
    1351           0 :     dst = NULL;
    1352           0 :     return NULL;
    1353             : }
    1354             : 
    1355             : int
    1356           0 : vr_send_interface_dump(struct nl_client *cl, unsigned int router_id,
    1357             :         int marker, int core)
    1358             : {
    1359             :     vr_interface_req req;
    1360             : 
    1361           0 :     memset(&req, 0, sizeof(req));
    1362           0 :     req.h_op = SANDESH_OP_DUMP;
    1363           0 :     req.vifr_rid = router_id;
    1364           0 :     req.vifr_marker = marker;
    1365           0 :     req.vifr_core = core;
    1366           0 :     return vr_sendmsg(cl, &req, "vr_interface_req");
    1367             : }
    1368             : 
    1369             : int
    1370          10 : vr_send_interface_get(struct nl_client *cl, unsigned int router_id,
    1371             :         int vif_index, int os_index, int core, int get_drops)
    1372             : {
    1373             :     vr_interface_req req;
    1374             : 
    1375          10 :     memset(&req, 0, sizeof(req));
    1376             : 
    1377          10 :     req.h_op = SANDESH_OP_GET;
    1378          10 :     req.vifr_rid = router_id;
    1379          10 :     req.vifr_os_idx = os_index;
    1380          10 :     req.vifr_idx = vif_index;
    1381          10 :     req.vifr_core = core;
    1382          10 :     if (get_drops)
    1383           0 :         req.vifr_flags |= VIF_FLAG_GET_DROP_STATS;
    1384             : 
    1385          10 :     return vr_sendmsg(cl, &req, "vr_interface_req");
    1386             : }
    1387             : 
    1388             : int
    1389           8 : vr_send_interface_delete(struct nl_client *cl, unsigned int router_id,
    1390             :         char *vif_name, int vif_index)
    1391             : {
    1392             :     vr_interface_req req;
    1393             : 
    1394           8 :     memset(&req, 0, sizeof(req));
    1395             : 
    1396           8 :     req.h_op = SANDESH_OP_DEL;
    1397           8 :     req.vifr_rid = router_id;
    1398           8 :     req.vifr_name = vif_name;
    1399           8 :     req.vifr_idx = vif_index;
    1400             : 
    1401           8 :     return vr_sendmsg(cl, &req, "vr_interface_req");
    1402             : }
    1403             : 
    1404             : int
    1405           0 : vr_send_interface_add(struct nl_client *cl, int router_id, char *vif_name,
    1406             :         int os_index, int vif_index, int *vif_xconnect_index, int vif_type,
    1407             :         unsigned int vrf, unsigned int flags, int8_t *vif_mac, int8_t vif_transport,
    1408             :         const char *guid)
    1409             : {
    1410           0 :     int platform, i = 0;
    1411             :     vr_interface_req req;
    1412             : 
    1413           0 :     platform = get_platform();
    1414           0 :     memset(&req, 0, sizeof(req));
    1415             : 
    1416           0 :     req.h_op = SANDESH_OP_ADD;
    1417           0 :     if (vif_name)
    1418           0 :         req.vifr_name = vif_name;
    1419           0 :     if (vif_mac) {
    1420           0 :         req.vifr_mac_size = 6;
    1421           0 :         req.vifr_mac = vif_mac;
    1422             :     }
    1423           0 :     req.vifr_vrf = vrf;
    1424           0 :     req.vifr_mcast_vrf = (uint16_t)(-1);
    1425             : 
    1426           0 :     if (os_index > 0)
    1427           0 :         req.vifr_os_idx = os_index;
    1428             : 
    1429           0 :     req.vifr_idx = vif_index;
    1430           0 :     req.vifr_rid = router_id;
    1431           0 :     req.vifr_type = vif_type;
    1432           0 :     req.vifr_flags = flags;
    1433           0 :     req.vifr_transport = vif_transport;
    1434             : 
    1435           0 :     if (vif_type == VIF_TYPE_HOST) {
    1436           0 :         for(i = 0; i < VR_MAX_PHY_INF; i++) {
    1437           0 :             if(vif_xconnect_index[i] < 0) {
    1438           0 :                 break;
    1439             :             }
    1440             :         }
    1441           0 :         req.vifr_cross_connect_idx_size = i;
    1442           0 :         req.vifr_cross_connect_idx = vif_xconnect_index;
    1443             :     }
    1444             : 
    1445           0 :     return vr_sendmsg(cl, &req, "vr_interface_req");
    1446             : }
    1447             : 
    1448             : int
    1449           1 : vr_send_vif_clear_stats(struct nl_client *cl, unsigned int router_id,
    1450             :         int vif_idx, int core)
    1451             : {
    1452             :     vr_interface_req req;
    1453             : 
    1454           1 :     memset(&req, 0, sizeof(req));
    1455           1 :     req.h_op = SANDESH_OP_RESET;
    1456           1 :     req.vifr_rid = router_id;
    1457           1 :     req.vifr_idx = vif_idx;
    1458           1 :     req.vifr_core = core + 1;
    1459             : 
    1460           1 :     return vr_sendmsg(cl, &req, "vr_interface_req");
    1461             : }
    1462             : 
    1463             : /* interface end */
    1464             : 
    1465             : 
    1466             : int
    1467           0 : vr_send_mem_stats_get(struct nl_client *cl, unsigned int router_id)
    1468             : {
    1469             :     vr_mem_stats_req req;
    1470             : 
    1471           0 :     memset(&req, 0, sizeof(req));
    1472           0 :     req.h_op = SANDESH_OP_GET;
    1473           0 :     req.vms_rid = router_id;
    1474             : 
    1475           0 :     return vr_sendmsg(cl, &req, "vr_mem_stats_req");
    1476             : }
    1477             : 
    1478             : /* mirror start */
    1479             : void
    1480           0 : vr_mirror_req_destroy(vr_mirror_req *req)
    1481             : {
    1482           0 :     if (!req)
    1483           0 :         return;
    1484             : 
    1485           0 :     free(req);
    1486             : 
    1487           0 :     return;
    1488             : }
    1489             : 
    1490             : vr_mirror_req *
    1491           0 : vr_mirror_req_get_copy(vr_mirror_req *req)
    1492             : {
    1493             :     vr_mirror_req *dst;
    1494             : 
    1495           0 :     if (!req)
    1496           0 :         return NULL;
    1497             : 
    1498           0 :     dst = malloc(sizeof(*req));
    1499           0 :     if (!dst)
    1500           0 :         return NULL;
    1501             : 
    1502           0 :     *dst = *req;
    1503             : 
    1504           0 :     return dst;
    1505             : }
    1506             : 
    1507             : int
    1508           0 : vr_send_mirror_dump(struct nl_client *cl, unsigned int router_id,
    1509             :         int marker)
    1510             : {
    1511             :     vr_mirror_req req;
    1512             : 
    1513           0 :     req.h_op = SANDESH_OP_DUMP;
    1514           0 :     req.mirr_rid = router_id;
    1515           0 :     req.mirr_marker = marker;
    1516             : 
    1517           0 :     return vr_sendmsg(cl, &req, "vr_mirror_req");
    1518             : }
    1519             : 
    1520             : int
    1521           0 : vr_send_mirror_get(struct nl_client *cl, unsigned int router_id,
    1522             :         unsigned int mirror_index)
    1523             : {
    1524             :     vr_mirror_req req;
    1525             : 
    1526           0 :     req.h_op = SANDESH_OP_GET;
    1527           0 :     req.mirr_rid = router_id;
    1528           0 :     req.mirr_index = mirror_index;
    1529             : 
    1530           0 :     return vr_sendmsg(cl, &req, "vr_mirror_req");
    1531             : }
    1532             : 
    1533             : int
    1534           0 : vr_send_mirror_delete(struct nl_client *cl, unsigned int router_id,
    1535             :         unsigned int mirror_index)
    1536             : {
    1537             :     vr_mirror_req req;
    1538             : 
    1539           0 :     req.h_op = SANDESH_OP_DEL;
    1540           0 :     req.mirr_rid = router_id;
    1541           0 :     req.mirr_index = mirror_index;
    1542             : 
    1543           0 :     return vr_sendmsg(cl, &req, "vr_mirror_req");
    1544             : }
    1545             : 
    1546             : int
    1547           0 : vr_send_mirror_add(struct nl_client *cl, unsigned int router_id,
    1548             :         unsigned int mirror_index, int mirror_nh_index,
    1549             :         unsigned int mirror_flags, int vni_id)
    1550             : {
    1551             :     vr_mirror_req req;
    1552             : 
    1553           0 :     memset(&req, 0, sizeof(req));
    1554             : 
    1555           0 :     req.h_op = SANDESH_OP_ADD;
    1556           0 :     req.mirr_rid = router_id;
    1557           0 :     req.mirr_index = mirror_index;
    1558           0 :     req.mirr_nhid = mirror_nh_index;
    1559           0 :     req.mirr_flags = mirror_flags;
    1560           0 :     req.mirr_vni = vni_id;
    1561             : 
    1562           0 :     return vr_sendmsg(cl, &req, "vr_mirror_req");
    1563             : }
    1564             : /* mirror end */
    1565             : 
    1566             : int
    1567           0 : vr_send_vrf_dump(struct nl_client *cl, unsigned int router_id,
    1568             :         int marker)
    1569             : {
    1570             :     vr_vrf_req req;
    1571             : 
    1572           0 :     req.h_op = SANDESH_OP_DUMP;
    1573           0 :     req.vrf_rid = router_id;
    1574           0 :     req.vrf_marker = marker;
    1575             : 
    1576           0 :     return vr_sendmsg(cl, &req, "vr_vrf_req");
    1577             : }
    1578             : 
    1579             : int
    1580           0 : vr_send_vrf_get(struct nl_client *cl, unsigned int router_id,
    1581             :         unsigned int vrf_index)
    1582             : {
    1583             :     vr_vrf_req req;
    1584             : 
    1585           0 :     req.h_op = SANDESH_OP_GET;
    1586           0 :     req.vrf_rid = router_id;
    1587           0 :     req.vrf_idx = vrf_index;
    1588             : 
    1589           0 :     return vr_sendmsg(cl, &req, "vr_vrf_req");
    1590             : }
    1591             : 
    1592             : int
    1593           0 : vr_send_vrf_delete(struct nl_client *cl, unsigned int router_id,
    1594             :         unsigned int vrf_index)
    1595             : {
    1596             :     vr_vrf_req req;
    1597             : 
    1598           0 :     req.h_op = SANDESH_OP_DEL;
    1599           0 :     req.vrf_rid = router_id;
    1600           0 :     req.vrf_idx = vrf_index;
    1601             : 
    1602           0 :     return vr_sendmsg(cl, &req, "vr_vrf_req");
    1603             : }
    1604             : 
    1605             : int
    1606           0 : vr_send_vrf_add(struct nl_client *cl, unsigned int router_id,
    1607             :         unsigned int vrf_index, int hbfl_idx, int hbfr_idx,
    1608             :         unsigned int vrf_flags)
    1609             : {
    1610             :     vr_vrf_req req;
    1611             : 
    1612           0 :     memset(&req, 0, sizeof(req));
    1613             : 
    1614           0 :     req.h_op = SANDESH_OP_ADD;
    1615           0 :     req.vrf_rid = router_id;
    1616           0 :     req.vrf_idx = vrf_index;
    1617           0 :     req.vrf_flags = vrf_flags;
    1618           0 :     req.vrf_hbfl_vif_idx = hbfl_idx;
    1619           0 :     req.vrf_hbfr_vif_idx = hbfr_idx;
    1620             : 
    1621           0 :     return vr_sendmsg(cl, &req, "vr_vrf_req");
    1622             : }
    1623             : 
    1624             : int
    1625           0 : vr_send_mpls_delete(struct nl_client *cl, unsigned int router_id,
    1626             :         unsigned int label)
    1627             : {
    1628             :     vr_mpls_req req;
    1629             : 
    1630           0 :     memset(&req, 0, sizeof(req));
    1631           0 :     req.h_op = SANDESH_OP_DEL;
    1632           0 :     req.mr_rid = router_id;
    1633           0 :     req.mr_label = label;
    1634             : 
    1635           0 :     return vr_sendmsg(cl, &req, "vr_mpls_req");
    1636             : }
    1637             : 
    1638             : int
    1639           0 : vr_send_mpls_dump(struct nl_client *cl, unsigned int router_id, int marker)
    1640             : {
    1641             :     vr_mpls_req req;
    1642             : 
    1643           0 :     memset(&req, 0, sizeof(req));
    1644           0 :     req.h_op = SANDESH_OP_DUMP;
    1645           0 :     req.mr_rid = router_id;
    1646           0 :     req.mr_marker = marker;
    1647             : 
    1648           0 :     return vr_sendmsg(cl, &req, "vr_mpls_req");
    1649             : }
    1650             : 
    1651             : int
    1652           0 : vr_send_mpls_get(struct nl_client *cl, unsigned int router_id, unsigned int label)
    1653             : {
    1654             :     vr_mpls_req req;
    1655             : 
    1656           0 :     memset(&req, 0, sizeof(req));
    1657           0 :     req.h_op = SANDESH_OP_GET;
    1658           0 :     req.mr_rid = router_id;
    1659           0 :     req.mr_label = label;
    1660             : 
    1661           0 :     return vr_sendmsg(cl, &req, "vr_mpls_req");
    1662             : }
    1663             : 
    1664             : int
    1665           0 : vr_send_mpls_add(struct nl_client *cl, unsigned int router_id,
    1666             :         unsigned int label, unsigned int nh_index)
    1667             : {
    1668             :     vr_mpls_req req;
    1669             : 
    1670           0 :     memset(&req, 0, sizeof(req));
    1671           0 :     req.h_op = SANDESH_OP_ADD;
    1672           0 :     req.mr_rid = router_id;
    1673           0 :     req.mr_label = label;
    1674           0 :     req.mr_nhid = nh_index;
    1675             : 
    1676           0 :     return vr_sendmsg(cl, &req, "vr_mpls_req");
    1677             : }
    1678             : 
    1679             : char *
    1680           7 : vr_nexthop_type_string(vr_nexthop_req *nh)
    1681             : {
    1682           7 :     switch (nh->nhr_type) {
    1683           0 :     case NH_DEAD:
    1684           0 :         return "DEAD";
    1685             :         break;
    1686             : 
    1687           0 :     case NH_RCV:
    1688           0 :         return "RECEIVE";
    1689             :         break;
    1690             : 
    1691           7 :     case NH_ENCAP:
    1692           7 :         return "ENCAP";
    1693             :         break;
    1694             : 
    1695           0 :     case NH_TUNNEL:
    1696           0 :         return "TUNNEL";
    1697             :         break;
    1698             : 
    1699           0 :     case NH_RESOLVE:
    1700           0 :         return "RESOLVE";
    1701             :         break;
    1702             : 
    1703           0 :     case NH_DISCARD:
    1704           0 :         return "DISCARD";
    1705             :         break;
    1706             : 
    1707           0 :     case NH_COMPOSITE:
    1708           0 :         return "COMPOSITE";
    1709             :         break;
    1710             : 
    1711           0 :     case NH_VRF_TRANSLATE:
    1712           0 :         return "VRF_TRANSLATE";
    1713             :         break;
    1714             : 
    1715           0 :     case NH_L2_RCV:
    1716           0 :         return "L2_RECEIVE";
    1717             :         break;
    1718             : 
    1719           0 :      default:
    1720           0 :         return "NONE";
    1721             :     }
    1722             : 
    1723             :     return "NONE";
    1724             : }
    1725             : 
    1726             : 
    1727             : bool
    1728          10 : vr_nexthop_req_has_vif(vr_nexthop_req *req)
    1729             : {
    1730          10 :     switch (req->nhr_type) {
    1731           2 :     case NH_ENCAP:
    1732             :     case NH_TUNNEL:
    1733             :     case NH_RCV:
    1734             :     case NH_L2_RCV:
    1735           2 :         return true;
    1736             :         break;
    1737             : 
    1738           8 :     case NH_COMPOSITE:
    1739             :     default:
    1740           8 :         return false;
    1741             :         break;
    1742             :     }
    1743             : 
    1744             :     return false;
    1745             : }
    1746             : 
    1747             : void
    1748         115 : vr_nexthop_req_destroy(vr_nexthop_req *req)
    1749             : {
    1750         115 :     if (!req)
    1751         100 :         return;
    1752             : 
    1753          15 :     if (req->nhr_encap_size && req->nhr_encap) {
    1754           7 :         free(req->nhr_encap);
    1755           7 :         req->nhr_encap = NULL;
    1756           7 :         req->nhr_encap_size = 0;
    1757           7 :         req->nhr_encap_len = 0;
    1758             :     }
    1759             : 
    1760          15 :     if (req->nhr_nh_list_size && req->nhr_nh_list) {
    1761           0 :         free(req->nhr_nh_list);
    1762           0 :         req->nhr_nh_list = NULL;
    1763           0 :         req->nhr_nh_list_size = 0;
    1764             :     }
    1765             : 
    1766          15 :     if (req->nhr_label_list_size && req->nhr_label_list) {
    1767           0 :         free(req->nhr_label_list);
    1768           0 :         req->nhr_label_list = NULL;
    1769           0 :         req->nhr_label_list_size = 0;
    1770             :     }
    1771             : 
    1772          15 :     if (req->nhr_tun_sip6_size && req->nhr_tun_sip6) {
    1773           0 :         free(req->nhr_tun_sip6);
    1774           0 :         req->nhr_tun_sip6 = NULL;
    1775           0 :         req->nhr_tun_sip6_size = 0;
    1776             :     }
    1777             : 
    1778          15 :     if (req->nhr_tun_dip6_size && req->nhr_tun_dip6) {
    1779           0 :         free(req->nhr_tun_dip6);
    1780           0 :         req->nhr_tun_dip6 = NULL;
    1781           0 :         req->nhr_tun_dip6_size = 0;
    1782             :     }
    1783             : 
    1784          15 :     if (req->nhr_encap_oif_id_size && req->nhr_encap_oif_id) {
    1785          15 :         free(req->nhr_encap_oif_id);
    1786          15 :         req->nhr_encap_oif_id = NULL;
    1787          15 :         req->nhr_encap_oif_id_size = 0;
    1788             :     }
    1789             : 
    1790          15 :     if (req->nhr_encap_valid_size && req->nhr_encap_valid) {
    1791           0 :         free(req->nhr_encap_valid);
    1792           0 :         req->nhr_encap_valid = NULL;
    1793           0 :         req->nhr_encap_valid_size = 0;
    1794             :     }
    1795             : 
    1796          15 :     free(req);
    1797             : 
    1798          15 :     return;
    1799             : }
    1800             : 
    1801             : vr_nexthop_req *
    1802          15 : vr_nexthop_req_get_copy(vr_nexthop_req *src)
    1803             : {
    1804             :     vr_nexthop_req *dst;
    1805             : 
    1806          15 :     dst = calloc(sizeof(vr_nexthop_req), 1);
    1807          15 :     if (!dst)
    1808           0 :         return NULL;
    1809             : 
    1810             :     /* first copy the in-built members */
    1811          15 :     *dst = *src;
    1812             : 
    1813          15 :     dst->nhr_encap = NULL;
    1814          15 :     dst->nhr_encap_size = 0;
    1815          15 :     dst->nhr_nh_list = NULL;
    1816          15 :     dst->nhr_nh_list_size = 0;
    1817          15 :     dst->nhr_label_list = NULL;
    1818          15 :     dst->nhr_label_list_size = 0;
    1819          15 :     dst->nhr_tun_sip6 = NULL;
    1820          15 :     dst->nhr_tun_sip6_size = 0;
    1821          15 :     dst->nhr_tun_dip6 = NULL;
    1822          15 :     dst->nhr_tun_dip6_size = 0;
    1823          15 :     dst->nhr_encap_oif_id = NULL;
    1824          15 :     dst->nhr_encap_oif_id_size = 0;
    1825          15 :     dst->nhr_encap_valid = NULL;
    1826          15 :     dst->nhr_encap_valid_size = 0;
    1827             : 
    1828             :     /* ...and then the list elements */
    1829          15 :     if (src->nhr_encap_size && src->nhr_encap) {
    1830           7 :         dst->nhr_encap = malloc(src->nhr_encap_size);
    1831           7 :         if (!dst->nhr_encap)
    1832           0 :             goto free_nh;
    1833           7 :         memcpy(dst->nhr_encap, src->nhr_encap, src->nhr_encap_size);
    1834           7 :         dst->nhr_encap_size = src->nhr_encap_size;
    1835             :     }
    1836             : 
    1837             :     /* component nexthop list */
    1838          15 :     if (src->nhr_nh_list_size && src->nhr_nh_list) {
    1839           0 :         dst->nhr_nh_list = malloc(src->nhr_nh_list_size * sizeof(uint32_t));
    1840           0 :         if (!src->nhr_nh_list)
    1841           0 :             goto free_nh;
    1842           0 :         memcpy(dst->nhr_nh_list, src->nhr_nh_list,
    1843           0 :                 src->nhr_nh_list_size * sizeof(uint32_t));
    1844           0 :         dst->nhr_nh_list_size = src->nhr_nh_list_size;
    1845             :     }
    1846             : 
    1847             :     /* label list */
    1848          15 :     if (src->nhr_label_list_size && src->nhr_label_list) {
    1849           0 :         dst->nhr_label_list = malloc(src->nhr_label_list_size * sizeof(uint32_t));
    1850           0 :         if (!src->nhr_label_list)
    1851           0 :             goto free_nh;
    1852           0 :         memcpy(dst->nhr_label_list, src->nhr_label_list,
    1853           0 :                 src->nhr_label_list_size * sizeof(uint32_t));
    1854           0 :         dst->nhr_label_list_size = src->nhr_label_list_size;
    1855             :     }
    1856             : 
    1857             :     /* ipv6 tunnel source */
    1858          15 :     if (src->nhr_tun_sip6_size && src->nhr_tun_sip6) {
    1859           0 :         dst->nhr_tun_sip6 = malloc(src->nhr_tun_sip6_size);
    1860           0 :         if (!src->nhr_tun_sip6)
    1861           0 :             goto free_nh;
    1862           0 :         memcpy(dst->nhr_tun_sip6, src->nhr_tun_sip6, src->nhr_tun_sip6_size);
    1863           0 :         dst->nhr_tun_sip6_size = src->nhr_tun_sip6_size;
    1864             :     }
    1865             : 
    1866             :     /* ipv6 tunnel destination */
    1867          15 :     if (src->nhr_tun_dip6_size && src->nhr_tun_dip6) {
    1868           0 :         dst->nhr_tun_dip6 = malloc(src->nhr_tun_dip6_size);
    1869           0 :         if (!src->nhr_tun_dip6)
    1870           0 :             goto free_nh;
    1871           0 :         memcpy(dst->nhr_tun_dip6, src->nhr_tun_dip6, src->nhr_tun_dip6_size);
    1872           0 :         dst->nhr_tun_dip6_size = src->nhr_tun_dip6_size;
    1873             :     }
    1874             : 
    1875             :     /* encap oif id list */
    1876          15 :     if (src->nhr_encap_oif_id_size && src->nhr_encap_oif_id) {
    1877          15 :         dst->nhr_encap_oif_id = malloc(src->nhr_encap_oif_id_size * sizeof(int32_t));
    1878          15 :         if (!src->nhr_encap_oif_id)
    1879           0 :             goto free_nh;
    1880          15 :         memcpy(dst->nhr_encap_oif_id, src->nhr_encap_oif_id,
    1881          15 :                 src->nhr_encap_oif_id_size * sizeof(int32_t));
    1882          15 :         dst->nhr_encap_oif_id_size = src->nhr_encap_oif_id_size;
    1883             :     }
    1884             : 
    1885             :     /* encap valid list */
    1886          15 :     if (src->nhr_encap_valid_size && src->nhr_encap_valid &&
    1887           0 :             (src->nhr_flags & NH_FLAG_TUNNEL_UNDERLAY_ECMP)) {
    1888           0 :         dst->nhr_encap_valid = malloc(src->nhr_encap_valid_size * sizeof(int32_t));
    1889           0 :         if (!src->nhr_encap_valid)
    1890           0 :             goto free_nh;
    1891           0 :         memcpy(dst->nhr_encap_valid, src->nhr_encap_valid,
    1892           0 :                 src->nhr_encap_valid_size * sizeof(int32_t));
    1893           0 :         dst->nhr_encap_valid_size = src->nhr_encap_valid_size;
    1894             :     }
    1895             : 
    1896          15 :     return dst;
    1897             : 
    1898           0 : free_nh:
    1899           0 :     vr_nexthop_req_destroy(dst);
    1900           0 :     return NULL;
    1901             : }
    1902             : 
    1903             : int
    1904           0 : vr_send_nexthop_delete(struct nl_client *cl, unsigned int router_id,
    1905             :         unsigned int nh_index)
    1906             : {
    1907             :     vr_nexthop_req req;
    1908             : 
    1909           0 :     memset(&req, 0, sizeof(req));
    1910           0 :     req.h_op = SANDESH_OP_DEL;
    1911           0 :     req.nhr_rid = router_id;
    1912           0 :     req.nhr_id = nh_index;
    1913             : 
    1914           0 :     return vr_sendmsg(cl, &req, "vr_nexthop_req");
    1915             : }
    1916             : 
    1917             : int
    1918           0 : vr_send_nexthop_dump(struct nl_client *cl, unsigned int router_id,
    1919             :         int marker)
    1920             : {
    1921             :     vr_nexthop_req req;
    1922             : 
    1923           0 :     memset(&req, 0, sizeof(req));
    1924           0 :     req.h_op = SANDESH_OP_DUMP;
    1925           0 :     req.nhr_rid = router_id;
    1926           0 :     req.nhr_marker = marker;
    1927             : 
    1928           0 :     return vr_sendmsg(cl, &req, "vr_nexthop_req");
    1929             : }
    1930             : 
    1931             : int
    1932          19 : vr_send_nexthop_get(struct nl_client *cl, unsigned int router_id,
    1933             :         unsigned int nh_index)
    1934             : {
    1935             :     vr_nexthop_req req;
    1936             : 
    1937          19 :     memset(&req, 0, sizeof(req));
    1938          19 :     req.h_op = SANDESH_OP_GET;
    1939          19 :     req.nhr_rid = router_id;
    1940          19 :     req.nhr_id = nh_index;
    1941             : 
    1942          19 :     return vr_sendmsg(cl, &req, "vr_nexthop_req");
    1943             : }
    1944             : 
    1945             : int
    1946           0 : vr_send_pbb_tunnel_add(struct nl_client *cl, unsigned int router_id, int
    1947             :         nh_index, unsigned int flags, int vrf_index, int8_t *bmac,
    1948             :         unsigned int direct_nh_id, unsigned int direct_label)
    1949             : {
    1950           0 :     int ret = 0;
    1951             :     unsigned int i;
    1952             :     vr_nexthop_req req;
    1953             : 
    1954           0 :     memset(&req, 0, sizeof(req));
    1955           0 :     req.h_op = SANDESH_OP_ADD;
    1956           0 :     req.nhr_rid = router_id;
    1957           0 :     req.nhr_vrf = vrf_index;
    1958           0 :     req.nhr_id = nh_index;
    1959           0 :     req.nhr_flags = flags;
    1960           0 :     req.nhr_type = NH_TUNNEL;
    1961             : 
    1962           0 :     req.nhr_encap_oif_id_size = 1;
    1963           0 :     req.nhr_encap_oif_id = calloc(req.nhr_encap_oif_id_size, sizeof(unsigned int));
    1964           0 :     if (!req.nhr_encap_oif_id) {
    1965           0 :         ret = -ENOMEM;
    1966           0 :         goto fail;
    1967             :     }
    1968           0 :     req.nhr_encap_oif_id[0] = 0;
    1969             : 
    1970           0 :     req.nhr_nh_list_size = 1;
    1971           0 :     req.nhr_nh_list = calloc(1, sizeof(uint32_t));
    1972           0 :     if (!req.nhr_nh_list) {
    1973           0 :         ret = -ENOMEM;
    1974           0 :         goto fail;
    1975             :     }
    1976             : 
    1977           0 :     req.nhr_label_list = calloc(1, sizeof(uint32_t));
    1978           0 :     if (!req.nhr_label_list) {
    1979           0 :         ret = -ENOMEM;
    1980           0 :         goto fail;
    1981             :     }
    1982             : 
    1983           0 :     req.nhr_pbb_mac_size = VR_ETHER_ALEN;
    1984           0 :     req.nhr_pbb_mac = calloc(VR_ETHER_ALEN, sizeof(uint8_t));
    1985           0 :     if (!req.nhr_pbb_mac) {
    1986           0 :         ret = -ENOMEM;
    1987           0 :         goto fail;
    1988             :     }
    1989           0 :     VR_MAC_COPY(req.nhr_pbb_mac, bmac);
    1990             : 
    1991           0 :     req.nhr_label_list_size = 1;
    1992           0 :     req.nhr_nh_list[0] = direct_nh_id;
    1993           0 :     req.nhr_label_list[0] = direct_label;
    1994           0 :     req.nhr_family = AF_BRIDGE;
    1995             : 
    1996           0 :     ret = vr_sendmsg(cl, &req, "vr_nexthop_req");
    1997           0 : fail:
    1998           0 :     if (req.nhr_nh_list) {
    1999           0 :         free(req.nhr_nh_list);
    2000           0 :         req.nhr_nh_list = NULL;
    2001             :     }
    2002             : 
    2003           0 :     if (req.nhr_label_list) {
    2004           0 :         free(req.nhr_label_list);
    2005           0 :         req.nhr_label_list = NULL;
    2006             :     }
    2007             : 
    2008           0 :     return ret;
    2009             : }
    2010             : 
    2011             : int
    2012           0 : vr_send_nexthop_composite_add(struct nl_client *cl, unsigned int router_id,
    2013             :         int nh_index, unsigned int flags, int vrf_index,
    2014             :         unsigned int num_components, unsigned int *component_nh_indices,
    2015             :         unsigned int *component_labels, unsigned int family)
    2016             : {
    2017           0 :     int ret = 0;
    2018             :     unsigned int i;
    2019             :     vr_nexthop_req req;
    2020             : 
    2021           0 :     memset(&req, 0, sizeof(req));
    2022           0 :     req.h_op = SANDESH_OP_ADD;
    2023           0 :     req.nhr_rid = router_id;
    2024           0 :     req.nhr_vrf = vrf_index;
    2025           0 :     req.nhr_id = nh_index;
    2026           0 :     req.nhr_flags = flags;
    2027           0 :     req.nhr_type = NH_COMPOSITE;
    2028             : 
    2029           0 :     req.nhr_nh_list_size = num_components;
    2030           0 :     req.nhr_nh_list = calloc(num_components, sizeof(uint32_t));
    2031           0 :     if (!req.nhr_nh_list) {
    2032           0 :         ret = -ENOMEM;
    2033           0 :         goto fail;
    2034             :     }
    2035             : 
    2036           0 :     req.nhr_label_list = calloc(num_components, sizeof(uint32_t));
    2037           0 :     if (!req.nhr_label_list) {
    2038           0 :         ret = -ENOMEM;
    2039           0 :         goto fail;
    2040             :     }
    2041             : 
    2042           0 :     req.nhr_label_list_size = num_components;
    2043           0 :     for (i = 0; i < num_components; i++) {
    2044           0 :         req.nhr_nh_list[i] = component_nh_indices[i];
    2045           0 :         req.nhr_label_list[i] = component_labels[i];
    2046             :     }
    2047             : 
    2048             : 
    2049           0 :     req.nhr_family = family;
    2050             : 
    2051           0 :     ret = vr_sendmsg(cl, &req, "vr_nexthop_req");
    2052           0 : fail:
    2053           0 :     if (req.nhr_nh_list) {
    2054           0 :         free(req.nhr_nh_list);
    2055           0 :         req.nhr_nh_list = NULL;
    2056             :     }
    2057             : 
    2058           0 :     if (req.nhr_label_list) {
    2059           0 :         free(req.nhr_label_list);
    2060           0 :         req.nhr_label_list = NULL;
    2061             :     }
    2062             : 
    2063           0 :     return ret;
    2064             : }
    2065             : 
    2066             : 
    2067             : int
    2068           0 : vr_send_nexthop_encap_tunnel_add(struct nl_client *cl, unsigned int router_id,
    2069             :         unsigned int type, int nh_index, unsigned int flags, int vrf_index,
    2070             :         int *vif_index, int8_t smac[][6], int8_t dmac[][6], struct in_addr sip,
    2071             :         struct in_addr dip, int sport, int dport, int8_t *l3_vxlan_mac, int family,
    2072             :         int count)
    2073             : {
    2074             :     vr_nexthop_req req;
    2075             :     int i;
    2076             : 
    2077           0 :     memset(&req, 0, sizeof(req));
    2078             : 
    2079           0 :     req.h_op = SANDESH_OP_ADD;
    2080           0 :     req.nhr_rid = router_id;
    2081           0 :     req.nhr_vrf = vrf_index;
    2082           0 :     req.nhr_id = nh_index;
    2083           0 :     req.nhr_flags = flags;
    2084           0 :     req.nhr_type = type;
    2085           0 :     if (req.nhr_flags & NH_FLAG_TUNNEL_UNDERLAY_ECMP) {
    2086           0 :         req.nhr_encap_oif_id_size = VR_MAX_PHY_INF;
    2087           0 :         req.nhr_encap_valid_size = VR_MAX_PHY_INF;
    2088           0 :         req.nhr_encap_valid = malloc(req.nhr_encap_valid_size * sizeof(unsigned int));
    2089             :     } else {
    2090           0 :         req.nhr_encap_oif_id_size = 1;
    2091           0 :         req.nhr_encap_valid_size = 0;
    2092           0 :         req.nhr_encap_valid = NULL;
    2093             :     }
    2094           0 :     req.nhr_encap_oif_id = malloc(req.nhr_encap_oif_id_size * sizeof(unsigned int));
    2095           0 :     if (flags & NH_FLAG_TUNNEL_UNDERLAY_ECMP) {
    2096           0 :         for (i = 0; i < VR_MAX_PHY_INF; i++) {
    2097           0 :             if (vif_index[i] < 0)
    2098           0 :                 req.nhr_encap_valid[i] = 0;
    2099             :             else
    2100           0 :                 req.nhr_encap_valid[i] = 1;
    2101           0 :             req.nhr_encap_oif_id[i] = vif_index[i];
    2102             :         }
    2103             :     }
    2104             :     else
    2105           0 :         req.nhr_encap_oif_id[0] = vif_index[0];
    2106           0 :     if (count)
    2107           0 :         req.nhr_encap_len = 14;
    2108           0 :     req.nhr_encap_size = 14 * count;
    2109           0 :     req.nhr_encap = malloc(req.nhr_encap_size);
    2110           0 :     if (!req.nhr_encap)
    2111           0 :         return -ENOMEM;
    2112           0 :     for (i = 0; i < count; i++) {
    2113           0 :         memcpy(req.nhr_encap + i*14, dmac, 6);
    2114           0 :         memcpy(req.nhr_encap + i*14 + 6, smac, 6);
    2115           0 :         *(uint16_t *)(&req.nhr_encap[12 + i*14]) = htons(0x0800);
    2116             :     }
    2117             : 
    2118             : #if defined(__linux__)
    2119           0 :     req.nhr_encap_family = ETH_P_ARP;
    2120             : #endif
    2121             : 
    2122           0 :     if (type == NH_TUNNEL) {
    2123           0 :         req.nhr_tun_sip = sip.s_addr;
    2124           0 :         req.nhr_tun_dip = dip.s_addr;
    2125           0 :         if ((sport >= 0) && (dport >= 0)) {
    2126           0 :             req.nhr_tun_sport = htons(sport);
    2127           0 :             req.nhr_tun_dport = htons(dport);
    2128             :         }
    2129           0 :         if (flags & NH_FLAG_L3_VXLAN) {
    2130           0 :             req.nhr_rw_dst_mac_size = 6;
    2131           0 :             req.nhr_rw_dst_mac = malloc(req.nhr_rw_dst_mac_size);
    2132           0 :             memcpy(req.nhr_rw_dst_mac, l3_vxlan_mac, 6);
    2133             :         }
    2134             :     }
    2135             : 
    2136           0 :     if (type == NH_ENCAP)
    2137           0 :         req.nhr_family = family;
    2138             : 
    2139           0 :     return vr_sendmsg(cl, &req, "vr_nexthop_req");
    2140             : }
    2141             : 
    2142             : int
    2143           0 : vr_send_nexthop_add(struct nl_client *cl, unsigned int router_id,
    2144             :         unsigned int type, int nh_index, unsigned int flags, int vrf_index,
    2145             :         int *vif_index, int family)
    2146             : {
    2147             :     vr_nexthop_req req;
    2148             : 
    2149           0 :     memset(&req, 0, sizeof(req));
    2150             : 
    2151           0 :     req.h_op = SANDESH_OP_ADD;
    2152           0 :     req.nhr_rid = router_id;
    2153           0 :     req.nhr_vrf = vrf_index;
    2154           0 :     req.nhr_id = nh_index;
    2155           0 :     req.nhr_flags = flags;
    2156           0 :     req.nhr_type = type;
    2157           0 :     req.nhr_family = family;
    2158           0 :     req.nhr_encap_oif_id_size = 1;
    2159           0 :     req.nhr_encap_valid_size = 0;
    2160           0 :     req.nhr_encap_valid = NULL;
    2161           0 :     req.nhr_encap_oif_id = malloc(req.nhr_encap_oif_id_size * sizeof(unsigned int));
    2162           0 :     req.nhr_encap_len = 14;
    2163           0 :     req.nhr_encap_oif_id[0] = vif_index[0];
    2164             : 
    2165           0 :     return vr_sendmsg(cl, &req, "vr_nexthop_req");
    2166             : }
    2167             : 
    2168             : void
    2169          20 : vr_route_req_destroy(vr_route_req *req)
    2170             : {
    2171          20 :     if (!req)
    2172          10 :         return;
    2173             : 
    2174          10 :     if (req->rtr_prefix_size && req->rtr_prefix) {
    2175           0 :         free(req->rtr_prefix);
    2176           0 :         req->rtr_prefix = NULL;
    2177           0 :         req->rtr_prefix_size = 0;
    2178             :     }
    2179             : 
    2180          10 :     if (req->rtr_mac_size && req->rtr_mac) {
    2181           0 :         free(req->rtr_mac);
    2182           0 :         req->rtr_mac = NULL;
    2183           0 :         req->rtr_mac_size = 0;
    2184             :     }
    2185             : 
    2186          10 :     free(req);
    2187          10 :     return;
    2188             : }
    2189             : 
    2190             : void
    2191          10 : address_mask(uint8_t *addr, uint8_t plen, unsigned int family)
    2192             : {
    2193             :    int i;
    2194             :     uint8_t address_bits;
    2195             :     uint8_t mask[VR_IP6_ADDRESS_LEN];
    2196             : 
    2197          10 :     if (family == AF_INET) {
    2198          10 :         address_bits = VR_IP_ADDRESS_LEN * 8;
    2199             :     } else {
    2200           0 :         address_bits = VR_IP6_ADDRESS_LEN * 8;
    2201             :     }
    2202             : 
    2203          10 :     memset(mask, 0xFF, sizeof(mask));
    2204          74 :     for (i = address_bits - 1; i >= plen; i--) {
    2205          64 :         mask[i / 8] ^= (1 << (7 - (i % 8)));
    2206             :     }
    2207             : 
    2208          50 :     for (i = 0; i < (address_bits / 8); i++) {
    2209          40 :         addr[i] &= mask[i];
    2210             :     }
    2211             : 
    2212          10 :     return;
    2213             : }
    2214             : 
    2215             : vr_route_req *
    2216          10 : vr_route_req_get_copy(vr_route_req *src)
    2217             : {
    2218             :     vr_route_req *dst;
    2219             : 
    2220          10 :     dst = malloc(sizeof(*dst));
    2221          10 :     if (!dst)
    2222           0 :         return NULL;
    2223             : 
    2224          10 :     *dst = *src;
    2225             : 
    2226          10 :     dst->rtr_prefix_size = 0;
    2227          10 :     dst->rtr_prefix = NULL;
    2228             : 
    2229          10 :     dst->rtr_marker_size = 0;
    2230          10 :     dst->rtr_marker = NULL;
    2231             : 
    2232          10 :     dst->rtr_mac_size = 0;
    2233          10 :     dst->rtr_mac = NULL;
    2234             : 
    2235          10 :     if (src->rtr_prefix_size && src->rtr_prefix) {
    2236          10 :         dst->rtr_prefix = malloc(src->rtr_prefix_size);
    2237          10 :         if (!dst->rtr_prefix)
    2238           0 :             goto free_rtr_req;
    2239          10 :         memcpy(dst->rtr_prefix, src->rtr_prefix, src->rtr_prefix_size);
    2240             :     }
    2241             : 
    2242          10 :     if (src->rtr_mac_size && src->rtr_mac) {
    2243           6 :         dst->rtr_mac = malloc(src->rtr_mac_size);
    2244           6 :         if (!dst->rtr_mac)
    2245           0 :             goto free_rtr_req;
    2246           6 :         memcpy(dst->rtr_mac, src->rtr_mac, src->rtr_mac_size);
    2247             :     }
    2248             : 
    2249          10 :     return dst;
    2250             : 
    2251           0 : free_rtr_req:
    2252           0 :     vr_route_req_destroy(dst);
    2253           0 :     return NULL;
    2254             : }
    2255             : 
    2256             : int
    2257           0 : vr_send_route_dump(struct nl_client *cl, unsigned int router_id, unsigned int vrf,
    2258             :         unsigned int family, uint8_t *marker)
    2259             : {
    2260             :     vr_route_req req;
    2261             : 
    2262           0 :     memset(&req, 0, sizeof(req));
    2263           0 :     req.h_op = SANDESH_OP_DUMP;
    2264           0 :     req.rtr_rid = router_id;
    2265           0 :     req.rtr_vrf_id = vrf;
    2266           0 :     req.rtr_family = family;
    2267             : 
    2268           0 :     if (family == AF_BRIDGE) {
    2269           0 :         req.rtr_mac = marker;
    2270           0 :         req.rtr_mac_size = VR_ETHER_ALEN;
    2271             :     } else {
    2272           0 :         req.rtr_prefix = marker;
    2273           0 :         req.rtr_prefix_size = RT_IP_ADDR_SIZE(family);
    2274           0 :         req.rtr_marker = marker;
    2275           0 :         req.rtr_marker_size = RT_IP_ADDR_SIZE(family);
    2276             :     }
    2277             : 
    2278           0 :     return vr_sendmsg(cl, &req, "vr_route_req");
    2279             : }
    2280             : 
    2281             : static int
    2282          10 : vr_send_route_common(struct nl_client *cl, unsigned int op,
    2283             :         unsigned int router_id, unsigned int vrf, unsigned int family,
    2284             :         uint8_t *prefix, unsigned int prefix_len, unsigned int nh_index,
    2285             :         int label, uint8_t *mac, uint32_t replace_len, unsigned int flags)
    2286             : {
    2287             :     vr_route_req req;
    2288             : 
    2289          10 :     memset(&req, 0, sizeof(req));
    2290          10 :     req.h_op = op;
    2291          10 :     req.rtr_rid = router_id;
    2292          10 :     req.rtr_vrf_id = vrf;
    2293          10 :     req.rtr_family = family;
    2294             : 
    2295          10 :     if ((family == AF_INET) || (family == AF_INET6)) {
    2296          10 :         req.rtr_prefix = prefix;
    2297          10 :         req.rtr_prefix_size = RT_IP_ADDR_SIZE(family);
    2298          10 :         req.rtr_prefix_len = prefix_len;
    2299           0 :     } else if (family == AF_BRIDGE) {
    2300           0 :         req.rtr_index = VR_BE_INVALID_INDEX;
    2301             :     }
    2302             : 
    2303          10 :     if (mac) {
    2304          10 :         req.rtr_mac = mac;
    2305          10 :         req.rtr_mac_size = VR_ETHER_ALEN;
    2306             :     }
    2307             : 
    2308          10 :     req.rtr_replace_plen = replace_len;
    2309          10 :     req.rtr_label_flags = flags;
    2310          10 :     req.rtr_label = label;
    2311          10 :     if (label != -1)
    2312          10 :         req.rtr_label_flags |= VR_RT_LABEL_VALID_FLAG;
    2313             : 
    2314          10 :     req.rtr_nh_id = nh_index;
    2315             : 
    2316          10 :     return vr_sendmsg(cl, &req, "vr_route_req");
    2317             : }
    2318             : 
    2319             : int
    2320          10 : vr_send_route_get(struct nl_client *cl,
    2321             :         unsigned int router_id, unsigned int vrf, unsigned int family,
    2322             :         uint8_t *prefix, unsigned int prefix_len, uint8_t *mac)
    2323             : {
    2324          10 :     return vr_send_route_common(cl, SANDESH_OP_GET, router_id, vrf,
    2325             :             family, prefix, prefix_len, 0, 0, mac, 0, 0);
    2326             : }
    2327             : 
    2328             : int
    2329           0 : vr_send_route_delete(struct nl_client *cl,
    2330             :         unsigned int router_id, unsigned int vrf, unsigned int family,
    2331             :         uint8_t *prefix, unsigned int prefix_len, unsigned int nh_index,
    2332             :         int label, uint8_t *mac, uint32_t replace_len, unsigned int flags)
    2333             : {
    2334           0 :     return vr_send_route_common(cl, SANDESH_OP_DEL, router_id, vrf,
    2335             :             family, prefix, prefix_len, nh_index, label,
    2336             :             mac, replace_len, flags);
    2337             : }
    2338             : 
    2339             : int
    2340           0 : vr_send_route_add(struct nl_client *cl,
    2341             :         unsigned int router_id, unsigned int vrf, unsigned int family,
    2342             :         uint8_t *prefix, unsigned int prefix_len, unsigned int nh_index,
    2343             :         int label, uint8_t *mac, uint32_t replace_len, unsigned int flags)
    2344             : {
    2345           0 :     return vr_send_route_common(cl, SANDESH_OP_ADD, router_id, vrf,
    2346             :             family, prefix, prefix_len, nh_index, label,
    2347             :             mac, replace_len,flags);
    2348             : }
    2349             : 
    2350             : /* vrf assign start */
    2351             : int
    2352           0 : vr_send_vrf_assign_dump(struct nl_client *cl, unsigned int router_id,
    2353             :         unsigned int vif_index, int marker)
    2354             : {
    2355             :     vr_vrf_assign_req req;
    2356             : 
    2357           0 :     memset(&req, 0, sizeof(req));
    2358           0 :     req.h_op = SANDESH_OP_DUMP;
    2359           0 :     req.var_rid = router_id;
    2360           0 :     req.var_vif_index = vif_index;
    2361           0 :     req.var_marker = marker;
    2362             : 
    2363           0 :     return vr_sendmsg(cl, &req, "vr_vrf_assign_req");
    2364             : }
    2365             : 
    2366             : int
    2367           0 : vr_send_vrf_assign_set(struct nl_client *cl, unsigned int router_id,
    2368             :         unsigned int vif_index, unsigned int vlan_id, unsigned int vrf_id)
    2369             : {
    2370             : 
    2371             :     vr_vrf_assign_req req;
    2372             : 
    2373           0 :     memset(&req, 0, sizeof(req));
    2374           0 :     req.h_op = SANDESH_OP_ADD;
    2375           0 :     req.var_rid = router_id;
    2376           0 :     req.var_vif_index = vif_index;
    2377           0 :     req.var_vif_vrf = vrf_id;
    2378           0 :     req.var_vlan_id = vlan_id;
    2379             : 
    2380           0 :     return vr_sendmsg(cl, &req, "vr_vrf_assign_req");
    2381             : }
    2382             : /* vrf assign end */
    2383             : 
    2384             : int
    2385           0 : vr_send_vrf_stats_dump(struct nl_client *cl, unsigned int router_id, int marker)
    2386             : {
    2387             :     vr_vrf_stats_req req;
    2388             : 
    2389           0 :     memset(&req, 0, sizeof(req));
    2390           0 :     req.h_op = SANDESH_OP_DUMP;
    2391           0 :     req.vsr_rid = router_id;
    2392           0 :     req.vsr_marker = marker;
    2393           0 :     req.vsr_family = AF_INET;
    2394             : 
    2395           0 :     return vr_sendmsg(cl, &req, "vr_vrf_stats_req");
    2396             : }
    2397             : 
    2398             : int
    2399           0 : vr_send_vrf_stats_get(struct nl_client *cl, unsigned int router_id,
    2400             :         unsigned int vrf)
    2401             : {
    2402             :     vr_vrf_stats_req req;
    2403             : 
    2404           0 :     memset(&req, 0, sizeof(req));
    2405           0 :     req.h_op = SANDESH_OP_GET;
    2406           0 :     req.vsr_rid = router_id;
    2407           0 :     req.vsr_vrf = vrf;
    2408           0 :     req.vsr_family = AF_INET;
    2409             : 
    2410           0 :     return vr_sendmsg(cl, &req, "vr_vrf_stats_req");
    2411             : }
    2412             : 
    2413             : int
    2414           0 : vr_send_vrouter_get(struct nl_client *cl, unsigned int router_id)
    2415             : {
    2416             :     vrouter_ops req;
    2417             : 
    2418           0 :     memset(&req, 0, sizeof(req));
    2419           0 :     req.h_op = SANDESH_OP_GET;
    2420             : 
    2421           0 :     return vr_sendmsg(cl, &req, "vrouter_ops");
    2422             : }
    2423             : 
    2424             : int
    2425           0 : vr_send_vrouter_set_logging(struct nl_client *cl, unsigned int router_id,
    2426             :         unsigned int log_level, unsigned int *e_log_types, unsigned int e_size,
    2427             :         unsigned int *d_log_types, unsigned int d_size)
    2428             : {
    2429             :     vrouter_ops req;
    2430             : 
    2431           0 :     memset(&req, 0, sizeof(req));
    2432           0 :     req.h_op = SANDESH_OP_ADD;
    2433             : 
    2434           0 :     if (log_level > 0)
    2435           0 :         req.vo_log_level = log_level;
    2436             : 
    2437           0 :     if (e_log_types && e_size) {
    2438           0 :         req.vo_log_type_enable_size = e_size;
    2439           0 :         req.vo_log_type_enable = e_log_types;
    2440             :     }
    2441             : 
    2442           0 :     if (d_log_types && d_size) {
    2443           0 :         req.vo_log_type_disable_size = d_size;
    2444           0 :         req.vo_log_type_disable = d_log_types;
    2445             :     }
    2446             : 
    2447             :     /*
    2448             :      * We create request to change logging options only. As we do not change
    2449             :      * vRouter's runtime parameters here, they need to be set to a meaningless
    2450             :      * value. They cannot be left zeroed, because 0 means 'feature turned off'.
    2451             :      */
    2452           0 :     req.vo_perfr = -1;
    2453           0 :     req.vo_perfs = -1;
    2454           0 :     req.vo_from_vm_mss_adj = -1;
    2455           0 :     req.vo_to_vm_mss_adj = -1;
    2456           0 :     req.vo_perfr1 = -1;
    2457           0 :     req.vo_perfr2 = -1;
    2458           0 :     req.vo_perfr3 = -1;
    2459           0 :     req.vo_perfp = -1;
    2460           0 :     req.vo_perfq1 = -1;
    2461           0 :     req.vo_perfq2 = -1;
    2462           0 :     req.vo_perfq3 = -1;
    2463           0 :     req.vo_udp_coff = -1;
    2464           0 :     req.vo_flow_hold_limit = -1;
    2465           0 :     req.vo_mudp = -1;
    2466           0 :     req.vo_packet_dump = -1;
    2467             : 
    2468           0 :     return vr_sendmsg(cl, &req, "vrouter_ops");
    2469             : }
    2470             : 
    2471             : int
    2472           0 : vr_send_vrouter_set_runtime_opts(struct nl_client *cl, unsigned int router_id,
    2473             :         int perfr, int perfs, int from_vm_mss_adj, int to_vm_mss_adj,
    2474             :         int perfr1, int perfr2, int perfr3, int perfp, int perfq1,
    2475             :         int perfq2, int perfq3, int udp_coff, int flow_hold_limit,
    2476             :         int mudp, int btokens, int binterval, int bstep,
    2477             :         unsigned int priority_tagging, int packet_dump)
    2478             : {
    2479             :     vrouter_ops req;
    2480             : 
    2481           0 :     memset(&req, 0, sizeof(req));
    2482           0 :     req.h_op = SANDESH_OP_ADD;
    2483             : 
    2484             :     /*
    2485             :      * vRouter runtime options. Adjustable by sysctl as well.
    2486             :      *
    2487             :      * No real validation is required, as sysctl does not perform any.
    2488             :      * Variables are only tested to be -1 ('do not change'),
    2489             :      * 0 ('feature turned off'), or non-zero ('feature turned on').
    2490             :      */
    2491           0 :     req.vo_perfr = perfr;
    2492           0 :     req.vo_perfs = perfs;
    2493           0 :     req.vo_from_vm_mss_adj = from_vm_mss_adj;
    2494           0 :     req.vo_to_vm_mss_adj = to_vm_mss_adj;
    2495           0 :     req.vo_perfr1 = perfr1;
    2496           0 :     req.vo_perfr2 = perfr2;
    2497           0 :     req.vo_perfr3 = perfr3;
    2498           0 :     req.vo_perfp = perfp;
    2499           0 :     req.vo_perfq1 = perfq1;
    2500           0 :     req.vo_perfq2 = perfq2;
    2501           0 :     req.vo_perfq3 = perfq3;
    2502           0 :     req.vo_udp_coff = udp_coff;
    2503           0 :     req.vo_flow_hold_limit = flow_hold_limit;
    2504           0 :     req.vo_mudp = mudp;
    2505           0 :     req.vo_burst_tokens = btokens;
    2506           0 :     req.vo_burst_interval = binterval;
    2507           0 :     req.vo_burst_step = bstep;
    2508           0 :     req.vo_priority_tagging = priority_tagging;
    2509           0 :     req.vo_packet_dump = packet_dump;
    2510             : 
    2511             :     /*
    2512             :      * We create request to change runtime (sysctl) options only. Log level
    2513             :      * fields can be left zeroed, because only non-zero values are meaningful
    2514             :      * in this case.
    2515             :      */
    2516             : 
    2517           0 :     return vr_sendmsg(cl, &req, "vrouter_ops");
    2518             : }
    2519             : 
    2520             : int
    2521           0 : vr_send_vxlan_delete(struct nl_client *cl, unsigned int router_id,
    2522             :         unsigned int vnid)
    2523             : {
    2524             :     vr_vxlan_req req;
    2525             : 
    2526           0 :     memset(&req, 0, sizeof(req));
    2527           0 :     req.h_op = SANDESH_OP_DEL;
    2528           0 :     req.vxlanr_vnid = vnid;
    2529             : 
    2530           0 :     return vr_sendmsg(cl, &req, "vr_vxlan_req");
    2531             : }
    2532             : 
    2533             : int
    2534           0 : vr_send_vxlan_dump(struct nl_client *cl, unsigned int router_id,
    2535             :         int marker)
    2536             : {
    2537             :     vr_vxlan_req req;
    2538             : 
    2539           0 :     memset(&req, 0, sizeof(req));
    2540           0 :     req.h_op = SANDESH_OP_DUMP;
    2541           0 :     req.vxlanr_vnid = marker;
    2542             : 
    2543           0 :     return vr_sendmsg(cl, &req, "vr_vxlan_req");
    2544             : }
    2545             : 
    2546             : int
    2547           0 : vr_send_vxlan_get(struct nl_client *cl, unsigned int router_id,
    2548             :         unsigned int vnid)
    2549             : {
    2550             :     vr_vxlan_req req;
    2551             : 
    2552           0 :     memset(&req, 0, sizeof(req));
    2553           0 :     req.h_op = SANDESH_OP_GET;
    2554           0 :     req.vxlanr_vnid = vnid;
    2555             : 
    2556           0 :     return vr_sendmsg(cl, &req, "vr_vxlan_req");
    2557             : }
    2558             : 
    2559             : int
    2560           0 : vr_send_vxlan_add(struct nl_client *cl, unsigned int router_id,
    2561             :         unsigned int vnid, unsigned int nh_index)
    2562             : {
    2563             :     vr_vxlan_req req;
    2564             : 
    2565           0 :     memset(&req, 0, sizeof(req));
    2566           0 :     req.h_op = SANDESH_OP_ADD;
    2567           0 :     req.vxlanr_vnid = vnid;
    2568           0 :     req.vxlanr_nhid = nh_index;
    2569             : 
    2570           0 :     return vr_sendmsg(cl, &req, "vr_vxlan_req");
    2571             : }
    2572             : 
    2573             : int
    2574           0 : vr_send_fc_map_get(struct nl_client *cl, unsigned int router_id,
    2575             :         uint8_t fc_map_id)
    2576             : {
    2577             :     vr_fc_map_req req;
    2578           0 :     int16_t id = fc_map_id;
    2579             : 
    2580           0 :     memset(&req, 0, sizeof(req));
    2581           0 :     req.h_op = SANDESH_OP_GET;
    2582           0 :     req.fmr_rid = router_id;
    2583           0 :     req.fmr_id = &id;
    2584           0 :     req.fmr_id_size = 1;
    2585             : 
    2586           0 :     return vr_sendmsg(cl, &req, "vr_fc_map_req");
    2587             : }
    2588             : 
    2589             : int
    2590           0 : vr_send_fc_map_dump(struct nl_client *cl, unsigned int router_id,
    2591             :         int marker)
    2592             : {
    2593             :     vr_fc_map_req req;
    2594             : 
    2595           0 :     memset(&req, 0, sizeof(req));
    2596           0 :     req.h_op = SANDESH_OP_DUMP;
    2597           0 :     req.fmr_rid = router_id;
    2598           0 :     req.fmr_marker = marker;
    2599             : 
    2600           0 :     return vr_sendmsg(cl, &req, "vr_fc_map_req");
    2601             : }
    2602             : 
    2603             : int
    2604           0 : vr_send_fc_map_delete(struct nl_client *cl, unsigned int router_id,
    2605             :         uint8_t fc_id)
    2606             : {
    2607             :     vr_fc_map_req req;
    2608           0 :     int16_t id = fc_id;
    2609             : 
    2610           0 :     memset(&req, 0, sizeof(req));
    2611           0 :     req.h_op = SANDESH_OP_DEL;
    2612           0 :     req.fmr_rid = router_id;
    2613           0 :     req.fmr_id = &id;
    2614           0 :     req.fmr_id_size = 1;
    2615             : 
    2616           0 :     return vr_sendmsg(cl, &req, "vr_fc_map_req");
    2617             : }
    2618             : 
    2619             : int
    2620           0 : vr_send_fc_map_add(struct nl_client *cl, unsigned int router_id,
    2621             :         int16_t *fc_id, uint8_t fc_id_size,
    2622             :         uint8_t *dscp, uint8_t *mpls_qos, uint8_t *dotonep, uint8_t *queue)
    2623             : {
    2624             :     vr_fc_map_req req;
    2625             : 
    2626           0 :     memset(&req, 0, sizeof(req));
    2627           0 :     req.fmr_rid = router_id;
    2628             : 
    2629           0 :     req.fmr_id = fc_id;
    2630           0 :     req.fmr_id_size = fc_id_size;
    2631           0 :     req.fmr_dscp = dscp;
    2632           0 :     req.fmr_dscp_size = fc_id_size;
    2633           0 :     req.fmr_mpls_qos = mpls_qos;
    2634           0 :     req.fmr_mpls_qos_size = fc_id_size;
    2635           0 :     req.fmr_dotonep = dotonep;
    2636           0 :     req.fmr_dotonep_size = fc_id_size;
    2637           0 :     req.fmr_queue_id = queue;
    2638           0 :     req.fmr_queue_id_size = fc_id_size;
    2639             : 
    2640           0 :     return vr_sendmsg(cl, &req, "vr_fc_map_req");
    2641             : }
    2642             : 
    2643             : int
    2644           0 : vr_send_qos_map_get(struct nl_client *cl, unsigned int router_id,
    2645             :         unsigned int qos_map_id)
    2646             : {
    2647             :     vr_qos_map_req req;
    2648             : 
    2649           0 :     memset(&req, 0, sizeof(req));
    2650           0 :     req.h_op = SANDESH_OP_GET;
    2651           0 :     req.qmr_rid = router_id;
    2652           0 :     req.qmr_id = qos_map_id;
    2653             : 
    2654           0 :     return vr_sendmsg(cl, &req, "vr_qos_map_req");
    2655             : }
    2656             : 
    2657             : 
    2658             : int
    2659           0 : vr_send_qos_map_dump(struct nl_client *cl, unsigned int router_id,
    2660             :         int marker)
    2661             : {
    2662             :     vr_qos_map_req req;
    2663             : 
    2664           0 :     memset(&req, 0, sizeof(req));
    2665           0 :     req.h_op = SANDESH_OP_DUMP;
    2666           0 :     req.qmr_rid = router_id;
    2667           0 :     req.qmr_marker = marker;
    2668             : 
    2669           0 :     return vr_sendmsg(cl, &req, "vr_qos_map_req");
    2670             : }
    2671             : 
    2672             : int
    2673           0 : vr_send_qos_map_delete(struct nl_client *cl, unsigned int router_id,
    2674             :         unsigned int qos_map_id)
    2675             : {
    2676             :     vr_qos_map_req req;
    2677             : 
    2678           0 :     memset(&req, 0, sizeof(req));
    2679           0 :     req.h_op = SANDESH_OP_DEL;
    2680           0 :     req.qmr_rid = router_id;
    2681           0 :     req.qmr_id = qos_map_id;
    2682             : 
    2683           0 :     return vr_sendmsg(cl, &req, "vr_qos_map_req");
    2684             : }
    2685             : 
    2686             : int
    2687           0 : vr_send_qos_map_add(struct nl_client *cl, unsigned int router_id,
    2688             :         unsigned int qos_id,
    2689             :         uint8_t *dscp, uint8_t num_dscp, uint8_t *dscp_fc_id,
    2690             :         uint8_t *mpls_qos, uint8_t num_mpls_qos, uint8_t *mpls_qos_fc_id,
    2691             :         uint8_t *dotonep, uint8_t num_dotonep, uint8_t *dotonep_fc_id)
    2692             : {
    2693             :     vr_qos_map_req req;
    2694             : 
    2695           0 :     memset(&req, 0, sizeof(req));
    2696           0 :     req.h_op = SANDESH_OP_ADD;
    2697           0 :     req.qmr_rid = router_id;
    2698           0 :     req.qmr_id = qos_id;
    2699             : 
    2700           0 :     if (num_dscp) {
    2701           0 :         req.qmr_dscp = dscp;
    2702           0 :         req.qmr_dscp_size = num_dscp;
    2703           0 :         req.qmr_dscp_fc_id = dscp_fc_id;
    2704           0 :         req.qmr_dscp_fc_id_size = num_dscp;
    2705             :     }
    2706             : 
    2707           0 :     if (num_mpls_qos) {
    2708           0 :         req.qmr_mpls_qos = mpls_qos;
    2709           0 :         req.qmr_mpls_qos_size = num_mpls_qos;
    2710           0 :         req.qmr_mpls_qos_fc_id = mpls_qos_fc_id;
    2711           0 :         req.qmr_mpls_qos_fc_id_size = num_mpls_qos;
    2712             :     }
    2713             : 
    2714           0 :     if (num_dotonep) {
    2715           0 :         req.qmr_dotonep = dotonep;
    2716           0 :         req.qmr_dotonep_size = num_dotonep;
    2717           0 :         req.qmr_dotonep_fc_id = dotonep_fc_id;
    2718           0 :         req.qmr_dotonep_fc_id_size = num_dotonep;
    2719             :     }
    2720             : 
    2721           0 :     return vr_sendmsg(cl, &req, "vr_qos_map_req");
    2722             : }
    2723             : 
    2724             : int
    2725           0 : vr_send_ddp_req(struct nl_client *cl, vr_info_msg_en msginfo, uint8_t *vr_info_inbuf)
    2726             : {
    2727             :     vr_info_req req;
    2728             : 
    2729           0 :     memset(&req, 0, sizeof(req));
    2730             : 
    2731           0 :     req.h_op        = SANDESH_OP_DUMP;
    2732           0 :     req.vdu_msginfo = msginfo;
    2733             : 
    2734           0 :     if (vr_info_inbuf != NULL) {
    2735           0 :         req.vdu_inbuf_size = strlen(vr_info_inbuf);
    2736           0 :         req.vdu_inbuf = vr_info_inbuf;
    2737             :     }
    2738           0 :     return vr_sendmsg(cl, &req, "vr_info_req");
    2739             : }

Generated by: LCOV version 1.14