3 * $Id: snmp_agent.cc,v 1.76 2000/05/16 07:06:06 wessels Exp $
5 * DEBUG: section 49 SNMP Interface
6 * AUTHOR: Kostas Anagnostakis
8 * SQUID Internet Object Cache http://squid.nlanr.net/Squid/
9 * ----------------------------------------------------------
11 * Squid is the result of efforts by numerous individuals from the
12 * Internet community. Development is led by Duane Wessels of the
13 * National Laboratory for Applied Network Research and funded by the
14 * National Science Foundation. Squid is Copyrighted (C) 1998 by
15 * the Regents of the University of California. Please see the
16 * COPYRIGHT file for full details. Squid incorporates software
17 * developed and/or copyrighted by other sources. Please see the
18 * CREDITS file for full details.
20 * This program is free software; you can redistribute it and/or modify
21 * it under the terms of the GNU General Public License as published by
22 * the Free Software Foundation; either version 2 of the License, or
23 * (at your option) any later version.
25 * This program is distributed in the hope that it will be useful,
26 * but WITHOUT ANY WARRANTY; without even the implied warranty of
27 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
28 * GNU General Public License for more details.
30 * You should have received a copy of the GNU General Public License
31 * along with this program; if not, write to the Free Software
32 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111, USA.
38 #include "cache_snmp.h"
40 extern StatCounters
*snmpStatGet(int);
42 /************************************************************************
44 SQUID MIB Implementation
46 ************************************************************************/
49 snmp_sysFn(variable_list
* Var
, snint
* ErrP
)
51 variable_list
*Answer
= NULL
;
52 debug(49, 5) ("snmp_sysFn: Processing request:\n", Var
->name
[LEN_SQ_SYS
]);
53 snmpDebugOid(5, Var
->name
, Var
->name_length
);
54 *ErrP
= SNMP_ERR_NOERROR
;
55 switch (Var
->name
[LEN_SQ_SYS
]) {
57 Answer
= snmp_var_new_integer(Var
->name
, Var
->name_length
,
62 Answer
= snmp_var_new_integer(Var
->name
, Var
->name_length
,
67 Answer
= snmp_var_new_integer(Var
->name
, Var
->name_length
,
68 tvSubDsec(squid_start
, current_time
) * 100,
72 *ErrP
= SNMP_ERR_NOSUCHNAME
;
79 snmp_confFn(variable_list
* Var
, snint
* ErrP
)
81 variable_list
*Answer
= NULL
;
83 debug(49, 5) ("snmp_confFn: Processing request with magic %d!\n", Var
->name
[8]);
84 *ErrP
= SNMP_ERR_NOERROR
;
85 switch (Var
->name
[LEN_SQ_CONF
]) {
87 Answer
= snmp_var_new(Var
->name
, Var
->name_length
);
88 Answer
->type
= ASN_OCTET_STR
;
89 Answer
->val_len
= strlen(Config
.adminEmail
);
90 Answer
->val
.string
= (u_char
*) xstrdup(Config
.adminEmail
);
93 Answer
= snmp_var_new(Var
->name
, Var
->name_length
);
94 Answer
->type
= ASN_OCTET_STR
;
95 Answer
->val_len
= strlen(appname
);
96 Answer
->val
.string
= (u_char
*) xstrdup(appname
);
99 Answer
= snmp_var_new(Var
->name
, Var
->name_length
);
100 Answer
->type
= ASN_OCTET_STR
;
101 Answer
->val_len
= strlen(SQUID_VERSION
);
102 Answer
->val
.string
= (u_char
*) xstrdup(SQUID_VERSION
);
105 switch (Var
->name
[LEN_SQ_CONF
+ 1]) {
107 Answer
= snmp_var_new_integer(Var
->name
, Var
->name_length
,
108 (snint
) Config
.memMaxSize
>> 20,
111 case CONF_ST_SWMAXSZ
:
112 Answer
= snmp_var_new_integer(Var
->name
, Var
->name_length
,
113 (snint
) Config
.Swap
.maxSize
>> 10,
117 Answer
= snmp_var_new_integer(Var
->name
, Var
->name_length
,
118 (snint
) Config
.Swap
.highWaterMark
,
122 Answer
= snmp_var_new_integer(Var
->name
, Var
->name_length
,
123 (snint
) Config
.Swap
.lowWaterMark
,
127 *ErrP
= SNMP_ERR_NOSUCHNAME
;
132 Answer
= snmp_var_new(Var
->name
, Var
->name_length
);
133 if (!(cp
= Config
.debugOptions
))
135 Answer
->type
= ASN_OCTET_STR
;
136 Answer
->val_len
= strlen(cp
);
137 Answer
->val
.string
= (u_char
*) xstrdup(cp
);
140 *ErrP
= SNMP_ERR_NOSUCHNAME
;
147 snmp_meshPtblFn(variable_list
* Var
, snint
* ErrP
)
149 variable_list
*Answer
= NULL
;
150 struct in_addr
*laddr
;
154 debug(49, 5) ("snmp_meshPtblFn: peer %d requested!\n", Var
->name
[LEN_SQ_MESH
+ 3]);
155 *ErrP
= SNMP_ERR_NOERROR
;
156 laddr
= oid2addr(&Var
->name
[LEN_SQ_MESH
+ 3]);
157 for (p
= Config
.peers
; p
!= NULL
; p
= p
->next
, cnt
++)
158 if (p
->in_addr
.sin_addr
.s_addr
== laddr
->s_addr
)
161 *ErrP
= SNMP_ERR_NOSUCHNAME
;
164 switch (Var
->name
[LEN_SQ_MESH
+ 2]) {
167 Answer
= snmp_var_new(Var
->name
, Var
->name_length
);
168 Answer
->type
= ASN_OCTET_STR
;
169 Answer
->val_len
= strlen(cp
);
170 Answer
->val
.string
= (u_char
*) xstrdup(cp
);
173 Answer
= snmp_var_new_integer(Var
->name
, Var
->name_length
,
174 (snint
) p
->in_addr
.sin_addr
.s_addr
,
178 Answer
= snmp_var_new_integer(Var
->name
, Var
->name_length
,
179 (snint
) p
->http_port
,
183 Answer
= snmp_var_new_integer(Var
->name
, Var
->name_length
,
188 Answer
= snmp_var_new_integer(Var
->name
, Var
->name_length
,
192 case MESH_PTBL_STATE
:
193 Answer
= snmp_var_new_integer(Var
->name
, Var
->name_length
,
194 (snint
) neighborUp(p
),
198 Answer
= snmp_var_new_integer(Var
->name
, Var
->name_length
,
202 case MESH_PTBL_PACKED
:
203 Answer
= snmp_var_new_integer(Var
->name
, Var
->name_length
,
204 p
->stats
.pings_acked
,
207 case MESH_PTBL_FETCHES
:
208 Answer
= snmp_var_new_integer(Var
->name
, Var
->name_length
,
213 Answer
= snmp_var_new_integer(Var
->name
, Var
->name_length
,
218 Answer
= snmp_var_new_integer(Var
->name
, Var
->name_length
,
219 p
->stats
.ignored_replies
,
222 case MESH_PTBL_KEEPAL_S
:
223 Answer
= snmp_var_new_integer(Var
->name
, Var
->name_length
,
224 p
->stats
.n_keepalives_sent
,
227 case MESH_PTBL_KEEPAL_R
:
228 Answer
= snmp_var_new_integer(Var
->name
, Var
->name_length
,
229 p
->stats
.n_keepalives_recv
,
233 *ErrP
= SNMP_ERR_NOSUCHNAME
;
240 snmp_prfSysFn(variable_list
* Var
, snint
* ErrP
)
242 variable_list
*Answer
= NULL
;
243 static struct rusage rusage
;
244 debug(49, 5) ("snmp_prfSysFn: Processing request with magic %d!\n", Var
->name
[LEN_SQ_PRF
+ 1]);
245 *ErrP
= SNMP_ERR_NOERROR
;
246 switch (Var
->name
[LEN_SQ_PRF
+ 1]) {
248 squid_getrusage(&rusage
);
249 Answer
= snmp_var_new_integer(Var
->name
, Var
->name_length
,
250 rusage_pagefaults(&rusage
),
254 Answer
= snmp_var_new_integer(Var
->name
, Var
->name_length
,
258 case PERF_SYS_MEMUSAGE
:
259 Answer
= snmp_var_new_integer(Var
->name
, Var
->name_length
,
260 (snint
) memTotalAllocated() >> 10,
263 case PERF_SYS_CPUTIME
:
264 squid_getrusage(&rusage
);
265 Answer
= snmp_var_new_integer(Var
->name
, Var
->name_length
,
266 (snint
) rusage_cputime(&rusage
),
269 case PERF_SYS_CPUUSAGE
:
270 squid_getrusage(&rusage
);
271 Answer
= snmp_var_new_integer(Var
->name
, Var
->name_length
,
272 (snint
) dpercent(rusage_cputime(&rusage
), tvSubDsec(squid_start
, current_time
)),
275 case PERF_SYS_MAXRESSZ
:
276 squid_getrusage(&rusage
);
277 Answer
= snmp_var_new_integer(Var
->name
, Var
->name_length
,
278 (snint
) rusage_maxrss(&rusage
),
281 case PERF_SYS_CURLRUEXP
:
282 /* No global LRU info anymore */
283 Answer
= snmp_var_new_integer(Var
->name
, Var
->name_length
,
287 case PERF_SYS_CURUNLREQ
:
288 Answer
= snmp_var_new_integer(Var
->name
, Var
->name_length
,
289 (snint
) Counter
.unlink
.requests
,
292 case PERF_SYS_CURUNUSED_FD
:
293 Answer
= snmp_var_new_integer(Var
->name
, Var
->name_length
,
294 (snint
) Squid_MaxFD
- Number_FD
,
297 case PERF_SYS_CURRESERVED_FD
:
298 Answer
= snmp_var_new_integer(Var
->name
, Var
->name_length
,
302 case PERF_SYS_NUMOBJCNT
:
303 Answer
= snmp_var_new_integer(Var
->name
, Var
->name_length
,
304 (snint
) memInUse(MEM_STOREENTRY
),
308 *ErrP
= SNMP_ERR_NOSUCHNAME
;
315 snmp_prfProtoFn(variable_list
* Var
, snint
* ErrP
)
317 variable_list
*Answer
= NULL
;
318 static StatCounters
*f
= NULL
;
319 static StatCounters
*l
= NULL
;
322 debug(49, 5) ("snmp_prfProtoFn: Processing request with magic %d!\n", Var
->name
[LEN_SQ_PRF
]);
323 *ErrP
= SNMP_ERR_NOERROR
;
324 switch (Var
->name
[LEN_SQ_PRF
+ 1]) {
325 case PERF_PROTOSTAT_AGGR
: /* cacheProtoAggregateStats */
326 switch (Var
->name
[LEN_SQ_PRF
+ 2]) {
327 case PERF_PROTOSTAT_AGGR_HTTP_REQ
:
328 Answer
= snmp_var_new_integer(Var
->name
, Var
->name_length
,
329 (snint
) Counter
.client_http
.requests
,
332 case PERF_PROTOSTAT_AGGR_HTTP_HITS
:
333 Answer
= snmp_var_new_integer(Var
->name
, Var
->name_length
,
334 (snint
) Counter
.client_http
.hits
,
337 case PERF_PROTOSTAT_AGGR_HTTP_ERRORS
:
338 Answer
= snmp_var_new_integer(Var
->name
, Var
->name_length
,
339 (snint
) Counter
.client_http
.errors
,
342 case PERF_PROTOSTAT_AGGR_HTTP_KBYTES_IN
:
343 Answer
= snmp_var_new_integer(Var
->name
, Var
->name_length
,
344 (snint
) Counter
.client_http
.kbytes_in
.kb
,
347 case PERF_PROTOSTAT_AGGR_HTTP_KBYTES_OUT
:
348 Answer
= snmp_var_new_integer(Var
->name
, Var
->name_length
,
349 (snint
) Counter
.client_http
.kbytes_out
.kb
,
352 case PERF_PROTOSTAT_AGGR_ICP_S
:
353 Answer
= snmp_var_new_integer(Var
->name
, Var
->name_length
,
354 (snint
) Counter
.icp
.pkts_sent
,
357 case PERF_PROTOSTAT_AGGR_ICP_R
:
358 Answer
= snmp_var_new_integer(Var
->name
, Var
->name_length
,
359 (snint
) Counter
.icp
.pkts_recv
,
362 case PERF_PROTOSTAT_AGGR_ICP_SKB
:
363 Answer
= snmp_var_new_integer(Var
->name
, Var
->name_length
,
364 (snint
) Counter
.icp
.kbytes_sent
.kb
,
367 case PERF_PROTOSTAT_AGGR_ICP_RKB
:
368 Answer
= snmp_var_new_integer(Var
->name
, Var
->name_length
,
369 (snint
) Counter
.icp
.kbytes_recv
.kb
,
372 case PERF_PROTOSTAT_AGGR_REQ
:
373 Answer
= snmp_var_new_integer(Var
->name
, Var
->name_length
,
374 (snint
) Counter
.server
.all
.requests
,
377 case PERF_PROTOSTAT_AGGR_ERRORS
:
378 Answer
= snmp_var_new_integer(Var
->name
, Var
->name_length
,
379 (snint
) Counter
.server
.all
.errors
,
382 case PERF_PROTOSTAT_AGGR_KBYTES_IN
:
383 Answer
= snmp_var_new_integer(Var
->name
, Var
->name_length
,
384 (snint
) Counter
.server
.all
.kbytes_in
.kb
,
387 case PERF_PROTOSTAT_AGGR_KBYTES_OUT
:
388 Answer
= snmp_var_new_integer(Var
->name
, Var
->name_length
,
389 (snint
) Counter
.server
.all
.kbytes_out
.kb
,
392 case PERF_PROTOSTAT_AGGR_CURSWAP
:
393 Answer
= snmp_var_new_integer(Var
->name
, Var
->name_length
,
394 (snint
) store_swap_size
,
397 case PERF_PROTOSTAT_AGGR_CLIENTS
:
398 Answer
= snmp_var_new_integer(Var
->name
, Var
->name_length
,
399 (snint
) Counter
.client_http
.clients
,
403 *ErrP
= SNMP_ERR_NOSUCHNAME
;
407 case PERF_PROTOSTAT_MEDIAN
:
408 if (Var
->name_length
== LEN_SQ_PRF
+ 5)
409 minutes
= Var
->name
[LEN_SQ_PRF
+ 4];
412 if ((minutes
< 1) || (minutes
> 60))
415 l
= snmpStatGet(minutes
);
416 debug(49, 8) ("median: min= %d, %d l= %x , f = %x\n", minutes
,
417 Var
->name
[LEN_SQ_PRF
+ 3], l
, f
);
418 debug(49, 8) ("median: l= %x , f = %x\n", l
, f
);
419 switch (Var
->name
[LEN_SQ_PRF
+ 3]) {
420 case PERF_MEDIAN_TIME
:
423 case PERF_MEDIAN_HTTP_ALL
:
424 x
= statHistDeltaMedian(&l
->client_http
.all_svc_time
,
425 &f
->client_http
.all_svc_time
);
427 case PERF_MEDIAN_HTTP_MISS
:
428 x
= statHistDeltaMedian(&l
->client_http
.miss_svc_time
,
429 &f
->client_http
.miss_svc_time
);
431 case PERF_MEDIAN_HTTP_NM
:
432 x
= statHistDeltaMedian(&l
->client_http
.nm_svc_time
,
433 &f
->client_http
.nm_svc_time
);
435 case PERF_MEDIAN_HTTP_HIT
:
436 x
= statHistDeltaMedian(&l
->client_http
.hit_svc_time
,
437 &f
->client_http
.hit_svc_time
);
439 case PERF_MEDIAN_ICP_QUERY
:
440 x
= statHistDeltaMedian(&l
->icp
.query_svc_time
, &f
->icp
.query_svc_time
);
442 case PERF_MEDIAN_ICP_REPLY
:
443 x
= statHistDeltaMedian(&l
->icp
.reply_svc_time
, &f
->icp
.reply_svc_time
);
445 case PERF_MEDIAN_DNS
:
446 x
= statHistDeltaMedian(&l
->dns
.svc_time
, &f
->dns
.svc_time
);
448 case PERF_MEDIAN_RHR
:
449 x
= statRequestHitRatio(minutes
);
451 case PERF_MEDIAN_BHR
:
452 x
= statByteHitRatio(minutes
);
455 *ErrP
= SNMP_ERR_NOSUCHNAME
;
458 return snmp_var_new_integer(Var
->name
, Var
->name_length
,
462 *ErrP
= SNMP_ERR_NOSUCHNAME
;