blob: 37380034fd2f5b7f4dbf464f378c7eea6e6cfb70 [file] [log] [blame]
Ed Warnickecb9cada2015-12-08 15:45:58 -07001/*
2 * Copyright (c) 2015 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 */
Damjan Marione936bbe2016-02-25 23:17:38 +010015#include <stdint.h>
Ed Warnickecb9cada2015-12-08 15:45:58 -070016#include <vnet/policer/policer.h>
Matus Fabian70e6a8d2016-06-20 08:10:42 -070017#include <vnet/classify/vnet_classify.h>
Ed Warnickecb9cada2015-12-08 15:45:58 -070018
Dave Wallace71612d62017-10-24 01:32:41 -040019vnet_policer_main_t vnet_policer_main;
20
Matus Fabian65fcd4d2016-05-13 05:44:48 -070021clib_error_t *
Damjan Marion3891cd82016-10-27 10:27:00 +020022policer_add_del (vlib_main_t * vm,
23 u8 * name,
24 sse2_qos_pol_cfg_params_st * cfg,
25 u32 * policer_index, u8 is_add)
Matus Fabian65fcd4d2016-05-13 05:44:48 -070026{
27 vnet_policer_main_t *pm = &vnet_policer_main;
28 policer_read_response_type_st test_policer;
Damjan Marion3891cd82016-10-27 10:27:00 +020029 policer_read_response_type_st *policer;
30 uword *p;
Matus Fabian70e6a8d2016-06-20 08:10:42 -070031 u32 pi;
Matus Fabian65fcd4d2016-05-13 05:44:48 -070032 int rv;
33
Matus Fabian70e6a8d2016-06-20 08:10:42 -070034 p = hash_get_mem (pm->policer_config_by_name, name);
35
Matus Fabian65fcd4d2016-05-13 05:44:48 -070036 if (is_add == 0)
37 {
Chaoyu Jin913b8732017-08-08 13:36:23 -070038 /* free policer config and template */
Matus Fabian65fcd4d2016-05-13 05:44:48 -070039 if (p == 0)
Damjan Marion3891cd82016-10-27 10:27:00 +020040 {
41 vec_free (name);
42 return clib_error_return (0, "No such policer configuration");
43 }
Chaoyu Jin913b8732017-08-08 13:36:23 -070044 pool_put_index (pm->configs, p[0]);
45 pool_put_index (pm->policer_templates, p[0]);
Matus Fabian65fcd4d2016-05-13 05:44:48 -070046 hash_unset_mem (pm->policer_config_by_name, name);
Chaoyu Jin913b8732017-08-08 13:36:23 -070047
48 /* free policer */
49 p = hash_get_mem (pm->policer_index_by_name, name);
50 if (p == 0)
51 {
52 vec_free (name);
53 return clib_error_return (0, "No such policer");
54 }
55 pool_put_index (pm->policers, p[0]);
Matus Fabian70e6a8d2016-06-20 08:10:42 -070056 hash_unset_mem (pm->policer_index_by_name, name);
Chaoyu Jin913b8732017-08-08 13:36:23 -070057
Damjan Marion3891cd82016-10-27 10:27:00 +020058 vec_free (name);
Matus Fabian65fcd4d2016-05-13 05:44:48 -070059 return 0;
60 }
61
Matus Fabian70e6a8d2016-06-20 08:10:42 -070062 if (p != 0)
63 {
Damjan Marion3891cd82016-10-27 10:27:00 +020064 vec_free (name);
Matus Fabian70e6a8d2016-06-20 08:10:42 -070065 return clib_error_return (0, "Policer already exists");
66 }
67
Matus Fabian65fcd4d2016-05-13 05:44:48 -070068 /* Vet the configuration before adding it to the table */
69 rv = sse2_pol_logical_2_physical (cfg, &test_policer);
70
71 if (rv == 0)
72 {
73 policer_read_response_type_st *pp;
74 sse2_qos_pol_cfg_params_st *cp;
75
76 pool_get (pm->configs, cp);
77 pool_get (pm->policer_templates, pp);
78
79 ASSERT (cp - pm->configs == pp - pm->policer_templates);
80
81 clib_memcpy (cp, cfg, sizeof (*cp));
82 clib_memcpy (pp, &test_policer, sizeof (*pp));
83
84 hash_set_mem (pm->policer_config_by_name, name, cp - pm->configs);
Matus Fabian70e6a8d2016-06-20 08:10:42 -070085 pool_get_aligned (pm->policers, policer, CLIB_CACHE_LINE_BYTES);
86 policer[0] = pp[0];
87 pi = policer - pm->policers;
88 hash_set_mem (pm->policer_index_by_name, name, pi);
89 *policer_index = pi;
Matus Fabian65fcd4d2016-05-13 05:44:48 -070090 }
91 else
92 {
93 vec_free (name);
94 return clib_error_return (0, "Config failed sanity check");
95 }
96
97 return 0;
98}
99
Damjan Marion3891cd82016-10-27 10:27:00 +0200100u8 *
101format_policer_instance (u8 * s, va_list * va)
Ed Warnickecb9cada2015-12-08 15:45:58 -0700102{
Damjan Marion3891cd82016-10-27 10:27:00 +0200103 policer_read_response_type_st *i
Ed Warnickecb9cada2015-12-08 15:45:58 -0700104 = va_arg (*va, policer_read_response_type_st *);
105
Damjan Marion3891cd82016-10-27 10:27:00 +0200106 s = format (s, "policer at %llx: %s rate, %s color-aware\n",
107 i, i->single_rate ? "single" : "dual",
108 i->color_aware ? "is" : "not");
Ed Warnickecb9cada2015-12-08 15:45:58 -0700109 s = format (s, "cir %u tok/period, pir %u tok/period, scale %u\n",
Damjan Marion3891cd82016-10-27 10:27:00 +0200110 i->cir_tokens_per_period, i->pir_tokens_per_period, i->scale);
Ed Warnickecb9cada2015-12-08 15:45:58 -0700111 s = format (s, "cur lim %u, cur bkt %u, ext lim %u, ext bkt %u\n",
Damjan Marion3891cd82016-10-27 10:27:00 +0200112 i->current_limit,
113 i->current_bucket, i->extended_limit, i->extended_bucket);
Ed Warnickecb9cada2015-12-08 15:45:58 -0700114 s = format (s, "last update %llu\n", i->last_update_time);
115 return s;
Damjan Marion3891cd82016-10-27 10:27:00 +0200116}
Ed Warnickecb9cada2015-12-08 15:45:58 -0700117
Damjan Marion3891cd82016-10-27 10:27:00 +0200118static u8 *
119format_policer_round_type (u8 * s, va_list * va)
Ed Warnickecb9cada2015-12-08 15:45:58 -0700120{
Damjan Marion3891cd82016-10-27 10:27:00 +0200121 sse2_qos_pol_cfg_params_st *c = va_arg (*va, sse2_qos_pol_cfg_params_st *);
Ed Warnickecb9cada2015-12-08 15:45:58 -0700122
123 if (c->rnd_type == SSE2_QOS_ROUND_TO_CLOSEST)
Damjan Marion3891cd82016-10-27 10:27:00 +0200124 s = format (s, "closest");
Ed Warnickecb9cada2015-12-08 15:45:58 -0700125 else if (c->rnd_type == SSE2_QOS_ROUND_TO_UP)
126 s = format (s, "up");
127 else if (c->rnd_type == SSE2_QOS_ROUND_TO_DOWN)
128 s = format (s, "down");
129 else
130 s = format (s, "ILLEGAL");
131 return s;
132}
133
134
Damjan Marion3891cd82016-10-27 10:27:00 +0200135static u8 *
136format_policer_rate_type (u8 * s, va_list * va)
Ed Warnickecb9cada2015-12-08 15:45:58 -0700137{
Damjan Marion3891cd82016-10-27 10:27:00 +0200138 sse2_qos_pol_cfg_params_st *c = va_arg (*va, sse2_qos_pol_cfg_params_st *);
Ed Warnickecb9cada2015-12-08 15:45:58 -0700139
140 if (c->rate_type == SSE2_QOS_RATE_KBPS)
141 s = format (s, "kbps");
142 else if (c->rate_type == SSE2_QOS_RATE_PPS)
Damjan Marion3891cd82016-10-27 10:27:00 +0200143 s = format (s, "pps");
Ed Warnickecb9cada2015-12-08 15:45:58 -0700144 else
145 s = format (s, "ILLEGAL");
146 return s;
147}
148
Damjan Marion3891cd82016-10-27 10:27:00 +0200149static u8 *
150format_policer_type (u8 * s, va_list * va)
Ed Warnickecb9cada2015-12-08 15:45:58 -0700151{
Damjan Marion3891cd82016-10-27 10:27:00 +0200152 sse2_qos_pol_cfg_params_st *c = va_arg (*va, sse2_qos_pol_cfg_params_st *);
153
Ed Warnickecb9cada2015-12-08 15:45:58 -0700154 if (c->rfc == SSE2_QOS_POLICER_TYPE_1R2C)
155 s = format (s, "1r2c");
Damjan Marion3891cd82016-10-27 10:27:00 +0200156
Ed Warnickecb9cada2015-12-08 15:45:58 -0700157 else if (c->rfc == SSE2_QOS_POLICER_TYPE_1R3C_RFC_2697)
158 s = format (s, "1r3c");
159
160 else if (c->rfc == SSE2_QOS_POLICER_TYPE_2R3C_RFC_2698)
161 s = format (s, "2r3c-2698");
162
163 else if (c->rfc == SSE2_QOS_POLICER_TYPE_2R3C_RFC_4115)
164 s = format (s, "2r3c-4115");
165
166 else if (c->rfc == SSE2_QOS_POLICER_TYPE_2R3C_RFC_MEF5CF1)
167 s = format (s, "2r3c-mef5cf1");
168 else
169 s = format (s, "ILLEGAL");
170 return s;
171}
172
Damjan Marion3891cd82016-10-27 10:27:00 +0200173static u8 *
174format_dscp (u8 * s, va_list * va)
Matus Fabian4ac74c92016-05-31 07:33:29 -0700175{
176 u32 i = va_arg (*va, u32);
Damjan Marion3891cd82016-10-27 10:27:00 +0200177 char *t = 0;
Matus Fabian4ac74c92016-05-31 07:33:29 -0700178
Damjan Marion3891cd82016-10-27 10:27:00 +0200179 switch (i)
180 {
181#define _(v,f,str) case VNET_DSCP_##f: t = str; break;
182 foreach_vnet_dscp
183#undef _
Matus Fabian4ac74c92016-05-31 07:33:29 -0700184 default:
185 return format (s, "ILLEGAL");
Damjan Marion3891cd82016-10-27 10:27:00 +0200186 }
Matus Fabian4ac74c92016-05-31 07:33:29 -0700187 s = format (s, "%s", t);
188 return s;
189}
190
Damjan Marion3891cd82016-10-27 10:27:00 +0200191static u8 *
192format_policer_action_type (u8 * s, va_list * va)
Matus Fabian4ac74c92016-05-31 07:33:29 -0700193{
Damjan Marion3891cd82016-10-27 10:27:00 +0200194 sse2_qos_pol_action_params_st *a
Matus Fabian4ac74c92016-05-31 07:33:29 -0700195 = va_arg (*va, sse2_qos_pol_action_params_st *);
196
197 if (a->action_type == SSE2_QOS_ACTION_DROP)
198 s = format (s, "drop");
199 else if (a->action_type == SSE2_QOS_ACTION_TRANSMIT)
200 s = format (s, "transmit");
201 else if (a->action_type == SSE2_QOS_ACTION_MARK_AND_TRANSMIT)
202 s = format (s, "mark-and-transmit %U", format_dscp, a->dscp);
203 else
204 s = format (s, "ILLEGAL");
205 return s;
206}
207
Damjan Marion3891cd82016-10-27 10:27:00 +0200208u8 *
209format_policer_config (u8 * s, va_list * va)
Ed Warnickecb9cada2015-12-08 15:45:58 -0700210{
Damjan Marion3891cd82016-10-27 10:27:00 +0200211 sse2_qos_pol_cfg_params_st *c = va_arg (*va, sse2_qos_pol_cfg_params_st *);
Ed Warnickecb9cada2015-12-08 15:45:58 -0700212
213 s = format (s, "type %U cir %u eir %u cb %u eb %u\n",
Damjan Marion3891cd82016-10-27 10:27:00 +0200214 format_policer_type, c,
215 c->rb.kbps.cir_kbps,
216 c->rb.kbps.eir_kbps, c->rb.kbps.cb_bytes, c->rb.kbps.eb_bytes);
Ed Warnickecb9cada2015-12-08 15:45:58 -0700217 s = format (s, "rate type %U, round type %U\n",
Damjan Marion3891cd82016-10-27 10:27:00 +0200218 format_policer_rate_type, c, format_policer_round_type, c);
Matus Fabian4ac74c92016-05-31 07:33:29 -0700219 s = format (s, "conform action %U, exceed action %U, violate action %U\n",
Damjan Marion3891cd82016-10-27 10:27:00 +0200220 format_policer_action_type, &c->conform_action,
221 format_policer_action_type, &c->exceed_action,
222 format_policer_action_type, &c->violate_action);
Ed Warnickecb9cada2015-12-08 15:45:58 -0700223 return s;
224}
225
226static uword
227unformat_policer_type (unformat_input_t * input, va_list * va)
228{
Damjan Marion3891cd82016-10-27 10:27:00 +0200229 sse2_qos_pol_cfg_params_st *c = va_arg (*va, sse2_qos_pol_cfg_params_st *);
Ed Warnickecb9cada2015-12-08 15:45:58 -0700230
231 if (!unformat (input, "type"))
232 return 0;
233
234 if (unformat (input, "1r2c"))
235 c->rfc = SSE2_QOS_POLICER_TYPE_1R2C;
236 else if (unformat (input, "1r3c"))
237 c->rfc = SSE2_QOS_POLICER_TYPE_1R3C_RFC_2697;
238 else if (unformat (input, "2r3c-2698"))
239 c->rfc = SSE2_QOS_POLICER_TYPE_2R3C_RFC_2698;
240 else if (unformat (input, "2r3c-4115"))
241 c->rfc = SSE2_QOS_POLICER_TYPE_2R3C_RFC_4115;
242 else if (unformat (input, "2r3c-mef5cf1"))
243 c->rfc = SSE2_QOS_POLICER_TYPE_2R3C_RFC_MEF5CF1;
244 else
245 return 0;
246 return 1;
247}
248
249static uword
250unformat_policer_round_type (unformat_input_t * input, va_list * va)
251{
Damjan Marion3891cd82016-10-27 10:27:00 +0200252 sse2_qos_pol_cfg_params_st *c = va_arg (*va, sse2_qos_pol_cfg_params_st *);
Ed Warnickecb9cada2015-12-08 15:45:58 -0700253
Damjan Marion3891cd82016-10-27 10:27:00 +0200254 if (!unformat (input, "round"))
Ed Warnickecb9cada2015-12-08 15:45:58 -0700255 return 0;
256
Damjan Marion3891cd82016-10-27 10:27:00 +0200257 if (unformat (input, "closest"))
Ed Warnickecb9cada2015-12-08 15:45:58 -0700258 c->rnd_type = SSE2_QOS_ROUND_TO_CLOSEST;
259 else if (unformat (input, "up"))
260 c->rnd_type = SSE2_QOS_ROUND_TO_UP;
261 else if (unformat (input, "down"))
262 c->rnd_type = SSE2_QOS_ROUND_TO_DOWN;
263 else
264 return 0;
265 return 1;
266}
267
268static uword
269unformat_policer_rate_type (unformat_input_t * input, va_list * va)
270{
Damjan Marion3891cd82016-10-27 10:27:00 +0200271 sse2_qos_pol_cfg_params_st *c = va_arg (*va, sse2_qos_pol_cfg_params_st *);
Ed Warnickecb9cada2015-12-08 15:45:58 -0700272
Damjan Marion3891cd82016-10-27 10:27:00 +0200273 if (!unformat (input, "rate"))
Ed Warnickecb9cada2015-12-08 15:45:58 -0700274 return 0;
275
276 if (unformat (input, "kbps"))
277 c->rate_type = SSE2_QOS_RATE_KBPS;
Damjan Marion3891cd82016-10-27 10:27:00 +0200278 else if (unformat (input, "pps"))
Ed Warnickecb9cada2015-12-08 15:45:58 -0700279 c->rate_type = SSE2_QOS_RATE_PPS;
280 else
281 return 0;
282 return 1;
283}
284
285static uword
286unformat_policer_cir (unformat_input_t * input, va_list * va)
287{
Damjan Marion3891cd82016-10-27 10:27:00 +0200288 sse2_qos_pol_cfg_params_st *c = va_arg (*va, sse2_qos_pol_cfg_params_st *);
Ed Warnickecb9cada2015-12-08 15:45:58 -0700289
290 if (unformat (input, "cir %u", &c->rb.kbps.cir_kbps))
291 return 1;
292 return 0;
293}
294
295static uword
296unformat_policer_eir (unformat_input_t * input, va_list * va)
297{
Damjan Marion3891cd82016-10-27 10:27:00 +0200298 sse2_qos_pol_cfg_params_st *c = va_arg (*va, sse2_qos_pol_cfg_params_st *);
Ed Warnickecb9cada2015-12-08 15:45:58 -0700299
300 if (unformat (input, "eir %u", &c->rb.kbps.eir_kbps))
301 return 1;
302 return 0;
303}
304
305static uword
306unformat_policer_cb (unformat_input_t * input, va_list * va)
307{
Damjan Marion3891cd82016-10-27 10:27:00 +0200308 sse2_qos_pol_cfg_params_st *c = va_arg (*va, sse2_qos_pol_cfg_params_st *);
Ed Warnickecb9cada2015-12-08 15:45:58 -0700309
310 if (unformat (input, "cb %u", &c->rb.kbps.cb_bytes))
311 return 1;
312 return 0;
313}
314
315static uword
316unformat_policer_eb (unformat_input_t * input, va_list * va)
317{
Damjan Marion3891cd82016-10-27 10:27:00 +0200318 sse2_qos_pol_cfg_params_st *c = va_arg (*va, sse2_qos_pol_cfg_params_st *);
Ed Warnickecb9cada2015-12-08 15:45:58 -0700319
320 if (unformat (input, "eb %u", &c->rb.kbps.eb_bytes))
321 return 1;
322 return 0;
323}
324
Matus Fabian4ac74c92016-05-31 07:33:29 -0700325static uword
326unformat_dscp (unformat_input_t * input, va_list * va)
327{
Damjan Marion3891cd82016-10-27 10:27:00 +0200328 u8 *r = va_arg (*va, u8 *);
Matus Fabian4ac74c92016-05-31 07:33:29 -0700329
Damjan Marion3891cd82016-10-27 10:27:00 +0200330 if (0);
Matus Fabian4ac74c92016-05-31 07:33:29 -0700331#define _(v,f,str) else if (unformat (input, str)) *r = VNET_DSCP_##f;
Damjan Marion3891cd82016-10-27 10:27:00 +0200332 foreach_vnet_dscp
Matus Fabian4ac74c92016-05-31 07:33:29 -0700333#undef _
Damjan Marion3891cd82016-10-27 10:27:00 +0200334 else
Matus Fabian4ac74c92016-05-31 07:33:29 -0700335 return 0;
336 return 1;
337}
338
339static uword
340unformat_policer_action_type (unformat_input_t * input, va_list * va)
341{
Damjan Marion3891cd82016-10-27 10:27:00 +0200342 sse2_qos_pol_action_params_st *a
Matus Fabian4ac74c92016-05-31 07:33:29 -0700343 = va_arg (*va, sse2_qos_pol_action_params_st *);
344
345 if (unformat (input, "drop"))
346 a->action_type = SSE2_QOS_ACTION_DROP;
347 else if (unformat (input, "transmit"))
348 a->action_type = SSE2_QOS_ACTION_TRANSMIT;
349 else if (unformat (input, "mark-and-transmit %U", unformat_dscp, &a->dscp))
350 a->action_type = SSE2_QOS_ACTION_MARK_AND_TRANSMIT;
351 else
352 return 0;
353 return 1;
354}
355
356static uword
357unformat_policer_action (unformat_input_t * input, va_list * va)
358{
Damjan Marion3891cd82016-10-27 10:27:00 +0200359 sse2_qos_pol_cfg_params_st *c = va_arg (*va, sse2_qos_pol_cfg_params_st *);
Matus Fabian4ac74c92016-05-31 07:33:29 -0700360
361 if (unformat (input, "conform-action %U", unformat_policer_action_type,
Damjan Marion3891cd82016-10-27 10:27:00 +0200362 &c->conform_action))
Matus Fabian4ac74c92016-05-31 07:33:29 -0700363 return 1;
364 else if (unformat (input, "exceed-action %U", unformat_policer_action_type,
Damjan Marion3891cd82016-10-27 10:27:00 +0200365 &c->exceed_action))
Matus Fabian4ac74c92016-05-31 07:33:29 -0700366 return 1;
367 else if (unformat (input, "violate-action %U", unformat_policer_action_type,
Damjan Marion3891cd82016-10-27 10:27:00 +0200368 &c->violate_action))
Matus Fabian4ac74c92016-05-31 07:33:29 -0700369 return 1;
370 return 0;
371}
Ed Warnickecb9cada2015-12-08 15:45:58 -0700372
Matus Fabian70e6a8d2016-06-20 08:10:42 -0700373static uword
374unformat_policer_classify_next_index (unformat_input_t * input, va_list * va)
375{
Damjan Marion3891cd82016-10-27 10:27:00 +0200376 u32 *r = va_arg (*va, u32 *);
Matus Fabian70e6a8d2016-06-20 08:10:42 -0700377 vnet_policer_main_t *pm = &vnet_policer_main;
Damjan Marion3891cd82016-10-27 10:27:00 +0200378 uword *p;
379 u8 *match_name = 0;
Matus Fabian70e6a8d2016-06-20 08:10:42 -0700380
381 if (unformat (input, "%s", &match_name))
382 ;
383 else
384 return 0;
385
386 p = hash_get_mem (pm->policer_index_by_name, match_name);
387
388 if (p == 0)
389 return 0;
390
391 *r = p[0];
392
393 return 1;
394}
395
396static uword
397unformat_policer_classify_precolor (unformat_input_t * input, va_list * va)
398{
Damjan Marion3891cd82016-10-27 10:27:00 +0200399 u32 *r = va_arg (*va, u32 *);
Matus Fabian70e6a8d2016-06-20 08:10:42 -0700400
401 if (unformat (input, "conform-color"))
402 *r = POLICE_CONFORM;
403 else if (unformat (input, "exceed-color"))
404 *r = POLICE_EXCEED;
405 else
406 return 0;
407
408 return 1;
409}
410
Ed Warnickecb9cada2015-12-08 15:45:58 -0700411#define foreach_config_param \
412_(eb) \
413_(cb) \
414_(eir) \
415_(cir) \
416_(rate_type) \
417_(round_type) \
Matus Fabian4ac74c92016-05-31 07:33:29 -0700418_(type) \
419_(action)
Ed Warnickecb9cada2015-12-08 15:45:58 -0700420
421static clib_error_t *
422configure_policer_command_fn (vlib_main_t * vm,
Damjan Marion3891cd82016-10-27 10:27:00 +0200423 unformat_input_t * input,
424 vlib_cli_command_t * cmd)
Ed Warnickecb9cada2015-12-08 15:45:58 -0700425{
Ed Warnickecb9cada2015-12-08 15:45:58 -0700426 sse2_qos_pol_cfg_params_st c;
Damjan Marion3891cd82016-10-27 10:27:00 +0200427 unformat_input_t _line_input, *line_input = &_line_input;
Matus Fabian65fcd4d2016-05-13 05:44:48 -0700428 u8 is_add = 1;
Damjan Marion3891cd82016-10-27 10:27:00 +0200429 u8 *name = 0;
Matus Fabian70e6a8d2016-06-20 08:10:42 -0700430 u32 pi;
Billy McFalla9a20e72017-02-15 11:39:12 -0500431 clib_error_t *error = NULL;
Ed Warnickecb9cada2015-12-08 15:45:58 -0700432
433 /* Get a line of input. */
Damjan Marion3891cd82016-10-27 10:27:00 +0200434 if (!unformat_user (input, unformat_line_input, line_input))
Ed Warnickecb9cada2015-12-08 15:45:58 -0700435 return 0;
436
437 memset (&c, 0, sizeof (c));
438
Damjan Marion3891cd82016-10-27 10:27:00 +0200439 while (unformat_check_input (line_input) != UNFORMAT_END_OF_INPUT)
Ed Warnickecb9cada2015-12-08 15:45:58 -0700440 {
441 if (unformat (line_input, "del"))
Damjan Marion3891cd82016-10-27 10:27:00 +0200442 is_add = 0;
443 else if (unformat (line_input, "name %s", &name))
444 ;
445 else if (unformat (line_input, "color-aware"))
446 c.color_aware = 1;
Ed Warnickecb9cada2015-12-08 15:45:58 -0700447
448#define _(a) else if (unformat (line_input, "%U", unformat_policer_##a, &c)) ;
449 foreach_config_param
450#undef _
Damjan Marion3891cd82016-10-27 10:27:00 +0200451 else
Billy McFalla9a20e72017-02-15 11:39:12 -0500452 {
453 error = clib_error_return (0, "unknown input `%U'",
454 format_unformat_error, line_input);
455 goto done;
456 }
Ed Warnickecb9cada2015-12-08 15:45:58 -0700457 }
458
Billy McFalla9a20e72017-02-15 11:39:12 -0500459 error = policer_add_del (vm, name, &c, &pi, is_add);
460
461done:
Ed Warnickecb9cada2015-12-08 15:45:58 -0700462 unformat_free (line_input);
463
Billy McFalla9a20e72017-02-15 11:39:12 -0500464 return error;
Ed Warnickecb9cada2015-12-08 15:45:58 -0700465}
466
Damjan Marion3891cd82016-10-27 10:27:00 +0200467/* *INDENT-OFF* */
Ed Warnickecb9cada2015-12-08 15:45:58 -0700468VLIB_CLI_COMMAND (configure_policer_command, static) = {
469 .path = "configure policer",
470 .short_help = "configure policer name <name> <params> ",
471 .function = configure_policer_command_fn,
472};
Damjan Marion3891cd82016-10-27 10:27:00 +0200473/* *INDENT-ON* */
Ed Warnickecb9cada2015-12-08 15:45:58 -0700474
475static clib_error_t *
476show_policer_command_fn (vlib_main_t * vm,
Damjan Marion3891cd82016-10-27 10:27:00 +0200477 unformat_input_t * input, vlib_cli_command_t * cmd)
Ed Warnickecb9cada2015-12-08 15:45:58 -0700478{
479 vnet_policer_main_t *pm = &vnet_policer_main;
Damjan Marion3891cd82016-10-27 10:27:00 +0200480 hash_pair_t *p;
Ed Warnickecb9cada2015-12-08 15:45:58 -0700481 u32 pool_index;
Damjan Marion3891cd82016-10-27 10:27:00 +0200482 u8 *match_name = 0;
483 u8 *name;
Ed Warnickecb9cada2015-12-08 15:45:58 -0700484 sse2_qos_pol_cfg_params_st *config;
485 policer_read_response_type_st *templ;
486
487 (void) unformat (input, "name %s", &match_name);
488
Damjan Marion3891cd82016-10-27 10:27:00 +0200489 /* *INDENT-OFF* */
Ed Warnickecb9cada2015-12-08 15:45:58 -0700490 hash_foreach_pair (p, pm->policer_config_by_name,
491 ({
492 name = (u8 *) p->key;
493 if (match_name == 0 || !strcmp((char *) name, (char *) match_name))
494 {
495 pool_index = p->value[0];
496 config = pool_elt_at_index (pm->configs, pool_index);
497 templ = pool_elt_at_index (pm->policer_templates, pool_index);
Damjan Marion3891cd82016-10-27 10:27:00 +0200498 vlib_cli_output (vm, "Name \"%s\" %U ",
Ed Warnickecb9cada2015-12-08 15:45:58 -0700499 name, format_policer_config, config);
Damjan Marion3891cd82016-10-27 10:27:00 +0200500 vlib_cli_output (vm, "Template %U",
Ed Warnickecb9cada2015-12-08 15:45:58 -0700501 format_policer_instance, templ);
502 vlib_cli_output (vm, "-----------");
503 }
504 }));
Damjan Marion3891cd82016-10-27 10:27:00 +0200505 /* *INDENT-ON* */
Ed Warnickecb9cada2015-12-08 15:45:58 -0700506 return 0;
507}
508
509
Damjan Marion3891cd82016-10-27 10:27:00 +0200510/* *INDENT-OFF* */
Ed Warnickecb9cada2015-12-08 15:45:58 -0700511VLIB_CLI_COMMAND (show_policer_command, static) = {
512 .path = "show policer",
513 .short_help = "show policer [name]",
514 .function = show_policer_command_fn,
515};
Damjan Marion3891cd82016-10-27 10:27:00 +0200516/* *INDENT-ON* */
Ed Warnickecb9cada2015-12-08 15:45:58 -0700517
Chaoyu Jin913b8732017-08-08 13:36:23 -0700518static clib_error_t *
519show_policer_pools_command_fn (vlib_main_t * vm,
520 unformat_input_t * input,
521 vlib_cli_command_t * cmd)
522{
523 vnet_policer_main_t *pm = &vnet_policer_main;
524
525 vlib_cli_output (vm, "pool sizes: configs=%d templates=%d policers=%d",
526 pool_elts (pm->configs),
527 pool_elts (pm->policer_templates),
528 pool_elts (pm->policers));
529 return 0;
530}
531/* *INDENT-OFF* */
532VLIB_CLI_COMMAND (show_policer_pools_command, static) = {
533 .path = "show policer pools",
534 .short_help = "show policer pools",
535 .function = show_policer_pools_command_fn,
536};
537/* *INDENT-ON* */
538
Damjan Marion3891cd82016-10-27 10:27:00 +0200539clib_error_t *
540policer_init (vlib_main_t * vm)
Ed Warnickecb9cada2015-12-08 15:45:58 -0700541{
Damjan Marion3891cd82016-10-27 10:27:00 +0200542 vnet_policer_main_t *pm = &vnet_policer_main;
543 void vnet_policer_node_funcs_reference (void);
Ed Warnickecb9cada2015-12-08 15:45:58 -0700544
Damjan Marion3891cd82016-10-27 10:27:00 +0200545 vnet_policer_node_funcs_reference ();
546
Ed Warnickecb9cada2015-12-08 15:45:58 -0700547 pm->vlib_main = vm;
Damjan Marion3891cd82016-10-27 10:27:00 +0200548 pm->vnet_main = vnet_get_main ();
Ed Warnickecb9cada2015-12-08 15:45:58 -0700549
550 pm->policer_config_by_name = hash_create_string (0, sizeof (uword));
Matus Fabian70e6a8d2016-06-20 08:10:42 -0700551 pm->policer_index_by_name = hash_create_string (0, sizeof (uword));
552
553 vnet_classify_register_unformat_policer_next_index_fn
554 (unformat_policer_classify_next_index);
555 vnet_classify_register_unformat_opaque_index_fn
556 (unformat_policer_classify_precolor);
557
Ed Warnickecb9cada2015-12-08 15:45:58 -0700558 return 0;
559}
560
Damjan Marion3891cd82016-10-27 10:27:00 +0200561VLIB_INIT_FUNCTION (policer_init);
Ed Warnickecb9cada2015-12-08 15:45:58 -0700562
563
Damjan Marion3891cd82016-10-27 10:27:00 +0200564
565/*
566 * fd.io coding-style-patch-verification: ON
567 *
568 * Local Variables:
569 * eval: (c-set-style "gnu")
570 * End:
571 */