The FreeRADIUS server $Id: a4e7f8c94e8038b7627bcf52356b7ed15955c1d7 $
Loading...
Searching...
No Matches
stats.c
Go to the documentation of this file.
1/*
2 * stats.c Internal statistics handling.
3 *
4 * Version: $Id: 6046869e53c5da24bace37628b2b191934ce1613 $
5 *
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 2 of the License, or
9 * (at your option) any later version.
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 St, Fifth Floor, Boston, MA 02110-1301, USA
19 *
20 * @copyright 2008 The FreeRADIUS server project
21 * @copyright 2008 Alan DeKok (aland@deployingradius.com)
22 */
23
24RCSID("$Id: 6046869e53c5da24bace37628b2b191934ce1613 $")
25
26#include <freeradius-devel/server/client.h>
27
28#include <freeradius-devel/util/misc.h>
29#include <freeradius-devel/radius/defs.h>
30
31#define FR_STATS_INIT { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, \
32 { 0, 0, 0, 0, 0, 0, 0, 0 }}
33
36
38{
39 if (request->counted) return;
40
41#if 0
42 if (!request->listener) return;
43 if (!request->client) return;
44 if (!request->packet) return;
45#endif
46
47#if 0
48 if ((request->listener->type != RAD_LISTEN_NONE) &&
49 (request->listener->type != RAD_LISTEN_ACCT) &&
50 (request->listener->type != RAD_LISTEN_AUTH)) return;
51#endif
52 /* don't count statistic requests */
53 if (request->packet->code == FR_RADIUS_CODE_STATUS_SERVER)
54 return;
55
56#undef INC_AUTH
57#define INC_AUTH(_x) do { radius_auth_stats._x++;request->client->auth._x++; } while (0)
58
59#undef INC_ACCT
60#define INC_ACCT(_x) do { radius_acct_stats._x++;request->client->acct._x++; } while (0)
61
62 /*
63 * Update the statistics.
64 *
65 * Note that we do NOT do this in a child thread.
66 * Instead, we update the stats when a request is
67 * deleted, because only the main server thread calls
68 * this function, which makes it thread-safe.
69 */
70 if (request->reply && (request->packet->code != FR_RADIUS_CODE_STATUS_SERVER)) switch (request->reply->code) {
72 INC_AUTH(total_access_accepts);
73
74 auth_stats:
75 INC_AUTH(total_responses);
76
77 /*
78 * FIXME: Do the time calculations once...
79 */
81 request->packet->timestamp,
82 request->reply->timestamp);
83 fr_stats_bins(&request->client->auth,
84 request->packet->timestamp,
85 request->reply->timestamp);
86 break;
87
89 INC_AUTH(total_access_rejects);
90 goto auth_stats;
91
93 INC_AUTH(total_access_challenges);
94 goto auth_stats;
95
97 INC_ACCT(total_responses);
99 request->packet->timestamp,
100 request->reply->timestamp);
101 break;
102
103 /*
104 * No response, it must have been a bad
105 * authenticator.
106 */
107 case 0:
108 switch (request->packet->code) {
110 if (request->reply->id == -1) {
111 INC_AUTH(total_bad_authenticators);
112 } else {
113 INC_AUTH(total_packets_dropped);
114 }
115 break;
116
117
119 if (request->reply->id == -1) {
120 INC_ACCT(total_bad_authenticators);
121 } else {
122 INC_ACCT(total_packets_dropped);
123 }
124 break;
125
126 default:
127 break;
128 }
129 break;
130
131 default:
132 break;
133 }
134
135 request->counted = true;
136}
137
138/** Sort latency times into bins
139 *
140 * This solves the problem of attempting to keep min/max/avg latencies, whilst
141 * not knowing what the polling frequency will be.
142 *
143 * @param[out] stats Holding monotonically increasing stats bins.
144 * @param[in] start of the request.
145 * @param[in] end of the request.
146 */
148{
149 fr_time_delta_t diff;
150 uint32_t delay;
151
152 if (fr_time_lt(end, start)) return; /* bad data */
153 diff = fr_time_sub(end, start);
154
156 stats->elapsed[7]++;
157 } else {
158 int i;
159 uint32_t cmp;
160
161 delay = (uint32_t) fr_time_delta_to_usec(diff); /* diff is less than 10s */
162
163 cmp = 10;
164 for (i = 0; i < 7; i++) {
165 if (delay < cmp) {
166 stats->elapsed[i]++;
167 break;
168 }
169 cmp *= 10;
170 }
171 }
172}
static uint8_t request[4]
#define RCSID(id)
Definition build.h:603
@ FR_RADIUS_CODE_ACCESS_CHALLENGE
RFC2865 - Access-Challenge.
Definition defs.h:43
@ FR_RADIUS_CODE_ACCESS_REQUEST
RFC2865 - Access-Request.
Definition defs.h:33
@ FR_RADIUS_CODE_STATUS_SERVER
RFC2865/RFC5997 - Status Server (request)
Definition defs.h:44
@ FR_RADIUS_CODE_ACCESS_ACCEPT
RFC2865 - Access-Accept.
Definition defs.h:34
@ FR_RADIUS_CODE_ACCOUNTING_RESPONSE
RFC2866 - Accounting-Response.
Definition defs.h:37
@ FR_RADIUS_CODE_ACCOUNTING_REQUEST
RFC2866 - Accounting-Request.
Definition defs.h:36
@ FR_RADIUS_CODE_ACCESS_REJECT
RFC2865 - Access-Reject.
Definition defs.h:35
uint64_t elapsed[8]
Definition stats.h:49
unsigned int uint32_t
void fr_stats_bins(fr_stats_t *stats, fr_time_t start, fr_time_t end)
Sort latency times into bins.
Definition stats.c:147
void request_stats_final(request_t *request)
Definition stats.c:37
fr_stats_t radius_auth_stats
Definition stats.c:34
#define FR_STATS_INIT
Definition stats.c:31
fr_stats_t radius_acct_stats
Definition stats.c:35
#define INC_AUTH(_x)
#define INC_ACCT(_x)
static fr_time_delta_t fr_time_delta_from_sec(int64_t sec)
Definition time.h:599
static int64_t fr_time_delta_to_usec(fr_time_delta_t delta)
Definition time.h:641
#define fr_time_delta_gteq(_a, _b)
Definition time.h:284
#define fr_time_sub(_a, _b)
Subtract one time from another.
Definition time.h:229
#define fr_time_lt(_a, _b)
Definition time.h:239
A time delta, a difference in time measured in nanoseconds.
Definition time.h:80
"server local" time.
Definition time.h:69