FD.io VPP  v21.06
Vector Packet Processing
dispatch_wrapper.c
Go to the documentation of this file.
1 /*
2  * Copyright (c) 2020 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 "vppinfra/string.h"
17 #include <vnet/vnet.h>
18 
19 #include <vlibapi/api.h>
20 #include <vlibmemory/api.h>
21 #include <vnet/plugin/plugin.h>
22 #include <vpp/app/version.h>
23 #include <linux/limits.h>
24 #include <sys/ioctl.h>
25 
26 #include <perfmon/perfmon.h>
27 
29 perfmon_read_pmcs (u64 *counters, int *pmc_index, u8 n_counters)
30 {
31  switch (n_counters)
32  {
33  default:
34  case 7:
35  counters[6] = _rdpmc (pmc_index[6]);
36  case 6:
37  counters[5] = _rdpmc (pmc_index[5]);
38  case 5:
39  counters[4] = _rdpmc (pmc_index[4]);
40  case 4:
41  counters[3] = _rdpmc (pmc_index[3]);
42  case 3:
43  counters[2] = _rdpmc (pmc_index[2]);
44  case 2:
45  counters[1] = _rdpmc (pmc_index[1]);
46  case 1:
47  counters[0] = _rdpmc (pmc_index[0]);
48  break;
49  }
50 }
51 
54 {
55  return (int) (tr->mmap_pages[i]->index + tr->mmap_pages[i]->offset);
56 }
57 
60 {
61  return (int) (b->metrics[i]);
62 }
63 
64 uword
67 {
73 
74  u8 n_events = rt->n_events;
75 
76  u64 before[PERF_MAX_EVENTS];
77  u64 after[PERF_MAX_EVENTS];
78  int pmc_index[PERF_MAX_EVENTS];
79  uword rv;
80 
82 
83  switch (n_events)
84  {
85  default:
86  case 7:
87  pmc_index[6] = perfmon_calc_mmap_offset (rt, 6);
88  case 6:
89  pmc_index[5] = perfmon_calc_mmap_offset (rt, 5);
90  case 5:
91  pmc_index[4] = perfmon_calc_mmap_offset (rt, 4);
92  case 4:
93  pmc_index[3] = perfmon_calc_mmap_offset (rt, 3);
94  case 3:
95  pmc_index[2] = perfmon_calc_mmap_offset (rt, 2);
96  case 2:
97  pmc_index[1] = perfmon_calc_mmap_offset (rt, 1);
98  case 1:
99  pmc_index[0] = perfmon_calc_mmap_offset (rt, 0);
100  break;
101  }
102 
103  perfmon_read_pmcs (&before[0], pmc_index, n_events);
104  rv = node->function (vm, node, frame);
105  perfmon_read_pmcs (&after[0], pmc_index, n_events);
106 
107  if (rv == 0)
108  return rv;
109 
110  s->n_calls += 1;
111  s->n_packets += rv;
112 
113  for (int i = 0; i < n_events; i++)
114  s->value[i] += after[i] - before[i];
115 
116  return rv;
117 }
118 
119 uword
122 {
128 
129  u8 n_events = rt->n_events;
130 
131  u64 before[PERF_MAX_EVENTS];
132  int pmc_index[PERF_MAX_EVENTS];
133  uword rv;
134 
135  clib_prefetch_load (s);
136 
137  switch (n_events)
138  {
139  default:
140  case 7:
141  pmc_index[6] = perfmon_metric_index (rt->bundle, 6);
142  case 6:
143  pmc_index[5] = perfmon_metric_index (rt->bundle, 5);
144  case 5:
145  pmc_index[4] = perfmon_metric_index (rt->bundle, 4);
146  case 4:
147  pmc_index[3] = perfmon_metric_index (rt->bundle, 3);
148  case 3:
149  pmc_index[2] = perfmon_metric_index (rt->bundle, 2);
150  case 2:
151  pmc_index[1] = perfmon_metric_index (rt->bundle, 1);
152  case 1:
153  pmc_index[0] = perfmon_metric_index (rt->bundle, 0);
154  break;
155  }
156 
157  perfmon_read_pmcs (&before[0], pmc_index, n_events);
158  rv = node->function (vm, node, frame);
159 
160  clib_memcpy_fast (&s->t[0].value[0], &before, sizeof (before));
161  perfmon_read_pmcs (&s->t[1].value[0], pmc_index, n_events);
162 
163  if (rv == 0)
164  return rv;
165 
166  s->n_calls += 1;
167  s->n_packets += rv;
168 
169  return rv;
170 }
vnet_interface_output_runtime_t * rt
u32 metrics[PERF_MAX_EVENTS]
Definition: perfmon.h:107
static_always_inline void clib_prefetch_load(void *p)
Definition: cache.h:94
Optimized string handling code, including c11-compliant "safe C library" variants.
unsigned long u64
Definition: types.h:89
struct perf_event_mmap_page * mmap_pages[PERF_MAX_EVENTS]
Definition: perfmon.h:150
u32 thread_index
Definition: main.h:213
perfmon_node_stats_t * node_stats
Definition: perfmon.h:148
vlib_main_t vlib_node_runtime_t vlib_frame_t * frame
Definition: nat44_ei.c:3048
perfmon_thread_runtime_t * thread_runtimes
Definition: perfmon.h:155
perfmon_main_t perfmon_main
Definition: perfmon.c:27
unsigned char u8
Definition: types.h:56
vlib_buffer_t ** b
static_always_inline int perfmon_calc_mmap_offset(perfmon_thread_runtime_t *tr, u8 i)
#define static_always_inline
Definition: clib.h:112
vlib_node_function_t * function
Node function to call.
Definition: node.h:459
#define vec_elt_at_index(v, i)
Get vector value at index i checking that i is in bounds.
int __clib_unused rv
Definition: application.c:491
vlib_main_t * vm
X-connect all packets from the HOST to the PHY.
Definition: nat44_ei.c:3047
u32 node_index
Node index.
Definition: node.h:479
uword perfmon_dispatch_wrapper_mmap(vlib_main_t *vm, vlib_node_runtime_t *node, vlib_frame_t *frame)
#define PERF_MAX_EVENTS
Definition: perfmon.h:26
sll srl srl sll sra u16x4 i
Definition: vector_sse42.h:261
u64 value[PERF_MAX_EVENTS]
Definition: perfmon.h:138
static_always_inline void * clib_memcpy_fast(void *restrict dst, const void *restrict src, size_t n)
Definition: string.h:92
static_always_inline void perfmon_read_pmcs(u64 *counters, int *pmc_index, u8 n_counters)
vlib_main_t vlib_node_runtime_t * node
Definition: nat44_ei.c:3047
perfmon_bundle_t * bundle
Definition: perfmon.h:149
u64 uword
Definition: types.h:112
uword perfmon_dispatch_wrapper_metrics(vlib_main_t *vm, vlib_node_runtime_t *node, vlib_frame_t *frame)
static_always_inline int perfmon_metric_index(perfmon_bundle_t *b, u8 i)
struct perfmon_node_stats_t::@759::@761 t[2]