LCOV - code coverage report
Current view: top level - plugins/ioam/encap - ip6_ioam_e2e.c (source / functions) Hit Total Coverage
Test: coverage-filtered.info Lines: 9 65 13.8 %
Date: 2023-07-05 22:20:52 Functions: 5 10 50.0 %

          Line data    Source code
       1             : /*
       2             :  * Copyright (c) 2016 Cisco and/or its affiliates.
       3             :  * Licensed under the Apache License, Version 2.0 (the "License");
       4             :  * you may not use this file except in compliance with the License.
       5             :  * You may obtain a copy of the License at:
       6             :  *
       7             :  *     http://www.apache.org/licenses/LICENSE-2.0
       8             :  *
       9             :  * Unless required by applicable law or agreed to in writing, software
      10             :  * distributed under the License is distributed on an "AS IS" BASIS,
      11             :  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
      12             :  * See the License for the specific language governing permissions and
      13             :  * limitations under the License.
      14             :  */
      15             : 
      16             : #include <vlib/vlib.h>
      17             : #include <vnet/vnet.h>
      18             : #include <vppinfra/error.h>
      19             : 
      20             : #include <vnet/ip/ip.h>
      21             : 
      22             : #include <vppinfra/hash.h>
      23             : #include <vppinfra/error.h>
      24             : #include <vppinfra/elog.h>
      25             : 
      26             : #include <vnet/ip/ip6_hop_by_hop.h>
      27             : #include "ip6_ioam_e2e.h"
      28             : 
      29             : ioam_e2e_main_t ioam_e2e_main;
      30             : 
      31           0 : static u8 * ioam_e2e_trace_handler (u8 * s,
      32             :                                     ip6_hop_by_hop_option_t *opt)
      33             : {
      34           0 :   ioam_e2e_option_t * e2e = (ioam_e2e_option_t *)opt;
      35           0 :   u32 seqno = 0;
      36             : 
      37           0 :   if (e2e)
      38             :     {
      39           0 :       seqno = clib_net_to_host_u32 (e2e->e2e_hdr.e2e_data);
      40             :     }
      41             : 
      42           0 :   s = format (s, "SeqNo = 0x%Lx", seqno);
      43           0 :   return s;
      44             : }
      45             : 
      46             : int
      47           0 : ioam_e2e_config_handler (void *data, u8 disable)
      48             : {
      49           0 :   int *analyse = data;
      50             : 
      51             :   /* Register hanlders if enabled */
      52           0 :   if (!disable)
      53             :     {
      54             :       /* If encap node register for encap handler */
      55           0 :       if (0 == *analyse)
      56             :         {
      57           0 :           if (ip6_hbh_register_option(HBH_OPTION_TYPE_IOAM_EDGE_TO_EDGE,
      58             :                                       ioam_seqno_encap_handler,
      59             :                                       ioam_e2e_trace_handler) < 0)
      60             :             {
      61           0 :               return (-1);
      62             :             }
      63             :         }
      64             :       /* If analyze node then register for decap handler */
      65             :       else
      66             :         {
      67           0 :           if (ip6_hbh_pop_register_option(HBH_OPTION_TYPE_IOAM_EDGE_TO_EDGE,
      68             :                                           ioam_seqno_decap_handler) < 0)
      69             :             {
      70           0 :               return (-1);
      71             :             }
      72             :         }
      73           0 :       return 0;
      74             :     }
      75             : 
      76             :   /* UnRegister handlers */
      77           0 :   (void) ip6_hbh_unregister_option(HBH_OPTION_TYPE_IOAM_EDGE_TO_EDGE);
      78           0 :   (void) ip6_hbh_pop_unregister_option(HBH_OPTION_TYPE_IOAM_EDGE_TO_EDGE);
      79           0 :   return 0;
      80             : }
      81             : 
      82             : int
      83           0 : ioam_e2e_rewrite_handler (u8 *rewrite_string,
      84             :                           u8 *rewrite_size)
      85             : {
      86             :   ioam_e2e_option_t *e2e_option;
      87             : 
      88           0 :   if (rewrite_string && *rewrite_size == sizeof(ioam_e2e_option_t))
      89             :     {
      90           0 :       e2e_option = (ioam_e2e_option_t *)rewrite_string;
      91           0 :       e2e_option->hdr.type = HBH_OPTION_TYPE_IOAM_EDGE_TO_EDGE
      92             :           | HBH_OPTION_TYPE_SKIP_UNKNOWN;
      93           0 :       e2e_option->hdr.length = sizeof (ioam_e2e_option_t) -
      94             :           sizeof (ip6_hop_by_hop_option_t);
      95           0 :       return(0);
      96             :     }
      97           0 :   return(-1);
      98             : }
      99             : 
     100             : u32
     101           0 : ioam_e2e_flow_handler (u32 ctx, u8 add)
     102             : {
     103             :   ioam_e2e_data_t *data;
     104             :   u16 i;
     105             : 
     106           0 :   if (add)
     107             :     {
     108           0 :       pool_get(ioam_e2e_main.e2e_data, data);
     109           0 :       data->flow_ctx =  ctx;
     110           0 :       ioam_seqno_init_data(&data->seqno_data);
     111           0 :       return ((u32) (data - ioam_e2e_main.e2e_data));
     112             :     }
     113             : 
     114             :   /* Delete case */
     115           0 :   for (i = 0; i < vec_len(ioam_e2e_main.e2e_data); i++)
     116             :     {
     117           0 :       if (pool_is_free_index(ioam_e2e_main.e2e_data, i))
     118           0 :         continue;
     119             : 
     120           0 :       data = pool_elt_at_index(ioam_e2e_main.e2e_data, i);
     121           0 :       if (data && (data->flow_ctx == ctx))
     122             :         {
     123           0 :           pool_put_index(ioam_e2e_main.e2e_data, i);
     124           0 :           return (0);
     125             :         }
     126             :     }
     127           0 :   return 0;
     128             : }
     129             : 
     130             : static clib_error_t *
     131           0 : ioam_show_e2e_cmd_fn (vlib_main_t * vm,
     132             :                       unformat_input_t * input,
     133             :                       vlib_cli_command_t * cmd)
     134             : {
     135             :   ioam_e2e_data_t *e2e_data;
     136           0 :   u8 *s = 0;
     137             :   int i;
     138             : 
     139           0 :   vec_reset_length(s);
     140             : 
     141           0 :   s = format(0, "IOAM E2E information: \n");
     142           0 :   for (i = 0; i < vec_len(ioam_e2e_main.e2e_data); i++)
     143             :     {
     144           0 :       if (pool_is_free_index(ioam_e2e_main.e2e_data, i))
     145           0 :         continue;
     146             : 
     147           0 :       e2e_data = pool_elt_at_index(ioam_e2e_main.e2e_data, i);
     148           0 :       s = format(s, "Flow name: %s\n", get_flow_name_from_flow_ctx(e2e_data->flow_ctx));
     149             : 
     150           0 :       s = show_ioam_seqno_cmd_fn(s,
     151             :                                  &e2e_data->seqno_data,
     152           0 :                                  !IOAM_DEAP_ENABLED(e2e_data->flow_ctx));
     153             :     }
     154             : 
     155           0 :   vlib_cli_output(vm, "%v", s);
     156           0 :   return 0;
     157             : }
     158             : 
     159             : 
     160      176567 : VLIB_CLI_COMMAND (ioam_show_e2e_cmd, static) = {
     161             :     .path = "show ioam e2e ",
     162             :     .short_help = "show ioam e2e information",
     163             :     .function = ioam_show_e2e_cmd_fn,
     164             : };
     165             : 
     166             : /*
     167             :  * Init handler E2E headet handling.
     168             :  * Init hanlder registers encap, decap, trace and Rewrite handlers.
     169             :  */
     170             : static clib_error_t *
     171         559 : ioam_e2e_init (vlib_main_t * vm)
     172             : {
     173             :   /*
     174             :    * As of now we have only PPC under E2E header.
     175             :    */
     176         559 :   if (ip6_hbh_config_handler_register(HBH_OPTION_TYPE_IOAM_EDGE_TO_EDGE,
     177             :                                       ioam_e2e_config_handler) < 0)
     178             :     {
     179           0 :       return (clib_error_create("Registration of "
     180             :           "HBH_OPTION_TYPE_IOAM_EDGE_TO_EDGE for rewrite failed"));
     181             :     }
     182             : 
     183         559 :   if (ip6_hbh_add_register_option(HBH_OPTION_TYPE_IOAM_EDGE_TO_EDGE,
     184             :                                   sizeof(ioam_e2e_option_t),
     185             :                                   ioam_e2e_rewrite_handler) < 0)
     186             :     {
     187           0 :       return (clib_error_create("Registration of "
     188             :           "HBH_OPTION_TYPE_IOAM_EDGE_TO_EDGE for rewrite failed"));
     189             :     }
     190             : 
     191         559 :   if (ip6_hbh_flow_handler_register(HBH_OPTION_TYPE_IOAM_EDGE_TO_EDGE,
     192             :                                     ioam_e2e_flow_handler) < 0)
     193             :     {
     194           0 :       return (clib_error_create("Registration of "
     195             :           "HBH_OPTION_TYPE_IOAM_EDGE_TO_EDGE Flow handler failed"));
     196             :     }
     197             : 
     198         559 :   ioam_e2e_main.vlib_main = vm;
     199         559 :   ioam_e2e_main.vnet_main = vnet_get_main();
     200             : 
     201         559 :   return (0);
     202             : }
     203             : 
     204             : /*
     205             :  * Init function for the E2E lib.
     206             :  * ip6_hop_by_hop_ioam_e2e_init gets called during init.
     207             :  */
     208             : /* *INDENT-OFF* */
     209        5039 : VLIB_INIT_FUNCTION (ioam_e2e_init) =
     210             : {
     211             :     .runs_after = VLIB_INITS("ip6_hop_by_hop_ioam_init"),
     212             : };
     213             : /* *INDENT-ON* */

Generated by: LCOV version 1.14