FD.io VPP  v19.04.4-rc0-5-ge88582fac
Vector Packet Processing
qos_record.c
Go to the documentation of this file.
1 /*
2  * Copyright (c) 2018 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 <vnet/qos/qos_record.h>
17 #include <vnet/ip/ip.h>
18 #include <vnet/ip/ip6_to_ip4.h>
19 #include <vnet/feature/feature.h>
20 #include <vnet/qos/qos_types.h>
21 #include <vnet/l2/l2_input.h>
22 #include <vnet/l2/feat_bitmap.h>
23 
24 /**
25  * Per-interface, per-protocol vector of feature on/off configurations
26  */
29 
30 static void
32  qos_source_t input_source, u8 enable)
33 {
34  switch (input_source)
35  {
36  case QOS_SOURCE_IP:
37  vnet_feature_enable_disable ("ip6-unicast", "ip6-qos-record",
38  sw_if_index, enable, NULL, 0);
39  vnet_feature_enable_disable ("ip6-multicast", "ip6-qos-record",
40  sw_if_index, enable, NULL, 0);
41  vnet_feature_enable_disable ("ip4-unicast", "ip4-qos-record",
42  sw_if_index, enable, NULL, 0);
43  vnet_feature_enable_disable ("ip4-multicast", "ip4-qos-record",
44  sw_if_index, enable, NULL, 0);
45  l2input_intf_bitmap_enable (sw_if_index, L2INPUT_FEAT_L2_IP_QOS_RECORD,
46  enable);
47  break;
48  case QOS_SOURCE_MPLS:
49  vnet_feature_enable_disable ("mpls-input", "mpls-qos-record",
50  sw_if_index, enable, NULL, 0);
51  break;
52  case QOS_SOURCE_VLAN:
53  vnet_feature_enable_disable ("ip6-unicast", "vlan-ip6-qos-record",
54  sw_if_index, enable, NULL, 0);
55  vnet_feature_enable_disable ("ip6-multicast", "vlan-ip6-qos-record",
56  sw_if_index, enable, NULL, 0);
57  vnet_feature_enable_disable ("ip4-unicast", "vlan-ip4-qos-record",
58  sw_if_index, enable, NULL, 0);
59  vnet_feature_enable_disable ("ip4-multicast", "vlan-ip4-qos-record",
60  sw_if_index, enable, NULL, 0);
61  vnet_feature_enable_disable ("mpls-input", "vlan-mpls-qos-record",
62  sw_if_index, enable, NULL, 0);
63  break;
64  case QOS_SOURCE_EXT:
65  /* not a valid option for recording */
66  break;
67  }
68 }
69 
70 int
72 {
73  vec_validate (qos_record_configs[input_source], sw_if_index);
74 
75  if (0 == qos_record_configs[input_source][sw_if_index])
76  {
77  qos_record_feature_config (sw_if_index, input_source, 1);
78  }
79 
80  qos_record_configs[input_source][sw_if_index]++;
81  return (0);
82 }
83 
84 int
86 {
87  if (vec_len (qos_record_configs[input_source]) <= sw_if_index)
88  return VNET_API_ERROR_NO_MATCHING_INTERFACE;
89 
90  if (0 == qos_record_configs[input_source][sw_if_index])
91  return VNET_API_ERROR_VALUE_EXIST;
92 
93  qos_record_configs[input_source][sw_if_index]--;
94 
95  if (0 == qos_record_configs[input_source][sw_if_index])
96  {
97  qos_record_feature_config (sw_if_index, input_source, 0);
98  }
99 
100  return (0);
101 }
102 
103 /*
104  * Disable recording feature for all protocols when the interface
105  * is deleted
106  */
107 static clib_error_t *
110 {
111  if (!is_add)
112  {
113  qos_source_t qs;
114 
116  {
117  while (qos_record_disable (sw_if_index, qs) == 0);
118  }
119  }
120 
121  return (NULL);
122 }
123 
125 
126 clib_error_t *
128 {
129  qos_source_t qs;
130  vlib_node_t *node = vlib_get_node_by_name (vm, (u8 *) "l2-ip-qos-record");
131 
132  /* Initialize the feature next-node indexes */
135  node->index,
138  l2_qos_input_next[qs]);
139  return 0;
140 }
141 
143 
144 static clib_error_t *
146  unformat_input_t * input, vlib_cli_command_t * cmd)
147 {
148  vnet_main_t *vnm = vnet_get_main ();
149  u32 sw_if_index, qs;
150  u8 enable;
151 
152  qs = 0xff;
153  enable = 1;
154  sw_if_index = ~0;
155 
157  {
158  if (unformat (input, "%U", unformat_vnet_sw_interface,
159  vnm, &sw_if_index))
160  ;
161  else if (unformat (input, "%U", unformat_qos_source, &qs))
162  ;
163  else if (unformat (input, "enable"))
164  enable = 1;
165  else if (unformat (input, "disable"))
166  enable = 0;
167  else
168  break;
169  }
170 
171  if (~0 == sw_if_index)
172  return clib_error_return (0, "interface must be specified");
173  if (0xff == qs)
174  return clib_error_return (0, "input location must be specified");
175 
176  if (enable)
177  qos_record_enable (sw_if_index, qs);
178  else
179  qos_record_disable (sw_if_index, qs);
180 
181  return (NULL);
182 }
183 
184 /*?
185  * Enable QoS bit recording on an interface using the packet's input DSCP bits
186  * Which input QoS bits to use are either; IP, MPLS or VLAN. If more than
187  * one protocol is chosen (which is foolish) the higher layers override the
188  * lower.
189  *
190  * @cliexpar
191  * @cliexcmd{qos record ip GigEthernet0/1/0}
192  ?*/
193 /* *INDENT-OFF* */
194 VLIB_CLI_COMMAND (qos_record_command, static) = {
195  .path = "qos record",
196  .short_help = "qos record <record-source> <INTERFACE> [disable]",
197  .function = qos_record_cli,
198  .is_mp_safe = 1,
199 };
200 /* *INDENT-ON* */
201 
202 
203 /*
204  * fd.io coding-style-patch-verification: ON
205  *
206  * Local Variables:
207  * eval: (c-set-style "gnu")
208  * End:
209  */
#define vec_validate(V, I)
Make sure vector is long enough for given index (no header, unspecified alignment) ...
Definition: vec.h:439
u32 sw_if_index
Definition: ipsec_gre.api:37
vnet_main_t * vnet_get_main(void)
Definition: misc.c:47
#define NULL
Definition: clib.h:58
u32 index
Definition: node.h:279
VNET_SW_INTERFACE_ADD_DEL_FUNCTION(qos_record_ip_interface_add_del)
u8 * qos_record_configs[QOS_N_SOURCES]
Per-interface, per-protocol vector of feature on/off configurations.
Definition: qos_record.c:27
clib_error_t * l2_ip_qos_init(vlib_main_t *vm)
Definition: qos_record.c:127
unformat_function_t unformat_vnet_sw_interface
unsigned char u8
Definition: types.h:56
Some external source, e.g.
Definition: qos_types.h:35
static clib_error_t * qos_record_cli(vlib_main_t *vm, unformat_input_t *input, vlib_cli_command_t *cmd)
Definition: qos_record.c:145
#define VLIB_INIT_FUNCTION(x)
Definition: init.h:163
#define clib_error_return(e, args...)
Definition: error.h:99
#define FOR_EACH_QOS_SOURCE(_src)
Definition: qos_types.h:54
unsigned int u32
Definition: types.h:88
static clib_error_t * qos_record_ip_interface_add_del(vnet_main_t *vnm, u32 sw_if_index, u32 is_add)
Definition: qos_record.c:108
u32 l2_qos_input_next[QOS_N_SOURCES][32]
Definition: qos_record.c:28
struct _unformat_input_t unformat_input_t
static void qos_record_feature_config(u32 sw_if_index, qos_source_t input_source, u8 enable)
Definition: qos_record.c:31
#define UNFORMAT_END_OF_INPUT
Definition: format.h:144
vlib_main_t * vm
Definition: buffer.c:312
enum qos_source_t_ qos_source_t
QoS types.
static void feat_bitmap_init_next_nodes(vlib_main_t *vm, u32 node_index, u32 num_features, char **feat_names, u32 *next_nodes)
Initialize the feature next-node indexes of a graph node.
Definition: feat_bitmap.h:43
vlib_node_t * vlib_get_node_by_name(vlib_main_t *vm, u8 *name)
Definition: node.c:45
char ** l2input_get_feat_names(void)
Return an array of strings containing graph node names of each feature.
Definition: l2_input.c:62
#define VLIB_CLI_COMMAND(x,...)
Definition: cli.h:155
u8 is_add
Definition: ipsec_gre.api:36
int qos_record_disable(u32 sw_if_index, qos_source_t input_source)
Definition: qos_record.c:85
u32 l2input_intf_bitmap_enable(u32 sw_if_index, l2input_feat_masks_t feature_bitmap, u32 enable)
Enable (or disable) the feature in the bitmap for the given interface.
Definition: l2_input.c:536
IPv6 to IPv4 translation.
#define vec_len(v)
Number of elements in vector (rvalue-only, NULL tolerant)
int qos_record_enable(u32 sw_if_index, qos_source_t input_source)
Definition: qos_record.c:71
uword unformat_qos_source(unformat_input_t *input, va_list *args)
Definition: qos_types.c:35
uword unformat(unformat_input_t *i, const char *fmt,...)
Definition: unformat.c:972
int vnet_feature_enable_disable(const char *arc_name, const char *node_name, u32 sw_if_index, int enable_disable, void *feature_config, u32 n_feature_config_bytes)
Definition: feature.c:274
static uword unformat_check_input(unformat_input_t *i)
Definition: format.h:170
#define QOS_N_SOURCES
The maximum number of sources.
Definition: qos_types.h:45