1 /* $Id$ */
2 /*
3 ** Copyright (C) 2014-2021 Cisco and/or its affiliates. All rights reserved.
4 **
5 ** This program is free software; you can redistribute it and/or modify
6 ** it under the terms of the GNU General Public License Version 2 as
7 ** published by the Free Software Foundation. You may not use, modify or
8 ** distribute this program under any other version of the GNU General
9 ** Public License.
10 **
11 ** This program is distributed in the hope that it will be useful,
12 ** but WITHOUT ANY WARRANTY; without even the implied warranty of
13 ** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 ** GNU General Public License for more details.
15 **
16 ** You should have received a copy of the GNU General Public License
17 ** along with this program; if not, write to the Free Software
18 ** Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
19 */
20
21 #include "sf_types.h"
22
23 #include "sfdaq.h"
24
25 #include "perf_indicators.h"
26
27 #ifdef PI_PACKET_LATENCY_SUPPORT
28 static PreprocStats *latencyStats = { NULL };
29 #endif
30
31 static double ticks_per_microsec = 0.0;
32
getTicksPerMicrosec(void)33 static void getTicksPerMicrosec(void)
34 {
35 if (ticks_per_microsec == 0.0)
36 {
37 ticks_per_microsec = get_ticks_per_usec();
38 }
39 }
40
41 #ifdef PI_PACKET_LATENCY_SUPPORT
GetPacketLatency(void)42 uint32_t GetPacketLatency(void)
43 {
44 if( (latencyStats != NULL) && (latencyStats->exits != 0) )
45 {
46 getTicksPerMicrosec();
47
48 /* The exit counter indicate the number of full enter-exit cycles
49 * have been added to the ticks count. */
50 return( (uint32_t)((double)latencyStats->ticks /
51 (double)latencyStats->exits /
52 ticks_per_microsec));
53 }
54 else
55 return( 0 );
56 }
57 #endif
58
59 #ifdef PI_PACKET_DROPS_SUPPORT
GetPacketDropPortion(void)60 double GetPacketDropPortion(void)
61 {
62 uint64_t drop, recv, sum;
63 double portion;
64 const DAQ_Stats_t* ps = DAQ_GetStats();
65
66 /* Debugging code:
67 DAQ_Stats_t test_stats;
68 test_stats.packets_received = 2000;
69 test_stats.hw_packets_dropped = 1050;
70 ps = &test_stats; */
71
72 recv = ps->packets_received;
73 drop = ps->hw_packets_dropped;
74
75 sum = recv + drop;
76
77 if( sum == 0 )
78 portion = 0.0;
79 else
80 portion = ((double)drop / (double)sum);
81
82 return( portion );
83 }
84 #endif
85
86 #ifdef PERF_PROFILING
PerfIndicator_RegisterPreprocStat(PreprocStats * Stats,enum Perf_Indicator_Type Type)87 int PerfIndicator_RegisterPreprocStat( PreprocStats *Stats,
88 enum Perf_Indicator_Type Type )
89 {
90 if( (Stats != NULL) && (Type == Perf_Indicator_Type_Packet_Latency) )
91 {
92 latencyStats = Stats;
93 return( 0 );
94 }
95 else
96 return( -1 );
97 }
98 #endif
99
PerfIndicator_GetIndicators(Perf_Indicator_Descriptor_p_t PI_List)100 int PerfIndicator_GetIndicators( Perf_Indicator_Descriptor_p_t PI_List )
101 {
102 if( PI_List == NULL )
103 return( -1 );
104
105 for( ; PI_List != NULL; PI_List = PI_List->Next )
106 {
107 PI_List->Valid = false;
108 switch( PI_List->Type )
109 {
110 #ifdef PI_PACKET_LATENCY_SUPPORT
111 case( Perf_Indicator_Type_Packet_Latency ):
112 {
113 PI_List->Indicator.Latency.Latency_us = GetPacketLatency();
114 PI_List->Valid = true;
115 break;
116 }
117 #endif
118 #ifdef PI_PROCESSOR_UTILIZATION_SUPPORT
119 case( Perf_Indicator_Type_Processor_Utilization ):
120 {
121 PI_List->Valid = false;
122 break;
123 }
124 #endif
125 #ifdef PI_PACKET_DROPS_SUPPORT
126 case( Perf_Indicator_Type_DAQ_Drops ):
127 {
128 PI_List->Indicator.Drops.Drop_Portion = GetPacketDropPortion();
129 PI_List->Valid = true;
130 break;
131 }
132 #endif
133 default:
134 {
135 return( -1 );
136 }
137 }
138 }
139
140 return( 0 );
141 }
142