1 /*
2 ** $Id$
3 **
4 ** perf-base.c
5 **
6 ** Copyright (C) 2014-2021 Cisco and/or its affiliates. All rights reserved.
7 ** Copyright (C) 2002-2013 Sourcefire, Inc.
8 ** Dan Roelker <droelker@sourcefire.com>
9 ** Marc Norton <mnorton@sourcefire.com>
10 **
11 ** This program is free software; you can redistribute it and/or modify
12 ** it under the terms of the GNU General Public License Version 2 as
13 ** published by the Free Software Foundation. You may not use, modify or
14 ** distribute this program under any other version of the GNU General
15 ** Public License.
16 **
17 ** This program is distributed in the hope that it will be useful,
18 ** but WITHOUT ANY WARRANTY; without even the implied warranty of
19 ** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
20 ** GNU General Public License for more details.
21 **
22 ** You should have received a copy of the GNU General Public License
23 ** along with this program; if not, write to the Free Software
24 ** Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
25 **
26 ** DESCRIPTION
27 ** The following subroutines are concerned with getting
28 ** basic stats on packet bytes and times that an app
29 ** takes in processing packets. The times measured are
30 ** kernel and user time for the process. Real-time
31 ** (wall clock) is also measured to show when processing
32 ** has reached capacity and to measure the true processing
33 ** that the app is currently doing.
34 **
35 ** NOTES
36 ** 4.8.02 : Initial Code (DJR,MAN)
37 ** 4.22.02 : Added Comments (DJR)
38 ** 7.10.02 : Added sfprocpidstats code for SMP linux (DJR)
39 ** 8.8.02 : Added stream4 instrumentation (cmg)
40 ** 9.1.04 : Removed NO_PKTS, ACCUMULATE/RESET #defines, now we use SFBASE->iReset
41 ** and the permonitor command has 'reset' and 'accrue' commands instead.(MAN)
42 ** 10.4.06 : Added UDP Session Stats (SAS)
43 ** 4.3.07 : Added stats for TCP sessions (SAS)
44 */
45
46 #include <time.h>
47 #ifndef WIN32
48 #include <sys/time.h>
49 #include <sys/resource.h>
50 #endif
51 #include <stdlib.h>
52 #include <stdio.h>
53 #include <math.h>
54 #include <sys/types.h>
55
56 #ifdef HAVE_CONFIG_H
57 #include "config.h"
58 #endif
59
60 #include "sf_types.h"
61 #include "snort.h"
62 #include "util.h"
63 #include "mpse.h"
64 #include "sfdaq.h"
65 #include "session_api.h"
66 #include "stream_api.h"
67 #include "sf_types.h"
68 #include "snort_bounds.h"
69
70
71 static void GetPktDropStats(SFBASE *, SFBASE_STATS *);
72 static void DisplayBasePerfStatsConsole(SFBASE_STATS *, int);
73 static int CalculateBasePerfStats(SFBASE *, SFBASE_STATS *, int);
74 static void LogBasePerfStats(SFBASE_STATS *, FILE *);
75 static void GetPacketsPerSecond(SFBASE *, SFBASE_STATS *, SYSTIMES *, int);
76 static void GetMbitsPerSecond(SFBASE *, SFBASE_STATS *, SYSTIMES *, int);
77 static int GetProcessingTime(SYSTIMES *, SFBASE *);
78 static void GetEventsPerSecond(SFBASE *, SFBASE_STATS *, SYSTIMES *);
79 static void GetuSecondsPerPacket(SFBASE *, SFBASE_STATS *, SYSTIMES *);
80 static void GetCPUTime(SFBASE *, SFBASE_STATS *, SYSTIMES *);
81
82
83 //We should never output NaN or Infitity
zeroFpException(double in)84 static inline double zeroFpException(double in)
85 {
86 //FIXME WIN32 -vc++6 does NOT provide the function |isnan() | nor |isinf()| - VJR 7/22/15
87 // (see also:http://stackoverflow.com/questions/2249110/how-do-i-make-a-portable-isnan-isinf-function)
88 #ifndef WIN32
89 if (isnan(in) || isinf(in))
90 return 0.0;
91 #endif
92 return in;
93 }
94
95 /*
96 ** NAME
97 ** InitBaseStats
98 ** DESCRIPTION
99 ** Initializes structs and variables for the next performance
100 ** sample.
101 **
102 ** FORMAL INPUTS
103 ** SFBASE * -- pointer to structure to initialize
104 **
105 ** FORMAL OUTPUTS
106 ** int -- 0 is successful
107 */
InitBaseStats(SFBASE * sfBase)108 int InitBaseStats(SFBASE *sfBase)
109 {
110 int todRet = -1;
111 struct timeval tvTime;
112
113 #ifndef WIN32
114 #ifndef LINUX_SMP
115 struct rusage rusage;
116 int rusageRet = -1;
117 #endif
118
119 #ifdef LINUX_SMP
120 todRet = gettimeofday(&tvTime, NULL);
121 #else
122
123 rusageRet = getrusage(RUSAGE_SELF, &rusage);
124 todRet = gettimeofday(&tvTime, NULL);
125
126 if (rusageRet >= 0)
127 {
128 sfBase->usertime_sec = (double)rusage.ru_utime.tv_sec +
129 ((double)rusage.ru_utime.tv_usec * 1.0e-6);
130 sfBase->systemtime_sec = (double)rusage.ru_stime.tv_sec +
131 ((double)rusage.ru_stime.tv_usec * 1.0e-6);
132 }
133 else
134 {
135 sfBase->usertime_sec = 0;
136 sfBase->systemtime_sec = 0;
137 }
138
139 #endif /* !LINUX_SMP */
140 #else
141 sfBase->usertime_sec = 0;
142 sfBase->systemtime_sec = 0;
143 todRet = gettimeofday(&tvTime, NULL);
144 #endif /* !WIN32 */
145
146 if(todRet >= 0)
147 {
148 sfBase->realtime_sec = (double)tvTime.tv_sec +
149 ((double)tvTime.tv_usec * 1.0e-6);
150 }
151 else
152 {
153 sfBase->realtime_sec = 0;
154 }
155
156 sfBase->total_blocked_packets = 0;
157 sfBase->total_injected_packets = 0;
158 sfBase->total_wire_packets = 0;
159 sfBase->total_ipfragmented_packets = 0;
160 sfBase->total_ipreassembled_packets = 0;
161 sfBase->total_packets = 0;
162 sfBase->total_rebuilt_packets = 0;
163
164 sfBase->total_wire_bytes = 0;
165 sfBase->total_ipfragmented_bytes = 0;
166 sfBase->total_ipreassembled_bytes = 0;
167 sfBase->total_bytes = 0;
168 sfBase->total_rebuilt_bytes = 0;
169 sfBase->total_blocked_bytes = 0;
170
171 sfBase->iNewSessions = 0;
172 sfBase->iDeletedSessions = 0;
173
174 sfBase->iStreamFlushes = 0;
175 sfBase->iStreamFaults = 0;
176 sfBase->iStreamTimeouts = 0;
177 //sfBase->iMaxSessions = 0;
178 //sfBase->iMaxSessionsInterval = 0;
179 //sfBase->iMidStreamSessions = 0;
180 //sfBase->iClosedSessions = 0;
181 //sfBase->iPrunedSessions = 0;
182 //sfBase->iDroppedAsyncSessions = 0;
183 //sfBase->iSessionsInitializing = 0;
184 //sfBase->iSessionsEstablished = 0;
185 //sfBase->iSessionsClosing = 0;
186
187 sfBase->iFragCreates = 0;
188 sfBase->iFragCompletes = 0;
189 sfBase->iFragInserts = 0;
190 sfBase->iFragDeletes = 0;
191 sfBase->iFragAutoFrees = 0;
192 sfBase->iFragFlushes = 0;
193 sfBase->iFragTimeouts = 0;
194 sfBase->iFragFaults = 0;
195
196 #ifdef NORMALIZER
197 {
198 int i = 0;
199 for ( i = 0; i < PERF_COUNT_MAX; i++ )
200 {
201 sfBase->iPegs[i][NORM_MODE_ON] = 0;
202 sfBase->iPegs[i][NORM_MODE_WOULDA] = 0;
203 }
204 }
205 #endif
206
207 sfBase->iNewUDPSessions = 0;
208 sfBase->iDeletedUDPSessions = 0;
209
210 //sfBase->iAttributeHosts = 0;
211 //sfBase->iAttributeReloads = 0;
212 sfBase->total_mpls_packets = 0;
213 sfBase->total_mpls_bytes = 0;
214 sfBase->total_blocked_mpls_packets = 0;
215 sfBase->total_blocked_mpls_bytes = 0;
216
217 sfBase->total_tcp_filtered_packets = 0;
218 sfBase->total_udp_filtered_packets = 0;
219
220 sfBase->frag3_mem_in_use = 0;
221 sfBase->stream5_mem_in_use = 0;
222 sfBase->total_iAlerts = 0;
223
224 return 0;
225 }
226
227 /*
228 ** NAME
229 ** UpdateBaseStats
230 **
231 ** DESCRIPTION
232 ** Simple update of stats.
233 **
234 ** FORMAL INPUTS
235 ** SFBASE * - structure to update
236 ** int - length of packet payload in bytes
237 **
238 ** FORMAL OUTPUTS
239 ** int - 0 is successful
240 **
241 ** Add in Ethernet Overhead - assume a standerd Ethernet service
242 **
243 ** Ethernet Frame
244 ** ---------------
245 ** | <----------- PCAP Packet --------> |
246 ** Preamble Dest Mac Src Mac Type Payload CRC IFG
247 ** | 8 bytes | 6 Bytes | 6 Bytes | 2-Bytes | 46-1500 | 4 Bytes | 12 |
248 **
249 ** Len = PCAP Packet + 4 bytes for CRC
250 ** Overhead = 20 bytes
251 ** Min on the wire == 84 bytes
252 ** Min Size of PCAP packet = 60 bytes (84 - 20 overhead - 4 CRC)
253 **
254 ** Len is the amount of user data being sent. This will be less then
255 ** actual wire-speed, because of the interframe gap (96 bits) and preamble
256 ** (8 bytes).
257 **
258 ** A 60 byte minimum packet uses 672 bits (60 bytes + 4 CRC), this limits a
259 ** 1000 Mbit network to 1.488 Million packets with a bandwidth of 760
260 ** Mbits. The lost 240 Mbits is due to interframe gap (96 bits) and preamble
261 ** (8 bytes).
262 **
263 ** Even if the actual data is only 40 bytes per packet (ie, an empty
264 ** TCP ACK), wire data is still 64 bytes per packet, even though actual
265 ** packet size is 40 bytes. Bandwith drops to 480 Mbits.
266 **
267 ** This explains why when a network goes over 50% capactiy you are closer to
268 ** the edge than you realize, depending on the traffic profile. At 75% you
269 ** are at the limit of your network, if you can get there.
270 **
271 ** bool rebuilt determines whether the packet is rebuilt or not. We keep
272 ** separate statistics between wire pkts and rebuilt pkts.
273 **
274 */
UpdateBaseStats(SFBASE * sfBase,Packet * p,bool rebuilt)275 void UpdateBaseStats(SFBASE *sfBase, Packet *p, bool rebuilt)
276 {
277 uint32_t len = p->pkth->caplen;
278
279 if (!rebuilt)
280 {
281 // For SYN to SYN/ACK counts to help determine if traffic is asynchronous
282 if ((p->tcph != NULL) && (p->tcph->th_flags & TH_SYN))
283 {
284 if (p->tcph->th_flags & TH_ACK)
285 sfBase->iSynAcks++;
286 else
287 sfBase->iSyns++;
288 }
289
290 len += 4; /* for the CRC */
291 }
292
293 /* Includes wire, IP reassembled & TCP rebuilt packets
294 * that make it to the application layer. */
295 sfBase->total_packets++;
296 sfBase->total_bytes += len;
297 }
298
299 /*
300 ** NAME
301 ** UpdateWireStats
302 **
303 ** DESCRIPTION
304 ** Simple update of stats for "on the wire".
305 **
306 ** FORMAL INPUTS
307 ** SFBASE * - structure to update
308 ** int - length of packet payload in bytes
309 **
310 ** FORMAL OUTPUTS
311 ** none
312 */
UpdateWireStats(SFBASE * sfBase,int len,int dropped,int inject)313 void UpdateWireStats(SFBASE *sfBase, int len, int dropped, int inject)
314 {
315 sfBase->total_wire_packets++;
316
317 len += 4; /* for the CRC */
318 sfBase->total_wire_bytes += len;
319
320 if( dropped )
321 {
322 sfBase->total_blocked_packets++;
323 sfBase->total_blocked_bytes += len;
324 }
325 if ( inject )
326 sfBase->total_injected_packets++;
327 }
328
UpdateMPLSStats(SFBASE * sfBase,int len,int dropped)329 void UpdateMPLSStats(SFBASE *sfBase, int len, int dropped)
330 {
331 #ifdef MPLS
332 sfBase->total_mpls_packets++;
333
334 len += 4; /* for the CRC */
335 sfBase->total_mpls_bytes += len;
336
337 if( dropped )
338 {
339 sfBase->total_blocked_mpls_packets++;
340 sfBase->total_blocked_mpls_bytes += len;
341 }
342 #endif
343 }
344
345 /*
346 ** NAME
347 ** UpdateIPFragStats
348 **
349 ** DESCRIPTION
350 ** Simple update of stats for IP fragmented packets
351 **
352 ** FORMAL INPUTS
353 ** SFBASE * - structure to update
354 ** int - length of packet payload in bytes
355 **
356 ** FORMAL OUTPUTS
357 ** none
358 */
UpdateIPFragStats(SFBASE * sfBase,int len)359 void UpdateIPFragStats(SFBASE *sfBase, int len)
360 {
361 sfBase->total_ipfragmented_packets++;
362
363 len += 4; /* for the CRC */
364 sfBase->total_ipfragmented_bytes += len;
365 }
366
367 /*
368 ** NAME
369 ** UpdateIPReassStats
370 **
371 ** DESCRIPTION
372 ** Simple update of stats for IP reassembled packets
373 **
374 ** FORMAL INPUTS
375 ** SFBASE * - structure to update
376 ** int - length of packet payload in bytes
377 **
378 ** FORMAL OUTPUTS
379 ** none
380 */
UpdateIPReassStats(SFBASE * sfBase,int len)381 void UpdateIPReassStats(SFBASE *sfBase, int len)
382 {
383 sfBase->total_ipreassembled_bytes += len;
384 sfBase->total_ipreassembled_packets++;
385 }
386
UpdateStreamReassStats(SFBASE * sfBase,int len)387 void UpdateStreamReassStats(SFBASE *sfBase, int len)
388 {
389 sfBase->total_rebuilt_bytes += len;
390 sfBase->total_rebuilt_packets++;
391 }
392
393 /**API to update stats for packets discarded due to
394 * TCP/UDP port/service based filtering.
395 *
396 * @param sfBase - pointer to accumulated stats
397 */
UpdateFilteredPacketStats(SFBASE * sfBase,IpProto proto)398 void UpdateFilteredPacketStats(SFBASE *sfBase, IpProto proto)
399 {
400 switch (proto)
401 {
402 case IPPROTO_TCP:
403 sfBase->total_tcp_filtered_packets++;
404 break;
405 case IPPROTO_UDP:
406 sfBase->total_udp_filtered_packets++;
407 break;
408 default:
409 //coding error
410 ;
411 }
412 }
413 /*
414 ** NAME
415 ** AddStreamSession
416 **
417 ** DESCRIPTION
418 ** Add a session count
419 **
420 ** FORMAL INPUTS
421 ** SFBASE * - ptr to update.
422 **
423 ** FORMAL OUTPUTS
424 ** int - 0 is successful
425 */
426
AddStreamSession(SFBASE * sfBase,uint32_t flags)427 int AddStreamSession(SFBASE *sfBase, uint32_t flags)
428 {
429 sfBase->iTotalSessions++;
430 sfBase->iNewSessions++;
431
432 if (flags & SSNFLAG_MIDSTREAM)
433 sfBase->iMidStreamSessions++;
434
435 if(sfBase->iTotalSessions > sfBase->iMaxSessions)
436 sfBase->iMaxSessions = sfBase->iTotalSessions;
437
438 if(sfBase->iTotalSessions > sfBase->iMaxSessionsInterval)
439 sfBase->iMaxSessionsInterval = sfBase->iTotalSessions;
440
441 return 0;
442 }
443
444 /*
445 ** NAME
446 ** CloseStreamSession
447 **
448 ** DESCRIPTION
449 ** Add a session count
450 **
451 ** FORMAL INPUTS
452 ** SFBASE * - ptr to update.
453 **
454 ** FORMAL OUTPUTS
455 ** int - 0 is successful
456 */
457
CloseStreamSession(SFBASE * sfBase,char flags)458 int CloseStreamSession(SFBASE *sfBase, char flags)
459 {
460 if (flags & SESSION_CLOSED_NORMALLY)
461 sfBase->iClosedSessions++;
462 else{
463 if (flags & SESSION_CLOSED_TIMEDOUT)
464 sfBase->iStreamTimeouts++;
465 if (flags & SESSION_CLOSED_PRUNED)
466 sfBase->iPrunedSessions++;
467 if (flags & SESSION_CLOSED_ASYNC)
468 sfBase->iDroppedAsyncSessions++;
469 }
470 return 0;
471 }
472
473 /*
474 ** NAME
475 ** RemoveStreamSession
476 **
477 ** DESCRIPTION
478 ** Add a session count
479 **
480 ** FORMAL INPUTS
481 ** SFBASE * - ptr to update.
482 **
483 ** FORMAL OUTPUTS
484 ** int - 0 is successful
485 */
486
RemoveStreamSession(SFBASE * sfBase)487 int RemoveStreamSession(SFBASE *sfBase)
488 {
489 sfBase->iTotalSessions--;
490 sfBase->iDeletedSessions++;
491 return 0;
492 }
493
494 /*
495 ** NAME
496 ** AddUDPSession
497 **
498 ** DESCRIPTION
499 ** Add a session count
500 **
501 ** FORMAL INPUTS
502 ** SFBASE * - ptr to update.
503 **
504 ** FORMAL OUTPUTS
505 ** int - 0 is successful
506 */
AddUDPSession(SFBASE * sfBase)507 int AddUDPSession(SFBASE *sfBase)
508 {
509 sfBase->iTotalUDPSessions++;
510 sfBase->iNewUDPSessions++;
511
512 if(sfBase->iTotalUDPSessions > sfBase->iMaxUDPSessions)
513 sfBase->iMaxUDPSessions = sfBase->iTotalUDPSessions;
514
515 return 0;
516 }
517
518 /*
519 ** NAME
520 ** RemoveUDPSession
521 **
522 ** DESCRIPTION
523 ** Add a session count
524 **
525 ** FORMAL INPUTS
526 ** SFBASE * - ptr to update.
527 **
528 ** FORMAL OUTPUTS
529 ** int - 0 is successful
530 */
531
RemoveUDPSession(SFBASE * sfBase)532 int RemoveUDPSession(SFBASE *sfBase)
533 {
534 sfBase->iTotalUDPSessions--;
535 sfBase->iDeletedUDPSessions++;
536 return 0;
537 }
538
539 /*
540 ** NAME
541 ** ProcessBaseStats
542 **
543 ** DESCRIPTION
544 ** Main function to process Base Stats.
545 **
546 ** FORMAL INPUTS
547 ** SFBASE * - ptr to update.
548 **
549 ** FORMAL OUTPUTS
550 ** int - 0 is successful
551 */
ProcessBaseStats(SFBASE * sfBase,FILE * fh,int console,int max_stats)552 void ProcessBaseStats(SFBASE *sfBase, FILE *fh, int console, int max_stats)
553 {
554 SFBASE_STATS sfBaseStats;
555
556 if (fh || console)
557 {
558 if (CalculateBasePerfStats(sfBase, &sfBaseStats, max_stats))
559 return;
560
561 if (console)
562 DisplayBasePerfStatsConsole(&sfBaseStats, max_stats);
563
564 if (fh)
565 LogBasePerfStats(&sfBaseStats, fh);
566 }
567 }
568
GetProcessingTime(SYSTIMES * Systimes,SFBASE * sfBase)569 static int GetProcessingTime(SYSTIMES *Systimes, SFBASE *sfBase)
570 {
571 int todRet = -1;
572 struct timeval tvTime;
573 #ifdef LINUX_SMP
574
575 if(sfProcessProcPidStats(&(sfBase->sfProcPidStats)))
576 return -1;
577 todRet = gettimeofday(&tvTime, NULL);
578 #else
579 struct rusage rusage;
580 int rusageRet;
581 #ifndef WIN32
582 rusageRet = getrusage(RUSAGE_SELF, &rusage);
583 #else
584 rusageRet = -1;
585 #endif /* !WIN32 */
586 todRet = gettimeofday(&tvTime, NULL);
587
588 if (rusageRet < 0)
589 {
590 rusage.ru_utime.tv_sec = 0;
591 rusage.ru_utime.tv_usec = 0;
592 rusage.ru_stime.tv_sec = 0;
593 rusage.ru_stime.tv_usec = 0;
594 }
595 Systimes->usertime = ((double)rusage.ru_utime.tv_sec +
596 ((double)rusage.ru_utime.tv_usec * 1.0e-6)) -
597 sfBase->usertime_sec;
598 Systimes->systemtime = ((double)rusage.ru_stime.tv_sec +
599 ((double)rusage.ru_stime.tv_usec * 1.0e-6)) -
600 sfBase->systemtime_sec;
601 Systimes->totaltime = Systimes->usertime + Systimes->systemtime;
602 #endif /* LINUX_SMP */
603
604 if (todRet < 0)
605 {
606 return todRet;
607 }
608
609 Systimes->realtime = ((double)tvTime.tv_sec +
610 ((double)tvTime.tv_usec * 1.0e-6)) -
611 sfBase->realtime_sec;
612 return 0;
613 }
614
GetEventsPerSecond(SFBASE * sfBase,SFBASE_STATS * sfBaseStats,SYSTIMES * Systimes)615 static void GetEventsPerSecond(SFBASE *sfBase, SFBASE_STATS *sfBaseStats,
616 SYSTIMES *Systimes)
617 {
618 sfBaseStats->alerts_per_second =
619 (double)(pc.alert_pkts - sfBase->iAlerts) / Systimes->realtime;
620
621 sfBase->iAlerts = pc.alert_pkts;
622
623 sfBaseStats->total_alerts_per_second =
624 (double)(pc.total_alert_pkts - sfBase->total_iAlerts) / Systimes->realtime;
625
626 sfBase->total_iAlerts = pc.total_alert_pkts;
627
628 sfBaseStats->total_sessions = sfBase->iTotalSessions;
629 sfBaseStats->max_sessions = sfBase->iMaxSessions;
630
631 sfBaseStats->syns_per_second =
632 (double)(sfBase->iSyns) / Systimes->realtime;
633
634 sfBaseStats->synacks_per_second =
635 (double)(sfBase->iSynAcks) / Systimes->realtime;
636
637 sfBaseStats->deleted_sessions_per_second =
638 (double)(sfBase->iDeletedSessions) / Systimes->realtime;
639
640 sfBaseStats->new_sessions_per_second =
641 (double)(sfBase->iNewSessions) / Systimes->realtime;
642
643 sfBaseStats->tcp_sessions_midstream_per_second =
644 (double)(sfBase->iMidStreamSessions) / Systimes->realtime;
645
646 sfBaseStats->tcp_sessions_closed_per_second =
647 (double)(sfBase->iClosedSessions) / Systimes->realtime;
648
649 sfBaseStats->tcp_sessions_timedout_per_second =
650 (double)(sfBase->iStreamTimeouts) / Systimes->realtime;
651
652 sfBaseStats->tcp_sessions_pruned_per_second =
653 (double)(sfBase->iPrunedSessions) / Systimes->realtime;
654
655 sfBaseStats->tcp_sessions_dropped_async_per_second =
656 (double)(sfBase->iDroppedAsyncSessions) / Systimes->realtime;
657
658 sfBaseStats->max_tcp_sessions_interval = sfBase->iMaxSessionsInterval;
659
660 sfBaseStats->stream_flushes_per_second =
661 (double)sfBase->iStreamFlushes / Systimes->realtime;
662
663 sfBaseStats->stream_faults = sfBase->iStreamFaults;
664 sfBaseStats->stream_timeouts = sfBase->iStreamTimeouts;
665 sfBaseStats->curr_tcp_sessions_initializing = sfBase->iSessionsInitializing;
666 sfBaseStats->curr_tcp_sessions_established = sfBase->iSessionsEstablished;
667 sfBaseStats->curr_tcp_sessions_closing = sfBase->iSessionsClosing;
668
669 sfBaseStats->frag_creates_per_second =
670 (double)sfBase->iFragCreates / Systimes->realtime;
671
672 sfBaseStats->frag_completes_per_second =
673 (double)sfBase->iFragCompletes / Systimes->realtime;
674
675 sfBaseStats->frag_inserts_per_second =
676 (double)sfBase->iFragInserts / Systimes->realtime;
677
678 sfBaseStats->frag_deletes_per_second =
679 (double)sfBase->iFragDeletes / Systimes->realtime;
680
681 sfBaseStats->frag_autofrees_per_second =
682 (double)sfBase->iFragAutoFrees / Systimes->realtime;
683
684 sfBaseStats->frag_flushes_per_second =
685 (double)sfBase->iFragFlushes / Systimes->realtime;
686
687 sfBaseStats->max_frags = sfBase->iMaxFrags;
688 sfBaseStats->current_frags = sfBase->iCurrentFrags;
689 sfBaseStats->frag_timeouts = sfBase->iFragTimeouts;
690 sfBaseStats->frag_faults = sfBase->iFragFaults;
691
692 sfBase->iSyns = 0;
693 sfBase->iSynAcks = 0;
694 sfBase->iNewSessions = 0;
695 sfBase->iDeletedSessions = 0;
696
697 sfBase->iStreamFlushes = 0;
698 sfBase->iStreamFaults = 0;
699 sfBase->iStreamTimeouts = 0;
700
701 sfBase->iFragCreates = 0;
702 sfBase->iFragCompletes = 0;
703 sfBase->iFragInserts = 0;
704 sfBase->iFragDeletes = 0;
705 sfBase->iFragAutoFrees = 0;
706 sfBase->iFragFlushes = 0;
707 sfBase->iFragTimeouts = 0;
708 sfBase->iFragFaults = 0;
709
710 #ifdef NORMALIZER
711 {
712 int i = 0;
713 for ( i = 0; i < PERF_COUNT_MAX; i++ )
714 {
715 sfBase->iPegs[i][NORM_MODE_ON] = 0;
716 sfBase->iPegs[i][NORM_MODE_WOULDA] = 0;
717 }
718 }
719 #endif
720
721 sfBaseStats->total_udp_sessions = sfBase->iTotalUDPSessions;
722 sfBaseStats->max_udp_sessions = sfBase->iMaxUDPSessions;
723 sfBaseStats->deleted_udp_sessions_per_second =
724 (double)(sfBase->iDeletedUDPSessions) / Systimes->realtime;
725
726 sfBaseStats->new_udp_sessions_per_second =
727 (double)(sfBase->iNewUDPSessions) / Systimes->realtime;
728
729 sfBase->iNewUDPSessions = 0;
730 sfBase->iDeletedUDPSessions = 0;
731
732 sfBase->iMaxSessionsInterval = sfBase->iTotalSessions;
733 sfBase->iMidStreamSessions = 0;
734 sfBase->iClosedSessions = 0;
735 sfBase->iPrunedSessions = 0;
736 sfBase->iDroppedAsyncSessions = 0;
737 }
738
GetPacketsPerSecond(SFBASE * sfBase,SFBASE_STATS * sfBaseStats,SYSTIMES * Systimes,int max_stats)739 static void GetPacketsPerSecond(SFBASE *sfBase, SFBASE_STATS *sfBaseStats,
740 SYSTIMES *Systimes, int max_stats)
741 {
742 sfBaseStats->kpackets_per_sec.realtime =
743 (double)((double)sfBase->total_packets / 1000) / Systimes->realtime;
744
745 if (max_stats)
746 {
747 sfBaseStats->kpackets_per_sec.usertime =
748 (double)((double)sfBase->total_packets / 1000) /
749 Systimes->usertime;
750 sfBaseStats->kpackets_per_sec.systemtime =
751 (double)((double)sfBase->total_packets / 1000) /
752 Systimes->systemtime;
753 sfBaseStats->kpackets_per_sec.totaltime =
754 (double)((double)sfBase->total_packets / 1000) /
755 Systimes->totaltime;
756 }
757
758 sfBaseStats->kpackets_wire_per_sec.realtime =
759 (double)((double)sfBase->total_wire_packets / 1000) / Systimes->realtime;
760
761 if (max_stats)
762 {
763 sfBaseStats->kpackets_wire_per_sec.usertime =
764 (double)((double)sfBase->total_wire_packets / 1000) /
765 Systimes->usertime;
766 sfBaseStats->kpackets_wire_per_sec.systemtime =
767 (double)((double)sfBase->total_wire_packets / 1000) /
768 Systimes->systemtime;
769 sfBaseStats->kpackets_wire_per_sec.totaltime =
770 (double)((double)sfBase->total_wire_packets / 1000) /
771 Systimes->totaltime;
772 }
773
774 sfBaseStats->kpackets_ipfrag_per_sec.realtime =
775 (double)((double)sfBase->total_ipfragmented_packets / 1000) / Systimes->realtime;
776
777 if (max_stats)
778 {
779 sfBaseStats->kpackets_ipfrag_per_sec.usertime =
780 (double)((double)sfBase->total_ipfragmented_packets / 1000) /
781 Systimes->usertime;
782 sfBaseStats->kpackets_ipfrag_per_sec.systemtime =
783 (double)((double)sfBase->total_ipfragmented_packets / 1000) /
784 Systimes->systemtime;
785 sfBaseStats->kpackets_ipfrag_per_sec.totaltime =
786 (double)((double)sfBase->total_ipfragmented_packets / 1000) /
787 Systimes->totaltime;
788 }
789
790 sfBaseStats->kpackets_ipreass_per_sec.realtime =
791 (double)((double)sfBase->total_ipreassembled_packets / 1000) / Systimes->realtime;
792
793 if (max_stats)
794 {
795 sfBaseStats->kpackets_ipreass_per_sec.usertime =
796 (double)((double)sfBase->total_ipreassembled_packets / 1000) /
797 Systimes->usertime;
798 sfBaseStats->kpackets_ipreass_per_sec.systemtime =
799 (double)((double)sfBase->total_ipreassembled_packets / 1000) /
800 Systimes->systemtime;
801 sfBaseStats->kpackets_ipreass_per_sec.totaltime =
802 (double)((double)sfBase->total_ipreassembled_packets / 1000) /
803 Systimes->totaltime;
804 }
805
806 sfBaseStats->kpackets_rebuilt_per_sec.realtime =
807 (double)((double)sfBase->total_rebuilt_packets / 1000) / Systimes->realtime;
808
809 if (max_stats)
810 {
811 sfBaseStats->kpackets_rebuilt_per_sec.usertime =
812 (double)((double)sfBase->total_rebuilt_packets / 1000) /
813 Systimes->usertime;
814 sfBaseStats->kpackets_rebuilt_per_sec.systemtime =
815 (double)((double)sfBase->total_rebuilt_packets / 1000) /
816 Systimes->systemtime;
817 sfBaseStats->kpackets_rebuilt_per_sec.totaltime =
818 (double)((double)sfBase->total_rebuilt_packets / 1000) /
819 Systimes->totaltime;
820 }
821
822 sfBaseStats->kpackets_per_sec_mpls.realtime =
823 (double)((double)sfBase->total_mpls_packets / 1000) / Systimes->realtime;
824
825 if (max_stats)
826 {
827 sfBaseStats->kpackets_per_sec_mpls.usertime =
828 (double)((double)sfBase->total_mpls_packets / 1000) /
829 Systimes->usertime;
830 sfBaseStats->kpackets_per_sec_mpls.systemtime =
831 (double)((double)sfBase->total_mpls_packets / 1000) /
832 Systimes->systemtime;
833 sfBaseStats->kpackets_per_sec_mpls.totaltime =
834 (double)((double)sfBase->total_mpls_packets / 1000) /
835 Systimes->totaltime;
836 }
837 }
838
GetuSecondsPerPacket(SFBASE * sfBase,SFBASE_STATS * sfBaseStats,SYSTIMES * Systimes)839 static void GetuSecondsPerPacket(SFBASE *sfBase, SFBASE_STATS *sfBaseStats,
840 SYSTIMES *Systimes)
841 {
842 if(sfBase->total_packets)
843 {
844 sfBaseStats->usecs_per_packet.usertime = (Systimes->usertime * 1.0e6) /
845 (double)sfBase->total_packets;
846 sfBaseStats->usecs_per_packet.systemtime = (Systimes->systemtime * 1.0e6) /
847 (double)sfBase->total_packets;
848 sfBaseStats->usecs_per_packet.totaltime = (Systimes->totaltime * 1.0e6) /
849 (double)sfBase->total_packets;
850 sfBaseStats->usecs_per_packet.realtime = (Systimes->realtime * 1.0e6) /
851 (double)sfBase->total_packets;
852 }
853 }
854
GetMbitsPerSecond(SFBASE * sfBase,SFBASE_STATS * sfBaseStats,SYSTIMES * Systimes,int max_stats)855 static void GetMbitsPerSecond(SFBASE *sfBase, SFBASE_STATS *sfBaseStats,
856 SYSTIMES *Systimes, int max_stats)
857 {
858 /*
859 ** These Mbits stats are for the Snort Maximum Performance stats
860 ** that can't reliably be gotten from Linux SMP kernels. So
861 ** we don't do them.
862 */
863 if (max_stats)
864 {
865 sfBaseStats->mbits_per_sec.usertime = ((double)
866 (sfBase->total_bytes<<3) *
867 1.0e-6) /
868 Systimes->usertime;
869 sfBaseStats->mbits_per_sec.systemtime = ((double)
870 (sfBase->total_bytes<<3) *
871 1.0e-6) /
872 Systimes->systemtime;
873 sfBaseStats->mbits_per_sec.totaltime = ((double)
874 (sfBase->total_bytes<<3) *
875 1.0e-6) /
876 Systimes->totaltime;
877 }
878
879 sfBaseStats->mbits_per_sec.realtime = ((double)(sfBase->total_bytes<<3) *
880 1.0e-6) /
881 Systimes->realtime;
882 sfBaseStats->wire_mbits_per_sec.realtime =
883 ((double)(sfBase->total_wire_bytes<<3) *
884 1.0e-6) /
885 Systimes->realtime;
886 sfBaseStats->rebuilt_mbits_per_sec.realtime =
887 ((double)(sfBase->total_rebuilt_bytes<<3) *
888 1.0e-6) /
889 Systimes->realtime;
890
891 sfBaseStats->ipfrag_mbits_per_sec.realtime =
892 ((double)(sfBase->total_ipfragmented_bytes<<3) *
893 1.0e-6) /
894 Systimes->realtime;
895
896 sfBaseStats->ipreass_mbits_per_sec.realtime =
897 ((double)(sfBase->total_ipreassembled_bytes<<3) *
898 1.0e-6) /
899 Systimes->realtime;
900 sfBaseStats->mpls_mbits_per_sec.realtime =
901 ((double)(sfBase->total_mpls_bytes<<3) *
902 1.0e-6) /
903 Systimes->realtime;
904 }
905
GetCPUTime(SFBASE * sfBase,SFBASE_STATS * sfBaseStats,SYSTIMES * Systimes)906 static void GetCPUTime(SFBASE *sfBase, SFBASE_STATS *sfBaseStats, SYSTIMES *Systimes)
907 {
908 #ifndef LINUX_SMP
909 unsigned char needToNormalize = 0;
910 sfBaseStats->user_cpu_time = (Systimes->usertime /
911 Systimes->realtime) * 100;
912 sfBaseStats->system_cpu_time = (Systimes->systemtime /
913 Systimes->realtime) * 100;
914 sfBaseStats->idle_cpu_time = ((Systimes->realtime -
915 Systimes->totaltime) /
916 Systimes->realtime) * 100;
917
918 /* percentages can be < 0 because of a small variance between
919 * when the snapshot is taken of the CPU times and snapshot of
920 * the real time. So these are just a safe-guard to normalize
921 * the data so we see positive values.
922 */
923 if (sfBaseStats->user_cpu_time < 0)
924 {
925 sfBaseStats->user_cpu_time = 0;
926 needToNormalize = 1;
927 }
928 if (sfBaseStats->system_cpu_time < 0)
929 {
930 sfBaseStats->system_cpu_time = 0;
931 needToNormalize = 1;
932 }
933 if (sfBaseStats->idle_cpu_time < 0)
934 {
935 sfBaseStats->idle_cpu_time = 0;
936 needToNormalize = 1;
937 }
938
939 if (needToNormalize)
940 {
941 double totalPercent = sfBaseStats->user_cpu_time +
942 sfBaseStats->system_cpu_time +
943 sfBaseStats->idle_cpu_time;
944
945
946 sfBaseStats->user_cpu_time = (sfBaseStats->user_cpu_time /
947 totalPercent) * 100;
948 sfBaseStats->system_cpu_time = ( sfBaseStats->system_cpu_time /
949 totalPercent) * 100;
950 sfBaseStats->idle_cpu_time = ( sfBaseStats->idle_cpu_time /
951 totalPercent) * 100;
952
953 }
954 #endif
955 }
956
957
958 /*
959 ** NAME
960 ** CalculateBasePerfStats
961 **
962 ** DESCRIPTION
963 ** This is the main function that calculates the stats. Stats
964 ** that we caculate are:
965 ** *uSecs per Packet
966 ** *Packets per Second
967 ** *Mbits per Second
968 ** *Average bytes per Packet
969 ** *CPU Time
970 ** *Dropped Packets
971 ** These statistics are processed and then stored in the
972 ** SFBASE_STATS structure. This allows output functions to
973 ** be easily formed and inserted.
974 ** NOTE: We can break up these statistics into functions for easier
975 ** reading.
976 **
977 ** FORMAL INPUTS
978 ** SFBASE * - ptr to performance struct
979 ** SFBASE_STATS * - ptr to struct to fill in performance stats
980 ** int - do max stats
981 **
982 ** FORMAL OUTPUTS
983 ** int - 0 is successful
984 */
CalculateBasePerfStats(SFBASE * sfBase,SFBASE_STATS * sfBaseStats,int max_stats)985 static int CalculateBasePerfStats(SFBASE *sfBase, SFBASE_STATS *sfBaseStats, int max_stats)
986 {
987 SYSTIMES Systimes;
988 time_t clock;
989
990 #ifdef LINUX_SMP
991
992 /*
993 ** We also give sfBaseStats access to the CPU usage
994 ** contained in sfProcPidStats. This way we don't need
995 ** to complicate sfBaseStats further.
996 */
997 sfBaseStats->sfProcPidStats = &(sfBase->sfProcPidStats);
998
999 #endif
1000 if(GetProcessingTime(&Systimes, sfBase))
1001 return -1;
1002
1003 sfBaseStats->total_blocked_packets = sfBase->total_blocked_packets;
1004 sfBaseStats->total_injected_packets = sfBase->total_injected_packets;
1005 sfBaseStats->total_mpls_packets = sfBase->total_mpls_packets;
1006 sfBaseStats->total_mpls_bytes = sfBase->total_mpls_bytes;
1007 sfBaseStats->total_blocked_mpls_packets = sfBase->total_blocked_mpls_packets;
1008 sfBaseStats->total_blocked_mpls_bytes = sfBase->total_blocked_mpls_bytes;
1009
1010 sfBaseStats->total_tcp_filtered_packets = sfBase->total_tcp_filtered_packets;
1011 sfBaseStats->total_udp_filtered_packets = sfBase->total_udp_filtered_packets;
1012
1013 #ifdef NORMALIZER
1014 {
1015 int iCtr;
1016 for ( iCtr = 0; iCtr < PERF_COUNT_MAX; iCtr++ )
1017 {
1018 sfBaseStats->pegs[iCtr][NORM_MODE_ON] = sfBase->iPegs[iCtr][NORM_MODE_ON];
1019 sfBaseStats->pegs[iCtr][NORM_MODE_WOULDA] = sfBase->iPegs[iCtr][NORM_MODE_WOULDA];
1020 }
1021 }
1022 #endif
1023
1024 /*
1025 ** Avg. bytes per Packet
1026 */
1027 if (sfBase->total_packets > 0)
1028 sfBaseStats->avg_bytes_per_packet = zeroFpException(
1029 (int)((double)(sfBase->total_bytes) /
1030 (double)(sfBase->total_packets)));
1031 else
1032 sfBaseStats->avg_bytes_per_packet = 0;
1033
1034 if (sfBase->total_wire_packets > 0)
1035 sfBaseStats->avg_bytes_per_wire_packet = zeroFpException(
1036 (int)((double)(sfBase->total_wire_bytes) /
1037 (double)(sfBase->total_wire_packets)));
1038 else
1039 sfBaseStats->avg_bytes_per_wire_packet = 0;
1040
1041 if (sfBase->total_ipfragmented_packets > 0)
1042 sfBaseStats->avg_bytes_per_ipfrag_packet = zeroFpException(
1043 (int)((double)(sfBase->total_ipfragmented_bytes) /
1044 (double)(sfBase->total_ipfragmented_packets)));
1045 else
1046 sfBaseStats->avg_bytes_per_ipfrag_packet = 0;
1047
1048 if (sfBase->total_ipreassembled_packets > 0)
1049 sfBaseStats->avg_bytes_per_ipreass_packet = zeroFpException(
1050 (int)((double)(sfBase->total_ipreassembled_bytes) /
1051 (double)(sfBase->total_ipreassembled_packets)));
1052 else
1053 sfBaseStats->avg_bytes_per_ipreass_packet = 0;
1054
1055 if (sfBase->total_rebuilt_packets > 0)
1056 sfBaseStats->avg_bytes_per_rebuilt_packet = zeroFpException(
1057 (int)((double)(sfBase->total_rebuilt_bytes) /
1058 (double)(sfBase->total_rebuilt_packets)));
1059 else
1060 sfBaseStats->avg_bytes_per_rebuilt_packet = 0;
1061
1062 if (sfBase->total_mpls_packets > 0)
1063 sfBaseStats->avg_bytes_per_mpls_packet = zeroFpException(
1064 (int)((double)(sfBase->total_mpls_bytes) /
1065 (double)(sfBase->total_mpls_packets)));
1066 else
1067 sfBaseStats->avg_bytes_per_mpls_packet = 0;
1068
1069 /*
1070 ** CPU time
1071 */
1072 GetCPUTime(sfBase, sfBaseStats, &Systimes);
1073
1074 /*
1075 ** Get Dropped Packets
1076 */
1077 GetPktDropStats(sfBase, sfBaseStats);
1078
1079 /*
1080 ** Total packets
1081 */
1082 sfBaseStats->total_packets = sfBase->total_wire_packets;
1083
1084 /*
1085 * Pattern Matching Performance in Real and User time
1086 */
1087 sfBaseStats->patmatch_percent = zeroFpException(100.0 * mpseGetPatByteCount() /
1088 sfBase->total_wire_bytes);
1089
1090 mpseResetByteCount();
1091
1092 if (max_stats)
1093 {
1094 /*
1095 ** uSeconds per Packet
1096 ** user, system, total time
1097 */
1098 GetuSecondsPerPacket(sfBase, sfBaseStats, &Systimes);
1099 }
1100
1101 /*
1102 ** Mbits per sec
1103 ** user, system, total time
1104 */
1105 GetMbitsPerSecond(sfBase, sfBaseStats, &Systimes, max_stats);
1106
1107 /*
1108 ** EventsPerSecond
1109 ** We get the information from the global variable
1110 ** PacketCount.
1111 */
1112 GetEventsPerSecond(sfBase, sfBaseStats, &Systimes);
1113
1114 /*
1115 ** Packets per seconds
1116 ** user, system, total time
1117 */
1118 GetPacketsPerSecond(sfBase, sfBaseStats, &Systimes, max_stats);
1119
1120 /*
1121 ** Attribute Table counters
1122 **
1123 */
1124 sfBaseStats->current_attribute_hosts = sfBase->iAttributeHosts;
1125 sfBaseStats->attribute_table_reloads = sfBase->iAttributeReloads;
1126
1127 sfBaseStats->frag3_mem_in_use = sfBase->frag3_mem_in_use;
1128 sfBaseStats->stream5_mem_in_use = sfBase->stream5_mem_in_use;
1129
1130 /*
1131 ** Set the date string for print out
1132 */
1133 if (sfBase->time)
1134 {
1135 clock = sfBase->time;
1136 }
1137 else
1138 {
1139 time(&clock);
1140 }
1141 sfBaseStats->time = clock;
1142
1143 return 0;
1144 }
1145
1146 /*
1147 ** NAME
1148 ** GetPktDropStats
1149 **
1150 ** DESCRIPTION
1151 ** Gets the packet drop statisitics from DAQ.
1152 **
1153 ** FORMAL INPUT
1154 ** SFBASE * - ptr to struct
1155 ** SFBASE_STATS * - ptr to struct to fill in with perf stats
1156 **
1157 ** FORMAL OUTPUT
1158 ** void return
1159 */
GetPktDropStats(SFBASE * sfBase,SFBASE_STATS * sfBaseStats)1160 static void GetPktDropStats(SFBASE *sfBase, SFBASE_STATS *sfBaseStats)
1161 {
1162 uint64_t recv, drop, sum;
1163
1164 if (ScReadMode())
1165 {
1166 recv = pc.total_from_daq;
1167 drop = 0;
1168 }
1169 else
1170 {
1171 const DAQ_Stats_t* ps = DAQ_GetStats();
1172 recv = ps->hw_packets_received;
1173 drop = ps->hw_packets_dropped;
1174 if (perfmon_config->base_reset)
1175 {
1176 if (recv < sfBase->pkt_stats.pkts_recv)
1177 sfBase->pkt_stats.pkts_recv = 0;
1178
1179 if (drop < sfBase->pkt_stats.pkts_drop)
1180 sfBase->pkt_stats.pkts_drop = 0;
1181 }
1182 }
1183
1184 if (perfmon_config->base_reset)
1185 {
1186 sfBaseStats->pkt_stats.pkts_recv = recv - sfBase->pkt_stats.pkts_recv;
1187 sfBaseStats->pkt_stats.pkts_drop = drop - sfBase->pkt_stats.pkts_drop;
1188 }
1189 else
1190 {
1191 sfBaseStats->pkt_stats.pkts_recv = recv;
1192 sfBaseStats->pkt_stats.pkts_drop = drop;
1193 }
1194
1195 sum = sfBaseStats->pkt_stats.pkts_recv
1196 + sfBaseStats->pkt_stats.pkts_drop;
1197
1198 if ( !sum )
1199 sfBaseStats->pkt_drop_percent = 0.0;
1200
1201 else
1202 sfBaseStats->pkt_drop_percent = zeroFpException(
1203 ((double)sfBaseStats->pkt_stats.pkts_drop / (double)sum) * 100.0);
1204
1205 /*
1206 ** Reset sfBase stats for next go round.
1207 */
1208 sfBase->pkt_stats.pkts_recv = recv;
1209 sfBase->pkt_stats.pkts_drop = drop;
1210 }
1211
1212 /*
1213 *
1214 * Log Base Per Stats to File
1215 *
1216 * unixtime(in secs since epoch)
1217 * %pkts dropped
1218 * mbits/sec (wire)
1219 * alerts/sec
1220 * K-Packets/Sec (wire)
1221 * Avg Bytes/Pkt (wire)
1222 * %bytes pattern matched
1223 * syns/sec
1224 * synacks/sec
1225 * new-sessions/sec (tcp stream cache)
1226 * del-sessions/sec (tcp stream cache)
1227 * total-sessions open (tcp stream cache)
1228 * max-sessions, lifetime (tcp stream cache)
1229 * streamflushes/sec
1230 * streamfaults/sec
1231 * streamtimeouts
1232 * fragcreates/sec
1233 * fragcompletes/sec
1234 * fraginserts/sec
1235 * fragdeletes/sec
1236 * fragflushes/sec
1237 * current-frags open (frag cache)
1238 * max-frags (frag cache)
1239 * fragtimeouts
1240 * fragfaults
1241 * num cpus (following triple is repeated for each CPU)
1242 * %user-cpu usage
1243 * %sys-cpu usage
1244 * %idle-cpu usage
1245 * mbits/sec (wire)
1246 * mbits/sec (ip fragmented)
1247 * mbits/sec (ip reassembled)
1248 * mbits/sec (tcp stream rebuilt)
1249 * mbits/sec (app layer)
1250 * Avg Bytes/Pkt (wire)
1251 * Avg Bytes/Pkt (ip fragmented)
1252 * Avg Bytes/Pkt (ip reassembled)
1253 * Avg Bytes/Pkt (tcp stream rebuilt)
1254 * Avg Bytes/Pkt (app layer)
1255 * K-Packets/Sec (wire)
1256 * K-Packets/Sec (ip fragmented)
1257 * K-Packets/Sec (ip reassembled)
1258 * K-Packets/Sec (tcp stream rebuilt)
1259 * K-Packets/Sec (app layer)
1260 * Pkts recieved
1261 * Pkts dropped
1262 * Blocked-KPackets (wire)
1263 * udp-sessions
1264 * max-udp-sessions
1265 * del-udp-sessions/sec (udp stream cache)
1266 * new-udp-sessions/sec (udp stream cache)
1267 * max-sessions, interval (tcp stream cache)
1268 * curr-tcp-sessions-initializing (tcp stream cache, of total-sessions open)
1269 * curr-tcp-sessions-established (tcp stream cache, of total-sessions open)
1270 * curr-tcp-sessions-closing (tcp stream cache, of total-sessions open)
1271 * tcp-sessions-mistream/sec (tcp stream cache, of new-sessions/sec)
1272 * tcp-sessions-closed/sec (tcp stream cache, of del-sessions/sec)
1273 * tcp-sessions-timedout/sec (tcp stream cache, of del-sessions/sec)
1274 * tcp-sessions-pruned/sec (tcp stream cache, of del-sessions/sec)
1275 * tcp-sessions-dropped_async/sec (tcp stream cache, of del-sessions/sec)
1276 * hosts in attribute table
1277 * attribute table reloads
1278 *
1279 */
1280
1281 // IMPORTANT - whatever changes you make here, please be sure
1282 // they are reflected in the LogBasePerfHeader() below!
LogBasePerfStats(SFBASE_STATS * sfBaseStats,FILE * fh)1283 static void LogBasePerfStats(SFBASE_STATS *sfBaseStats, FILE * fh )
1284 {
1285 double sys=0.0,usr=0.0,idle=0.0;
1286 int iCtr = 0;
1287 long start, size = 0;
1288 size_t wrote;
1289 // Oversized buffer; For perspective, the column header is only 1905 + 1 ('\n') characters long.
1290 static char buff[4096];
1291
1292 if (fh == NULL)
1293 return;
1294
1295 if ( (start = ftell(fh)) < 0 )
1296 return;
1297
1298 memset(buff, 0, sizeof(buff));
1299
1300 size = SafeSnprintf(buff, sizeof(buff),
1301 "%lu,%.3f,%.3f,%.3f,%.3f,%d,%.3f,",
1302 (unsigned long)sfBaseStats->time,
1303 sfBaseStats->pkt_drop_percent,
1304 sfBaseStats->wire_mbits_per_sec.realtime,
1305 sfBaseStats->alerts_per_second,
1306 sfBaseStats->kpackets_wire_per_sec.realtime,
1307 sfBaseStats->avg_bytes_per_wire_packet,
1308 sfBaseStats->patmatch_percent);
1309
1310 /* Session estimation statistics */
1311
1312 size += SafeSnprintf(buff + size, sizeof(buff) - size,
1313 "%.3f,%.3f,%.3f,%.3f," CSVu64 CSVu64,
1314 sfBaseStats->syns_per_second,
1315 sfBaseStats->synacks_per_second,
1316 sfBaseStats->new_sessions_per_second,
1317 sfBaseStats->deleted_sessions_per_second,
1318 sfBaseStats->total_sessions,
1319 sfBaseStats->max_sessions);
1320
1321
1322 size += SafeSnprintf(buff + size, sizeof(buff) - size,
1323 "%.3f," CSVu64 CSVu64,
1324 sfBaseStats->stream_flushes_per_second,
1325 sfBaseStats->stream_faults,
1326 sfBaseStats->stream_timeouts);
1327
1328 size += SafeSnprintf(buff + size, sizeof(buff) - size,
1329 "%.3f,%.3f,%.3f,%.3f,%.3f,%.3f," CSVu64 CSVu64 CSVu64 CSVu64,
1330 sfBaseStats->frag_creates_per_second,
1331 sfBaseStats->frag_completes_per_second,
1332 sfBaseStats->frag_inserts_per_second,
1333 sfBaseStats->frag_deletes_per_second,
1334 sfBaseStats->frag_autofrees_per_second,
1335 sfBaseStats->frag_flushes_per_second,
1336 sfBaseStats->current_frags,
1337 sfBaseStats->max_frags,
1338 sfBaseStats->frag_timeouts,
1339 sfBaseStats->frag_faults);
1340
1341 /* CPU STATS - at the end of output record */
1342 #ifdef LINUX_SMP
1343 /* First the number of CPUs */
1344 size += SafeSnprintf(buff + size, sizeof(buff) - size,
1345 "%d,", sfBaseStats->sfProcPidStats->iCPUs);
1346
1347 /* Next, stats for each CPU (a triple) */
1348 for(iCtr = 0; iCtr < sfBaseStats->sfProcPidStats->iCPUs; iCtr++)
1349 {
1350 usr= sfBaseStats->sfProcPidStats->SysCPUs[iCtr].user;
1351 sys= sfBaseStats->sfProcPidStats->SysCPUs[iCtr].sys;
1352 idle= sfBaseStats->sfProcPidStats->SysCPUs[iCtr].idle;
1353
1354 size += SafeSnprintf(buff + size, sizeof(buff) - size,
1355 "%.3f,%.3f,%.3f,",usr,sys,idle);
1356 }
1357
1358 #else
1359
1360 usr=sfBaseStats->user_cpu_time;
1361 sys=sfBaseStats->system_cpu_time;
1362 idle=sfBaseStats->idle_cpu_time;
1363
1364 /* 1 CPU hardcoded */
1365 size += SafeSnprintf(buff + size, sizeof(buff) - size,
1366 "1,%.3f,%.3f,%.3f,",usr,sys,idle);
1367
1368 #endif
1369
1370 /* Status for MBits/s, Bytes/Pkt, KPkts/s for each of
1371 * wire, IP Fragmented, IP Reassembled, Stream Reassembled,
1372 * App Layer (data that reaches protocol decoders). */
1373 size += SafeSnprintf(buff + size, sizeof(buff) - size,
1374 "%.3f,%.3f,%.3f,%.3f,%.3f,",
1375 sfBaseStats->wire_mbits_per_sec.realtime,
1376 sfBaseStats->ipfrag_mbits_per_sec.realtime,
1377 sfBaseStats->ipreass_mbits_per_sec.realtime,
1378 sfBaseStats->rebuilt_mbits_per_sec.realtime,
1379 sfBaseStats->mbits_per_sec.realtime);
1380
1381 size += SafeSnprintf(buff + size, sizeof(buff) - size,
1382 "%d,%d,%d,%d,%d,",
1383 sfBaseStats->avg_bytes_per_wire_packet,
1384 sfBaseStats->avg_bytes_per_ipfrag_packet,
1385 sfBaseStats->avg_bytes_per_ipreass_packet,
1386 sfBaseStats->avg_bytes_per_rebuilt_packet,
1387 sfBaseStats->avg_bytes_per_packet);
1388
1389 size += SafeSnprintf(buff + size, sizeof(buff) - size,
1390 "%.3f,%.3f,%.3f,%.3f,%.3f,",
1391 sfBaseStats->kpackets_wire_per_sec.realtime,
1392 sfBaseStats->kpackets_ipfrag_per_sec.realtime,
1393 sfBaseStats->kpackets_ipreass_per_sec.realtime,
1394 sfBaseStats->kpackets_rebuilt_per_sec.realtime,
1395 sfBaseStats->kpackets_per_sec.realtime);
1396
1397 size += SafeSnprintf(buff + size, sizeof(buff) - size,
1398 CSVu64,sfBaseStats->pkt_stats.pkts_recv);
1399
1400 size += SafeSnprintf(buff + size, sizeof(buff) - size,
1401 CSVu64, sfBaseStats->pkt_stats.pkts_drop);
1402
1403 size += SafeSnprintf(buff + size, sizeof(buff) - size,
1404 CSVu64, sfBaseStats->total_blocked_packets);
1405
1406 size += SafeSnprintf(buff + size, sizeof(buff) - size,
1407 "%.3f,%.3f," CSVu64 CSVu64,
1408 sfBaseStats->new_udp_sessions_per_second,
1409 sfBaseStats->deleted_udp_sessions_per_second,
1410 sfBaseStats->total_udp_sessions,
1411 sfBaseStats->max_udp_sessions);
1412
1413 size += SafeSnprintf(buff + size, sizeof(buff) - size,
1414 CSVu64 CSVu64 CSVu64 CSVu64 "%.3f,%.3f,%.3f,%.3f,%.3f,",
1415 sfBaseStats->max_tcp_sessions_interval,
1416 sfBaseStats->curr_tcp_sessions_initializing,
1417 sfBaseStats->curr_tcp_sessions_established,
1418 sfBaseStats->curr_tcp_sessions_closing,
1419 sfBaseStats->tcp_sessions_midstream_per_second,
1420 sfBaseStats->tcp_sessions_closed_per_second,
1421 sfBaseStats->tcp_sessions_timedout_per_second,
1422 sfBaseStats->tcp_sessions_pruned_per_second,
1423 sfBaseStats->tcp_sessions_dropped_async_per_second);
1424
1425 size += SafeSnprintf(buff + size, sizeof(buff) - size,
1426 CSVu64 CSVu64,
1427 sfBaseStats->current_attribute_hosts,
1428 sfBaseStats->attribute_table_reloads);
1429
1430 size += SafeSnprintf(buff + size, sizeof(buff) - size,
1431 "%.3f,%d,%.3f,", sfBaseStats->mpls_mbits_per_sec.realtime,
1432 sfBaseStats->avg_bytes_per_mpls_packet,
1433 sfBaseStats->kpackets_per_sec_mpls.realtime);
1434
1435 size += SafeSnprintf(buff + size, sizeof(buff) - size,
1436 CSVu64 CSVu64,
1437 sfBaseStats->total_tcp_filtered_packets,
1438 sfBaseStats->total_udp_filtered_packets);
1439
1440 #ifdef NORMALIZER
1441 size += SafeSnprintf(buff + size, sizeof(buff) - size,
1442 "%d,",
1443 PERF_COUNT_MAX);
1444 for ( iCtr = 0; iCtr < PERF_COUNT_MAX; iCtr++ )
1445 size += SafeSnprintf(buff + size, sizeof(buff) - size,
1446 CSVu64, sfBaseStats->pegs[iCtr][NORM_MODE_ON]);
1447 for ( iCtr = 0; iCtr < PERF_COUNT_MAX; iCtr++ )
1448 size += SafeSnprintf(buff + size, sizeof(buff) - size,
1449 CSVu64, sfBaseStats->pegs[iCtr][NORM_MODE_WOULDA]);
1450 #endif
1451
1452 size += SafeSnprintf(buff + size, sizeof(buff) - size,
1453 CSVu64, sfBaseStats->total_injected_packets);
1454 size += SafeSnprintf(buff + size, sizeof(buff) - size,
1455 CSVu64, sfBaseStats->frag3_mem_in_use);
1456 size += SafeSnprintf(buff + size, sizeof(buff) - size,
1457 CSVu64, sfBaseStats->stream5_mem_in_use);
1458
1459 size += SafeSnprintf(buff + size, sizeof(buff) - size,
1460 "%.3f", sfBaseStats->total_alerts_per_second);
1461
1462 size += SafeSnprintf(buff + size, sizeof(buff) - size, "\n");
1463
1464 // Write to file. On error, reset the file position and inform the user.
1465 wrote = fwrite(buff, size, 1, fh);
1466
1467 if (wrote != 1)
1468 {
1469 WarningMessage("%s: Failed to write stats\n", __FUNCTION__);
1470
1471 // fseek to adjust offset; ftruncate doesn't do that for us.
1472 if (fseek(fh, start, SEEK_SET))
1473 {
1474 WarningMessage("%s: Failed to adjust offset\n", __FUNCTION__);
1475 }
1476 ftruncate(fileno(fh), start);
1477 }
1478
1479 fflush(fh);
1480 }
1481
1482 #ifdef NORMALIZER
1483 static const char* iNames[PERF_COUNT_MAX] = {
1484 "ip4::trim",
1485 "ip4::tos",
1486 "ip4::df",
1487 "ip4::rf",
1488 "ip4::ttl",
1489 "ip4::opts",
1490 "icmp4::echo",
1491 "ip6::ttl",
1492 "ip6::opts",
1493 "icmp6::echo",
1494 "tcp::syn_opt",
1495 "tcp::opt",
1496 "tcp::pad",
1497 "tcp::rsv",
1498 "tcp::ns",
1499 "tcp::urp",
1500 "tcp::ecn_pkt",
1501 "tcp::ecn_ssn",
1502 "tcp::ts_ecr",
1503 "tcp::ts_nop",
1504 "tcp::ips_data",
1505 "tcp::block",
1506 "tcp::req_urg",
1507 "tcp::req_pay",
1508 "tcp::req_urp",
1509 "tcp::trim_syn",
1510 "tcp::trim_rst",
1511 "tcp::trim_win",
1512 "tcp::trim_mss",
1513 };
1514 #endif
1515
1516 // IMPORTANT - whatever changes you make here, please be sure
1517 // they correspond to the LogBasePerfStats() above!
LogBasePerfHeader(FILE * fh)1518 void LogBasePerfHeader (FILE* fh)
1519 {
1520 int iCtr, iCPUs;
1521 if( !fh ) return;
1522
1523 fprintf(fh,
1524 "#%s,%s,%s,%s,%s,%s,%s",
1525 "time",
1526 "pkt_drop_percent",
1527 "wire_mbits_per_sec.realtime",
1528 "alerts_per_second",
1529 "kpackets_wire_per_sec.realtime",
1530 "avg_bytes_per_wire_packet",
1531 "patmatch_percent");
1532
1533 /* Session estimation statistics */
1534
1535 fprintf(fh,
1536 ",%s,%s,%s,%s,%s,%s",
1537 "syns_per_second",
1538 "synacks_per_second",
1539 "new_sessions_per_second",
1540 "deleted_sessions_per_second",
1541 "total_sessions",
1542 "max_sessions");
1543
1544 fprintf(fh,
1545 ",%s,%s,%s",
1546 "stream_flushes_per_second",
1547 "stream_faults",
1548 "stream_timeouts");
1549
1550 fprintf(fh,
1551 ",%s,%s,%s,%s,%s,%s,%s,%s,%s,%s",
1552 "frag_creates_per_second",
1553 "frag_completes_per_second",
1554 "frag_inserts_per_second",
1555 "frag_deletes_per_second",
1556 "frag_autofrees_per_second",
1557 "frag_flushes_per_second",
1558 "current_frags",
1559 "max_frags",
1560 "frag_timeouts",
1561 "frag_faults");
1562
1563 /* First the number of CPUs */
1564 fprintf(fh,
1565 ",%s", "iCPUs");
1566
1567 #ifdef LINUX_SMP
1568 iCPUs = sfBase.sfProcPidStats.iCPUs;
1569 #else
1570 iCPUs = 1;
1571 #endif
1572 /* Next, stats for each CPU (a triple) */
1573 for ( iCtr = 0; iCtr < iCPUs; iCtr++ )
1574 {
1575 fprintf(fh,
1576 ",%s[%d],%s[%d],%s[%d]",
1577 "usr",iCtr,"sys",iCtr,"idle",iCtr);
1578 }
1579
1580 /* Status for MBits/s, Bytes/Pkt, KPkts/s for each of
1581 * wire, IP Fragmented, IP Reassembled, Stream Reassembled,
1582 * App Layer (data that reaches protocol decoders). */
1583 fprintf(fh,
1584 ",%s,%s,%s,%s,%s",
1585 "wire_mbits_per_sec.realtime",
1586 "ipfrag_mbits_per_sec.realtime",
1587 "ipreass_mbits_per_sec.realtime",
1588 "rebuilt_mbits_per_sec.realtime",
1589 "mbits_per_sec.realtime");
1590
1591 fprintf(fh,
1592 ",%s,%s,%s,%s,%s",
1593 "avg_bytes_per_wire_packet",
1594 "avg_bytes_per_ipfrag_packet",
1595 "avg_bytes_per_ipreass_packet",
1596 "avg_bytes_per_rebuilt_packet",
1597 "avg_bytes_per_packet");
1598
1599 fprintf(fh,
1600 ",%s,%s,%s,%s,%s",
1601 "kpackets_wire_per_sec.realtime",
1602 "kpackets_ipfrag_per_sec.realtime",
1603 "kpackets_ipreass_per_sec.realtime",
1604 "kpackets_rebuilt_per_sec.realtime",
1605 "kpackets_per_sec.realtime");
1606
1607 fprintf(fh,
1608 ",%s,%s,%s",
1609 "pkt_stats.pkts_recv",
1610 "pkt_stats.pkts_drop",
1611 "total_blocked_verdicts");
1612
1613 fprintf(fh,
1614 ",%s,%s,%s,%s",
1615 "new_udp_sessions_per_second",
1616 "deleted_udp_sessions_per_second",
1617 "total_udp_sessions",
1618 "max_udp_sessions");
1619
1620 fprintf(fh,
1621 ",%s,%s,%s,%s,%s,%s,%s,%s,%s",
1622 "max_tcp_sessions_interval",
1623 "curr_tcp_sessions_initializing",
1624 "curr_tcp_sessions_established",
1625 "curr_tcp_sessions_closing",
1626 "tcp_sessions_midstream_per_second",
1627 "tcp_sessions_closed_per_second",
1628 "tcp_sessions_timedout_per_second",
1629 "tcp_sessions_pruned_per_second",
1630 "tcp_sessions_dropped_async_per_second");
1631
1632 fprintf(fh,
1633 ",%s,%s",
1634 "current_attribute_hosts",
1635 "attribute_table_reloads");
1636
1637 fprintf(fh,
1638 ",%s,%s,%s", "mpls_mbits_per_sec.realtime",
1639 "avg_bytes_per_mpls_packet",
1640 "kpackets_per_sec_mpls.realtime");
1641
1642 fprintf(fh,
1643 ",%s,%s",
1644 "total_tcp_filtered_packets",
1645 "total_udp_filtered_packets");
1646
1647 #ifdef NORMALIZER
1648 fprintf(fh, ",num_normalizations");
1649 for ( iCtr = 0; iCtr < PERF_COUNT_MAX; iCtr++ )
1650 fprintf(fh, ",%s", iNames[iCtr]);
1651 for ( iCtr = 0; iCtr < PERF_COUNT_MAX; iCtr++ )
1652 fprintf(fh, ",would_%s", iNames[iCtr]);
1653 #endif
1654
1655 fprintf(fh,
1656 ",%s,%s,%s",
1657 "total_injected_packets",
1658 "frag3_mem_in_use",
1659 "stream5_mem_in_use");
1660
1661 fprintf(fh, ",%s",
1662 "total_alerts_per_second");
1663
1664 fprintf(fh,"\n");
1665 fflush(fh);
1666 }
1667
1668 /*
1669 ** NAME
1670 ** DisplayBasePerfStats
1671 **
1672 ** DESCRIPTION
1673 ** Output Function. We can easily code multiple output buffers
1674 ** because all that is received is a SFBASE_STATS struct which
1675 ** holds all the information to output. This current output
1676 ** function just prints to stdout.
1677 **
1678 ** FORMAL INPUTS
1679 ** SFBASE_STATS * - struct with perf information
1680 ** int - flags for output
1681 **
1682 ** FORMAL OUTPUTS
1683 ** void return
1684 */
DisplayBasePerfStatsConsole(SFBASE_STATS * sfBaseStats,int max_stats)1685 static void DisplayBasePerfStatsConsole(SFBASE_STATS *sfBaseStats, int max_stats)
1686 {
1687 int iCtr = 0;
1688
1689 LogMessage("\n");
1690 LogMessage("\n");
1691 LogMessage("Snort Realtime Performance : %s--------------------------\n",
1692 ctime(&sfBaseStats->time));
1693
1694 LogMessage("Pkts Recv: " STDu64 "\n", sfBaseStats->pkt_stats.pkts_recv);
1695
1696 LogMessage("Pkts Drop: " STDu64 "\n", sfBaseStats->pkt_stats.pkts_drop);
1697
1698 LogMessage("%% Dropped: %.3f%%\n", sfBaseStats->pkt_drop_percent);
1699
1700 LogMessage("Block Verdict: " STDu64 "\n", sfBaseStats->total_blocked_packets);
1701 LogMessage("Injected: " STDu64 "\n", sfBaseStats->total_injected_packets);
1702 LogMessage("Pkts Filtered TCP: " STDu64 "\n", sfBaseStats->total_tcp_filtered_packets);
1703 LogMessage("Pkts Filtered UDP: " STDu64 "\n\n", sfBaseStats->total_udp_filtered_packets);
1704
1705 LogMessage("Mbits/Sec: %.3f (wire)\n",
1706 sfBaseStats->wire_mbits_per_sec.realtime);
1707 #ifdef MPLS
1708 LogMessage("Mbits/Sec: %.3f (mpls)\n",
1709 sfBaseStats->mpls_mbits_per_sec.realtime);
1710 #endif
1711 LogMessage("Mbits/Sec: %.3f (ip fragmented)\n",
1712 sfBaseStats->ipfrag_mbits_per_sec.realtime);
1713 LogMessage("Mbits/Sec: %.3f (ip reassembled)\n",
1714 sfBaseStats->ipreass_mbits_per_sec.realtime);
1715 LogMessage("Mbits/Sec: %.3f (tcp rebuilt)\n",
1716 sfBaseStats->rebuilt_mbits_per_sec.realtime);
1717 LogMessage("Mbits/Sec: %.3f (app layer)\n\n",
1718 sfBaseStats->mbits_per_sec.realtime);
1719
1720 LogMessage("Bytes/Pkt: %d (wire)\n",
1721 sfBaseStats->avg_bytes_per_wire_packet);
1722 #ifdef MPLS
1723 LogMessage("Bytes/Pkt: %d (mpls)\n",
1724 sfBaseStats->avg_bytes_per_mpls_packet);
1725 #endif
1726 LogMessage("Bytes/Pkt: %d (ip fragmented)\n",
1727 sfBaseStats->avg_bytes_per_ipfrag_packet);
1728 LogMessage("Bytes/Pkt: %d (ip reassembled)\n",
1729 sfBaseStats->avg_bytes_per_ipreass_packet);
1730 LogMessage("Bytes/Pkt: %d (tcp rebuilt)\n",
1731 sfBaseStats->avg_bytes_per_rebuilt_packet);
1732 LogMessage("Bytes/Pkt: %d (app layer)\n\n",
1733 sfBaseStats->avg_bytes_per_packet);
1734
1735 LogMessage("KPkts/Sec: %.3f (wire)\n",
1736 sfBaseStats->kpackets_wire_per_sec.realtime);
1737 #ifdef MPLS
1738 LogMessage("KPkts/Sec: %.3f (mpls)\n",
1739 sfBaseStats->kpackets_per_sec_mpls.realtime);
1740 #endif
1741 LogMessage("KPkts/Sec: %.3f (ip fragmented)\n",
1742 sfBaseStats->kpackets_ipfrag_per_sec.realtime);
1743 LogMessage("KPkts/Sec: %.3f (ip reassembled)\n",
1744 sfBaseStats->kpackets_ipreass_per_sec.realtime);
1745 LogMessage("KPkts/Sec: %.3f (tcp rebuilt)\n",
1746 sfBaseStats->kpackets_rebuilt_per_sec.realtime);
1747 LogMessage("KPkts/Sec: %.3f (app layer)\n\n",
1748 sfBaseStats->kpackets_per_sec.realtime);
1749
1750 LogMessage("PatMatch: %.3f%%\n\n", sfBaseStats->patmatch_percent);
1751
1752 /*
1753 ** The following ifdefs are for CPU stats dealing with multiple
1754 ** CPUs in Linux. Snort will show user, system and idle time for
1755 ** each CPU. The methods of calculating this are different though,
1756 ** since getrusage is broken for multiple CPUs in Linux. We get the
1757 ** CPU stats instead from the proc filesystem on Linux.
1758 */
1759 #ifdef LINUX_SMP
1760
1761 for(iCtr = 0; iCtr < sfBaseStats->sfProcPidStats->iCPUs; iCtr++)
1762 {
1763 LogMessage("CPU%d Usage: %.3f%% (user) %.3f%% (sys) %.3f%% (idle)\n",
1764 iCtr,
1765 sfBaseStats->sfProcPidStats->SysCPUs[iCtr].user,
1766 sfBaseStats->sfProcPidStats->SysCPUs[iCtr].sys,
1767 sfBaseStats->sfProcPidStats->SysCPUs[iCtr].idle);
1768 }
1769 printf("\n");
1770
1771 #else
1772
1773 LogMessage("CPU Usage: %.3f%% (user) %.3f%% (sys) %.3f%% (idle)\n\n",
1774 sfBaseStats->user_cpu_time,
1775 sfBaseStats->system_cpu_time,
1776 sfBaseStats->idle_cpu_time);
1777
1778 #endif
1779
1780 /*
1781 ** Shows the number of snort alerts per second.
1782 */
1783 LogMessage("Alerts/Sec : %.3f\n", sfBaseStats->alerts_per_second);
1784
1785 /* Session estimation statistics */
1786 LogMessage("Syns/Sec : %.3f\n", sfBaseStats->syns_per_second);
1787 LogMessage("Syn-Acks/Sec : %.3f\n", sfBaseStats->synacks_per_second);
1788 LogMessage("New Cached Sessions/Sec: %.3f\n", sfBaseStats->new_sessions_per_second);
1789 LogMessage("Midstream Sessions/Sec : %.3f\n", sfBaseStats->tcp_sessions_midstream_per_second);
1790 LogMessage("Cached Sessions Del/Sec: %.3f\n", sfBaseStats->deleted_sessions_per_second);
1791 LogMessage("Closed Sessions/Sec : %.3f\n", sfBaseStats->tcp_sessions_closed_per_second);
1792 LogMessage("TimedOut Sessions/Sec : %.3f\n", sfBaseStats->tcp_sessions_timedout_per_second);
1793 LogMessage("Pruned Sessions/Sec : %.3f\n", sfBaseStats->tcp_sessions_pruned_per_second);
1794 LogMessage("Dropped Async Ssns/Sec : %.3f\n", sfBaseStats->tcp_sessions_dropped_async_per_second);
1795
1796 LogMessage("Current Cached Sessions: " STDu64 "\n", sfBaseStats->total_sessions);
1797 LogMessage("Sessions Initializing : " STDu64 "\n", sfBaseStats->curr_tcp_sessions_initializing);
1798 LogMessage("Sessions Established : " STDu64 "\n", sfBaseStats->curr_tcp_sessions_established);
1799 LogMessage("Sessions Closing : " STDu64 "\n", sfBaseStats->curr_tcp_sessions_closing);
1800 LogMessage("Max Cached Sessions : " STDu64 "\n", sfBaseStats->max_sessions);
1801 LogMessage("Max Sessions (interval): " STDu64 "\n", sfBaseStats->max_tcp_sessions_interval);
1802
1803 /* more instrumentation for stream4/frag2 */
1804 LogMessage("Stream Flushes/Sec : %.3f\n", sfBaseStats->stream_flushes_per_second);
1805 LogMessage("Stream Cache Faults/Sec: " STDu64 "\n", sfBaseStats->stream_faults);
1806 LogMessage("Stream Cache Timeouts : " STDu64 "\n", sfBaseStats->stream_timeouts);
1807
1808 LogMessage("Frag Creates()s/Sec : %.3f\n", sfBaseStats->frag_creates_per_second);
1809 LogMessage("Frag Completes()s/Sec : %.3f\n", sfBaseStats->frag_completes_per_second);
1810 LogMessage("Frag Inserts()s/Sec : %.3f\n", sfBaseStats->frag_inserts_per_second);
1811 LogMessage("Frag Deletes/Sec : %.3f\n", sfBaseStats->frag_deletes_per_second);
1812 LogMessage("Frag AutoFrees/Sec : %.3f\n", sfBaseStats->frag_autofrees_per_second);
1813 LogMessage("Frag Flushes/Sec : %.3f\n", sfBaseStats->frag_flushes_per_second);
1814
1815 LogMessage("Current Cached Frags : " STDu64 "\n", sfBaseStats->current_frags);
1816 LogMessage("Max Cached Frags : " STDu64 "\n", sfBaseStats->max_frags);
1817 LogMessage("Frag Timeouts : " STDu64 "\n", sfBaseStats->frag_timeouts);
1818 LogMessage("Frag Faults : " STDu64 "\n\n", sfBaseStats->frag_faults);
1819
1820 LogMessage("New Cached UDP Ssns/Sec: %.3f\n", sfBaseStats->new_udp_sessions_per_second);
1821 LogMessage("Cached UDP Ssns Del/Sec: %.3f\n", sfBaseStats->deleted_udp_sessions_per_second);
1822
1823 LogMessage("Current Cached UDP Ssns: " STDu64 "\n", sfBaseStats->total_udp_sessions);
1824 LogMessage("Max Cached UDP Ssns : " STDu64 "\n\n", sfBaseStats->max_udp_sessions);
1825
1826 #ifdef TARGET_BASED
1827 LogMessage("Attribute Table Hosts : " STDu64 "\n", sfBaseStats->current_attribute_hosts);
1828 LogMessage("Attribute Table Reloads: " STDu64 "\n\n", sfBaseStats->attribute_table_reloads);
1829 #endif
1830
1831 #ifdef NORMALIZER
1832 LogMessage("Number of Normalizations : %d\n", PERF_COUNT_MAX);
1833 for ( iCtr = 0; iCtr < PERF_COUNT_MAX; iCtr++ )
1834 {
1835 LogMessage("%-26s: " STDu64 "\n",
1836 iNames[iCtr], sfBaseStats->pegs[iCtr][NORM_MODE_ON]);
1837 LogMessage("Would %-20s: " STDu64 "\n",
1838 iNames[iCtr], sfBaseStats->pegs[iCtr][NORM_MODE_WOULDA]);
1839 }
1840 #endif
1841 LogMessage("\n");
1842
1843 /*
1844 ** Snort Maximum Performance Statistics
1845 ** These statistics calculate the maximum performance that
1846 ** snort could attain by using the getrusage numbers. We've
1847 ** seen in testing that these numbers come close to the actual
1848 ** throughput for Mbits/Sec and Pkt/Sec. But note that these
1849 ** are not hard numbers and rigorous testing is necessary to
1850 ** establish snort performance on any hardware setting.
1851 */
1852 if (max_stats)
1853 {
1854
1855 LogMessage("Snort Maximum Performance\n");
1856 LogMessage("-------------------------\n\n");
1857
1858 LogMessage("Mbits/Second\n");
1859 LogMessage("----------------\n");
1860 LogMessage("Snort: %.3f\n",sfBaseStats->mbits_per_sec.usertime);
1861 LogMessage("Sniffing: %.3f\n",sfBaseStats->mbits_per_sec.systemtime);
1862 LogMessage("Combined: %.3f\n\n",sfBaseStats->mbits_per_sec.totaltime);
1863
1864
1865 LogMessage("uSeconds/Pkt\n");
1866 LogMessage("----------------\n");
1867 LogMessage("Snort: %.3f\n",sfBaseStats->usecs_per_packet.usertime);
1868 LogMessage("Sniffing: %.3f\n",sfBaseStats->usecs_per_packet.systemtime);
1869 LogMessage("Combined: %.3f\n\n",sfBaseStats->usecs_per_packet.totaltime);
1870
1871 LogMessage("KPkts/Second\n");
1872 LogMessage("------------------\n");
1873 LogMessage("Snort: %.3f\n",sfBaseStats->kpackets_per_sec.usertime);
1874 LogMessage("Sniffing: %.3f\n",sfBaseStats->kpackets_per_sec.systemtime);
1875 LogMessage("Combined: %.3f\n\n",sfBaseStats->kpackets_per_sec.totaltime);
1876 }
1877 }
1878
1879
1880