LCOV - code coverage report
Current view: top level - plugins/igmp - igmp_cli.c (source / functions) Hit Total Coverage
Test: coverage-filtered.info Lines: 27 172 15.7 %
Date: 2023-07-05 22:20:52 Functions: 21 27 77.8 %

          Line data    Source code
       1             : /*
       2             :  *------------------------------------------------------------------
       3             :  * Copyright (c) 2017 Cisco and/or its affiliates.
       4             :  * Licensed under the Apache License, Version 2.0 (the "License");
       5             :  * you may not use this file except in compliance with the License.
       6             :  * You may obtain a copy of the License at:
       7             :  *
       8             :  *     http://www.apache.org/licenses/LICENSE-2.0
       9             :  *
      10             :  * Unless required by applicable law or agreed to in writing, software
      11             :  * distributed under the License is distributed on an "AS IS" BASIS,
      12             :  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
      13             :  * See the License for the specific language governing permissions and
      14             :  * limitations under the License.
      15             :  *------------------------------------------------------------------
      16             :  */
      17             : 
      18             : #include <stdint.h>
      19             : #include <sys/ioctl.h>
      20             : #include <inttypes.h>
      21             : 
      22             : #include <vlib/vlib.h>
      23             : #include <vlib/unix/unix.h>
      24             : #include <vnet/ip/ip.h>
      25             : #include <vnet/fib/fib_entry.h>
      26             : #include <vnet/fib/fib_table.h>
      27             : #include <vnet/mfib/mfib_table.h>
      28             : 
      29             : #include <igmp/igmp.h>
      30             : 
      31             : static clib_error_t *
      32           0 : igmp_clear_interface_command_fn (vlib_main_t * vm, unformat_input_t * input,
      33             :                                  vlib_cli_command_t * cmd)
      34             : {
      35           0 :   unformat_input_t _line_input, *line_input = &_line_input;
      36           0 :   clib_error_t *error = NULL;
      37           0 :   vnet_main_t *vnm = vnet_get_main ();
      38             :   u32 sw_if_index;
      39             : 
      40             :   igmp_config_t *config;
      41             : 
      42           0 :   if (!unformat_user (input, unformat_line_input, line_input))
      43             :     {
      44             :       error =
      45           0 :         clib_error_return (0, "'help clear igmp' or 'clear igmp ?' for help");
      46           0 :       return error;
      47             :     }
      48             : 
      49           0 :   while (unformat_check_input (line_input) != UNFORMAT_END_OF_INPUT)
      50             :     {
      51           0 :       if (unformat
      52             :           (line_input, "int %U", unformat_vnet_sw_interface, vnm,
      53             :            &sw_if_index));
      54             :       else
      55             :         {
      56             :           error =
      57           0 :             clib_error_return (0, "unknown input '%U'", format_unformat_error,
      58             :                                line_input);
      59           0 :           goto done;
      60             :         }
      61             :     }
      62             : 
      63           0 :   config = igmp_config_lookup (sw_if_index);
      64           0 :   if (config)
      65           0 :     igmp_clear_config (config);
      66             : 
      67           0 : done:
      68           0 :   unformat_free (line_input);
      69           0 :   return error;
      70             : }
      71             : 
      72             : /* *INDENT-OFF* */
      73      196727 : VLIB_CLI_COMMAND (igmp_clear_interface_command, static) = {
      74             :   .path = "clear igmp",
      75             :   .short_help = "clear igmp int <interface>",
      76             :   .function = igmp_clear_interface_command_fn,
      77             : };
      78             : /* *INDENT-ON* */
      79             : 
      80             : static clib_error_t *
      81           0 : igmp_listen_command_fn (vlib_main_t * vm, unformat_input_t * input,
      82             :                         vlib_cli_command_t * cmd)
      83             : {
      84           0 :   unformat_input_t _line_input, *line_input = &_line_input;
      85           0 :   clib_error_t *error = NULL;
      86           0 :   u8 enable = 1;
      87           0 :   ip46_address_t saddr, *saddrs = NULL, gaddr;
      88           0 :   vnet_main_t *vnm = vnet_get_main ();
      89             :   u32 sw_if_index;
      90             :   int rv;
      91             : 
      92           0 :   if (!unformat_user (input, unformat_line_input, line_input))
      93             :     {
      94             :       error =
      95           0 :         clib_error_return (0,
      96             :                            "'help igmp listen' or 'igmp listen ?' for help");
      97           0 :       return error;
      98             :     }
      99             : 
     100           0 :   while (unformat_check_input (line_input) != UNFORMAT_END_OF_INPUT)
     101             :     {
     102           0 :       if (unformat (line_input, "enable"))
     103           0 :         enable = 1;
     104           0 :       else if (unformat (line_input, "disable"))
     105           0 :         enable = 0;
     106             :       else
     107           0 :         if (unformat
     108             :             (line_input, "int %U", unformat_vnet_sw_interface, vnm,
     109             :              &sw_if_index));
     110             :       else
     111           0 :         if (unformat (line_input, "saddr %U", unformat_ip46_address, &saddr))
     112           0 :         vec_add1 (saddrs, saddr);
     113             :       else
     114           0 :         if (unformat (line_input, "gaddr %U", unformat_ip46_address, &gaddr));
     115             :       else
     116             :         {
     117             :           error =
     118           0 :             clib_error_return (0, "unknown input '%U'", format_unformat_error,
     119             :                                line_input);
     120           0 :           goto done;
     121             :         }
     122             :     }
     123             : 
     124           0 :   if ((vnet_sw_interface_get_flags (vnm, sw_if_index)
     125             :        && VNET_SW_INTERFACE_FLAG_ADMIN_UP) == 0)
     126             :     {
     127           0 :       error = clib_error_return (0, "Interface is down");
     128           0 :       goto done;
     129             :     }
     130             : 
     131           0 :   rv = igmp_listen (vm, enable, sw_if_index, saddrs, &gaddr);
     132             : 
     133           0 :   if (rv == -1)
     134             :     {
     135           0 :       if (enable)
     136             :         error =
     137           0 :           clib_error_return (0, "This igmp configuration already exists");
     138             :       else
     139             :         error =
     140           0 :           clib_error_return (0, "This igmp configuration does not exist");
     141             :     }
     142           0 :   else if (rv == -2)
     143             :     error =
     144           0 :       clib_error_return (0,
     145             :                          "Failed to add configuration, interface is in router mode");
     146             : 
     147           0 : done:
     148           0 :   unformat_free (line_input);
     149           0 :   vec_free (saddrs);
     150           0 :   return error;
     151             : }
     152             : 
     153             : /* *INDENT-OFF* */
     154      196727 : VLIB_CLI_COMMAND (igmp_listen_command, static) = {
     155             :   .path = "igmp listen",
     156             :   .short_help = "igmp listen [<enable|disable>] "
     157             :                 "int <interface> saddr <ip4-address> gaddr <ip4-address>",
     158             :   .function = igmp_listen_command_fn,
     159             : };
     160             : /* *INDENT-ON* */
     161             : 
     162             : static clib_error_t *
     163           0 : igmp_enable_cli (vlib_main_t * vm,
     164             :                  unformat_input_t * input, vlib_cli_command_t * cmd)
     165             : {
     166           0 :   unformat_input_t _line_input, *line_input = &_line_input;
     167           0 :   igmp_mode_t mode = IGMP_MODE_ROUTER;
     168           0 :   vnet_main_t *vnm = vnet_get_main ();
     169           0 :   clib_error_t *error = NULL;
     170           0 :   u32 sw_if_index = ~0;
     171           0 :   u8 enable = 1;
     172             :   int rv;
     173             : 
     174           0 :   if (!unformat_user (input, unformat_line_input, line_input))
     175           0 :     return error;
     176             : 
     177           0 :   while (unformat_check_input (line_input) != UNFORMAT_END_OF_INPUT)
     178             :     {
     179           0 :       if (unformat (line_input, "enable"))
     180           0 :         enable = 1;
     181           0 :       else if (unformat (line_input, "disable"))
     182           0 :         enable = 0;
     183           0 :       if (unformat (line_input, "host"))
     184           0 :         mode = IGMP_MODE_HOST;
     185           0 :       else if (unformat (line_input, "router"))
     186           0 :         mode = IGMP_MODE_ROUTER;
     187           0 :       else if (unformat (line_input, "%U",
     188             :                          unformat_vnet_sw_interface, vnm, &sw_if_index));
     189             :       else
     190             :         {
     191             :           error =
     192           0 :             clib_error_return (0, "unknown input '%U'", format_unformat_error,
     193             :                                line_input);
     194           0 :           goto done;
     195             :         }
     196             :     }
     197             : 
     198           0 :   if (~0 == sw_if_index)
     199             :     {
     200           0 :       error = clib_error_return (0, "interface must be specified");
     201           0 :       goto done;
     202             :     }
     203             : 
     204           0 :   rv = igmp_enable_disable (sw_if_index, enable, mode);
     205             : 
     206           0 :   if (0 != rv)
     207           0 :     error = clib_error_return (0, "result: %d", rv);
     208             : 
     209           0 : done:
     210           0 :   unformat_free (line_input);
     211           0 :   return error;
     212             : }
     213             : 
     214             : /* *INDENT-OFF* */
     215      196727 : VLIB_CLI_COMMAND (igmp_enable_command, static) = {
     216             :   .path = "igmp",
     217             :   .short_help = "igmp <enable|disable> <host|router> <interface>",
     218             :   .function = igmp_enable_cli,
     219             : };
     220             : /* *INDENT-ON* */
     221             : 
     222             : static clib_error_t *
     223           0 : igmp_proxy_device_add_del_command_fn (vlib_main_t * vm,
     224             :                                       unformat_input_t * input,
     225             :                                       vlib_cli_command_t * cmd)
     226             : {
     227           0 :   unformat_input_t _line_input, *line_input = &_line_input;
     228           0 :   vnet_main_t *vnm = vnet_get_main ();
     229           0 :   clib_error_t *error = NULL;
     230           0 :   u32 sw_if_index = ~0;
     231           0 :   u32 vrf_id = ~0;
     232           0 :   u8 add = 1;
     233             :   int rv;
     234             : 
     235           0 :   if (!unformat_user (input, unformat_line_input, line_input))
     236           0 :     return error;
     237             : 
     238           0 :   while (unformat_check_input (line_input) != UNFORMAT_END_OF_INPUT)
     239             :     {
     240           0 :       if (unformat (line_input, "add"))
     241           0 :         add = 1;
     242           0 :       else if (unformat (line_input, "del"))
     243           0 :         add = 0;
     244           0 :       else if (unformat (line_input, "vrf-id %u", &vrf_id))
     245             :         ;
     246           0 :       else if (unformat (line_input, "%U",
     247             :                          unformat_vnet_sw_interface, vnm, &sw_if_index));
     248             :       else
     249             :         {
     250             :           error =
     251           0 :             clib_error_return (0, "unknown input '%U'", format_unformat_error,
     252             :                                line_input);
     253           0 :           goto done;
     254             :         }
     255             :     }
     256             : 
     257           0 :   if (~0 == sw_if_index)
     258             :     {
     259           0 :       error = clib_error_return (0, "interface must be specified");
     260           0 :       goto done;
     261             :     }
     262             : 
     263           0 :   if (~0 == vrf_id)
     264             :     {
     265           0 :       error = clib_error_return (0, "VRF must be specified");
     266           0 :       goto done;
     267             :     }
     268             : 
     269           0 :   rv = igmp_proxy_device_add_del (vrf_id, sw_if_index, add);
     270             : 
     271           0 :   if (0 != rv)
     272           0 :     error = clib_error_return (0, "result: %d", rv);
     273             : 
     274           0 : done:
     275           0 :   unformat_free (line_input);
     276           0 :   return error;
     277             : }
     278             : /* *INDENT-OFF* */
     279      196727 : VLIB_CLI_COMMAND (igmp_proxy_device_add_del_command, static) = {
     280             :   .path = "igmp proxy-dev",
     281             :   .short_help = "igmp proxy-dev <add|del> vrf-id <table-id> <interface>",
     282             :   .function = igmp_proxy_device_add_del_command_fn,
     283             : };
     284             : /* *INDENT-ON* */
     285             : 
     286             : static clib_error_t *
     287           0 : igmp_proxy_device_add_del_interface_command_fn (vlib_main_t * vm,
     288             :                                                 unformat_input_t * input,
     289             :                                                 vlib_cli_command_t * cmd)
     290             : {
     291           0 :   unformat_input_t _line_input, *line_input = &_line_input;
     292           0 :   vnet_main_t *vnm = vnet_get_main ();
     293           0 :   clib_error_t *error = NULL;
     294           0 :   u32 sw_if_index = ~0;
     295           0 :   u32 vrf_id = ~0;
     296           0 :   u8 add = 1;
     297             :   int rv;
     298             : 
     299           0 :   if (!unformat_user (input, unformat_line_input, line_input))
     300           0 :     return error;
     301             : 
     302           0 :   while (unformat_check_input (line_input) != UNFORMAT_END_OF_INPUT)
     303             :     {
     304           0 :       if (unformat (line_input, "add"))
     305           0 :         add = 1;
     306           0 :       else if (unformat (line_input, "del"))
     307           0 :         add = 0;
     308           0 :       else if (unformat (line_input, "vrf-id %u", &vrf_id))
     309             :         ;
     310           0 :       else if (unformat (line_input, "%U",
     311             :                          unformat_vnet_sw_interface, vnm, &sw_if_index));
     312             :       else
     313             :         {
     314             :           error =
     315           0 :             clib_error_return (0, "unknown input '%U'", format_unformat_error,
     316             :                                line_input);
     317           0 :           goto done;
     318             :         }
     319             :     }
     320             : 
     321           0 :   if (~0 == sw_if_index)
     322             :     {
     323           0 :       error = clib_error_return (0, "interface must be specified");
     324           0 :       goto done;
     325             :     }
     326             : 
     327           0 :   if (~0 == vrf_id)
     328             :     {
     329           0 :       error = clib_error_return (0, "VRF must be specified");
     330           0 :       goto done;
     331             :     }
     332             : 
     333           0 :   rv = igmp_proxy_device_add_del_interface (vrf_id, sw_if_index, add);
     334             : 
     335           0 :   if (0 != rv)
     336           0 :     error = clib_error_return (0, "result: %d", rv);
     337             : 
     338           0 : done:
     339           0 :   unformat_free (line_input);
     340           0 :   return error;
     341             : }
     342             : /* *INDENT-OFF* */
     343      196727 : VLIB_CLI_COMMAND (igmp_proxy_device_add_del_interface_command, static) = {
     344             :   .path = "igmp proxy-dev itf",
     345             :   .short_help = "igmp proxy-dev itf <add|del> vrf-id <table-id> <interface>",
     346             :   .function = igmp_proxy_device_add_del_interface_command_fn,
     347             : };
     348             : /* *INDENT-ON* */
     349             : 
     350             : static clib_error_t *
     351           1 : igmp_show_command_fn (vlib_main_t * vm, unformat_input_t * input,
     352             :                       vlib_cli_command_t * cmd)
     353             : {
     354           1 :   clib_error_t *error = NULL;
     355           1 :   igmp_main_t *im = &igmp_main;
     356             :   igmp_config_t *config;
     357             : 
     358             :   /* *INDENT-OFF* */
     359           2 :   pool_foreach (config, im->configs)
     360             :      {
     361           1 :       vlib_cli_output (vm, "%U", format_igmp_config, config);
     362             :     }
     363             :   /* *INDENT-ON* */
     364             : 
     365           1 :   return error;
     366             : }
     367             : 
     368             : /* *INDENT-OFF* */
     369      196727 : VLIB_CLI_COMMAND (igmp_show_command, static) = {
     370             :   .path = "show igmp config",
     371             :   .short_help = "show igmp config",
     372             :   .function = igmp_show_command_fn,
     373             : };
     374             : /* *INDENT-ON* */
     375             : 
     376             : static clib_error_t *
     377           0 : igmp_show_timers_command_fn (vlib_main_t * vm,
     378             :                              unformat_input_t * input,
     379             :                              vlib_cli_command_t * cmd)
     380             : {
     381             : #define _(n,f) vlib_cli_output (vm, "%s: %d", #f, igmp_timer_type_get(n));
     382           0 :   foreach_igmp_timer_type
     383             : #undef _
     384           0 :     return (NULL);
     385             : }
     386             : 
     387             : /* *INDENT-OFF* */
     388      196727 : VLIB_CLI_COMMAND (igmp_show_timers_command, static) = {
     389             :   .path = "show igmp timers",
     390             :   .short_help = "show igmp timers",
     391             :   .function = igmp_show_timers_command_fn,
     392             : };
     393             : /* *INDENT-ON* */
     394             : 
     395             : static clib_error_t *
     396           2 : test_igmp_command_fn (vlib_main_t * vm,
     397             :                       unformat_input_t * input, vlib_cli_command_t * cmd)
     398             : {
     399           2 :   clib_error_t *error = NULL;
     400             :   u32 value;
     401             : 
     402           8 :   while (unformat_check_input (input) != UNFORMAT_END_OF_INPUT)
     403             :     {
     404           6 :       if (unformat (input, "query %d", &value))
     405           2 :         igmp_timer_type_set (IGMP_TIMER_QUERY, value);
     406           4 :       else if (unformat (input, "src %d", &value))
     407           2 :         igmp_timer_type_set (IGMP_TIMER_SRC, value);
     408           2 :       else if (unformat (input, "leave %d", &value))
     409           2 :         igmp_timer_type_set (IGMP_TIMER_LEAVE, value);
     410             :       else
     411           0 :         error = clib_error_return (0, "query or src timers only");
     412             :     }
     413             : 
     414           2 :   return error;
     415             : }
     416             : 
     417             : /* *INDENT-OFF* */
     418      196727 : VLIB_CLI_COMMAND (test_igmp_command, static) = {
     419             :   .path = "test igmp timers",
     420             :   .short_help = "Change the default values for IGMP timers - only sensible during unit tests",
     421             :   .function = test_igmp_command_fn,
     422             : };
     423             : /* *INDENT-ON* */
     424             : 
     425             : 
     426             : clib_error_t *
     427         559 : igmp_cli_init (vlib_main_t * vm)
     428             : {
     429         559 :   return 0;
     430             : }
     431             : 
     432        1119 : VLIB_INIT_FUNCTION (igmp_cli_init);
     433             : 
     434             : /*
     435             :  * fd.io coding-style-patch-verification: ON
     436             :  *
     437             :  * Local Variables:
     438             :  * eval: (c-set-style "gnu")
     439             :  * End:
     440             :  */

Generated by: LCOV version 1.14