Merge branch 'Teaman-ND' into Teaman-RT
[tomato.git] / release / src / router / zebra / ospfd / ospf_snmp.c
blobe82bdefac2464ae989e557ac94d19acf76fce607
1 /* OSPFv2 SNMP support
2 * Copyright (C) 2000 IP Infusion Inc.
4 * Written by Kunihiro Ishiguro <kunihiro@zebra.org>
6 * This file is part of GNU Zebra.
8 * GNU Zebra is free software; you can redistribute it and/or modify it
9 * under the terms of the GNU General Public License as published by the
10 * Free Software Foundation; either version 2, or (at your option) any
11 * later version.
13 * GNU Zebra is distributed in the hope that it will be useful, but
14 * WITHOUT ANY WARRANTY; without even the implied warranty of
15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
16 * General Public License for more details.
18 * You should have received a copy of the GNU General Public License
19 * along with GNU Zebra; see the file COPYING. If not, write to the Free
20 * Software Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
21 * 02111-1307, USA.
24 #include <zebra.h>
26 #ifdef HAVE_SNMP
28 #ifdef HAVE_NETSNMP
29 #include <net-snmp/net-snmp-config.h>
30 #endif /* HAVE_NETSNMP */
32 #include <asn1.h>
33 #include <snmp.h>
34 #include <snmp_impl.h>
36 #include "if.h"
37 #include "log.h"
38 #include "prefix.h"
39 #include "table.h"
40 #include "command.h"
41 #include "memory.h"
42 #include "smux.h"
44 #include "ospfd/ospfd.h"
45 #include "ospfd/ospf_interface.h"
46 #include "ospfd/ospf_asbr.h"
47 #include "ospfd/ospf_lsa.h"
48 #include "ospfd/ospf_lsdb.h"
49 #include "ospfd/ospf_abr.h"
50 #include "ospfd/ospf_neighbor.h"
51 #include "ospfd/ospf_nsm.h"
52 #include "ospfd/ospf_flood.h"
54 /* OSPF2-MIB. */
55 #define OSPF2MIB 1,3,6,1,2,1,14
57 /* Zebra enterprise OSPF MIB. This variable is used for register
58 OSPF MIB to SNMP agent under SMUX protocol. */
59 #define OSPFDOID 1,3,6,1,4,1,3317,1,2,5
61 /* OSPF MIB General Group values. */
62 #define OSPFROUTERID 1
63 #define OSPFADMINSTAT 2
64 #define OSPFVERSIONNUMBER 3
65 #define OSPFAREABDRRTRSTATUS 4
66 #define OSPFASBDRRTRSTATUS 5
67 #define OSPFEXTERNLSACOUNT 6
68 #define OSPFEXTERNLSACKSUMSUM 7
69 #define OSPFTOSSUPPORT 8
70 #define OSPFORIGINATENEWLSAS 9
71 #define OSPFRXNEWLSAS 10
72 #define OSPFEXTLSDBLIMIT 11
73 #define OSPFMULTICASTEXTENSIONS 12
74 #define OSPFEXITOVERFLOWINTERVAL 13
75 #define OSPFDEMANDEXTENSIONS 14
77 /* OSPF MIB ospfAreaTable. */
78 #define OSPFAREAID 1
79 #define OSPFAUTHTYPE 2
80 #define OSPFIMPORTASEXTERN 3
81 #define OSPFSPFRUNS 4
82 #define OSPFAREABDRRTRCOUNT 5
83 #define OSPFASBDRRTRCOUNT 6
84 #define OSPFAREALSACOUNT 7
85 #define OSPFAREALSACKSUMSUM 8
86 #define OSPFAREASUMMARY 9
87 #define OSPFAREASTATUS 10
89 /* OSPF MIB ospfStubAreaTable. */
90 #define OSPFSTUBAREAID 1
91 #define OSPFSTUBTOS 2
92 #define OSPFSTUBMETRIC 3
93 #define OSPFSTUBSTATUS 4
94 #define OSPFSTUBMETRICTYPE 5
96 /* OSPF MIB ospfLsdbTable. */
97 #define OSPFLSDBAREAID 1
98 #define OSPFLSDBTYPE 2
99 #define OSPFLSDBLSID 3
100 #define OSPFLSDBROUTERID 4
101 #define OSPFLSDBSEQUENCE 5
102 #define OSPFLSDBAGE 6
103 #define OSPFLSDBCHECKSUM 7
104 #define OSPFLSDBADVERTISEMENT 8
106 /* OSPF MIB ospfAreaRangeTable. */
107 #define OSPFAREARANGEAREAID 1
108 #define OSPFAREARANGENET 2
109 #define OSPFAREARANGEMASK 3
110 #define OSPFAREARANGESTATUS 4
111 #define OSPFAREARANGEEFFECT 5
113 /* OSPF MIB ospfHostTable. */
114 #define OSPFHOSTIPADDRESS 1
115 #define OSPFHOSTTOS 2
116 #define OSPFHOSTMETRIC 3
117 #define OSPFHOSTSTATUS 4
118 #define OSPFHOSTAREAID 5
120 /* OSPF MIB ospfIfTable. */
121 #define OSPFIFIPADDRESS 1
122 #define OSPFADDRESSLESSIF 2
123 #define OSPFIFAREAID 3
124 #define OSPFIFTYPE 4
125 #define OSPFIFADMINSTAT 5
126 #define OSPFIFRTRPRIORITY 6
127 #define OSPFIFTRANSITDELAY 7
128 #define OSPFIFRETRANSINTERVAL 8
129 #define OSPFIFHELLOINTERVAL 9
130 #define OSPFIFRTRDEADINTERVAL 10
131 #define OSPFIFPOLLINTERVAL 11
132 #define OSPFIFSTATE 12
133 #define OSPFIFDESIGNATEDROUTER 13
134 #define OSPFIFBACKUPDESIGNATEDROUTER 14
135 #define OSPFIFEVENTS 15
136 #define OSPFIFAUTHKEY 16
137 #define OSPFIFSTATUS 17
138 #define OSPFIFMULTICASTFORWARDING 18
139 #define OSPFIFDEMAND 19
140 #define OSPFIFAUTHTYPE 20
142 /* OSPF MIB ospfIfMetricTable. */
143 #define OSPFIFMETRICIPADDRESS 1
144 #define OSPFIFMETRICADDRESSLESSIF 2
145 #define OSPFIFMETRICTOS 3
146 #define OSPFIFMETRICVALUE 4
147 #define OSPFIFMETRICSTATUS 5
149 /* OSPF MIB ospfVirtIfTable. */
150 #define OSPFVIRTIFAREAID 1
151 #define OSPFVIRTIFNEIGHBOR 2
152 #define OSPFVIRTIFTRANSITDELAY 3
153 #define OSPFVIRTIFRETRANSINTERVAL 4
154 #define OSPFVIRTIFHELLOINTERVAL 5
155 #define OSPFVIRTIFRTRDEADINTERVAL 6
156 #define OSPFVIRTIFSTATE 7
157 #define OSPFVIRTIFEVENTS 8
158 #define OSPFVIRTIFAUTHKEY 9
159 #define OSPFVIRTIFSTATUS 10
160 #define OSPFVIRTIFAUTHTYPE 11
162 /* OSPF MIB ospfNbrTable. */
163 #define OSPFNBRIPADDR 1
164 #define OSPFNBRADDRESSLESSINDEX 2
165 #define OSPFNBRRTRID 3
166 #define OSPFNBROPTIONS 4
167 #define OSPFNBRPRIORITY 5
168 #define OSPFNBRSTATE 6
169 #define OSPFNBREVENTS 7
170 #define OSPFNBRLSRETRANSQLEN 8
171 #define OSPFNBMANBRSTATUS 9
172 #define OSPFNBMANBRPERMANENCE 10
173 #define OSPFNBRHELLOSUPPRESSED 11
175 /* OSPF MIB ospfVirtNbrTable. */
176 #define OSPFVIRTNBRAREA 1
177 #define OSPFVIRTNBRRTRID 2
178 #define OSPFVIRTNBRIPADDR 3
179 #define OSPFVIRTNBROPTIONS 4
180 #define OSPFVIRTNBRSTATE 5
181 #define OSPFVIRTNBREVENTS 6
182 #define OSPFVIRTNBRLSRETRANSQLEN 7
183 #define OSPFVIRTNBRHELLOSUPPRESSED 8
185 /* OSPF MIB ospfExtLsdbTable. */
186 #define OSPFEXTLSDBTYPE 1
187 #define OSPFEXTLSDBLSID 2
188 #define OSPFEXTLSDBROUTERID 3
189 #define OSPFEXTLSDBSEQUENCE 4
190 #define OSPFEXTLSDBAGE 5
191 #define OSPFEXTLSDBCHECKSUM 6
192 #define OSPFEXTLSDBADVERTISEMENT 7
194 /* OSPF MIB ospfAreaAggregateTable. */
195 #define OSPFAREAAGGREGATEAREAID 1
196 #define OSPFAREAAGGREGATELSDBTYPE 2
197 #define OSPFAREAAGGREGATENET 3
198 #define OSPFAREAAGGREGATEMASK 4
199 #define OSPFAREAAGGREGATESTATUS 5
200 #define OSPFAREAAGGREGATEEFFECT 6
202 /* SYNTAX Status from OSPF-MIB. */
203 #define OSPF_STATUS_ENABLED 1
204 #define OSPF_STATUS_DISABLED 2
206 /* SNMP value hack. */
207 #define COUNTER ASN_COUNTER
208 #define INTEGER ASN_INTEGER
209 #define GAUGE ASN_GAUGE
210 #define TIMETICKS ASN_TIMETICKS
211 #define IPADDRESS ASN_IPADDRESS
212 #define STRING ASN_OCTET_STR
214 /* Declare static local variables for convenience. */
215 SNMP_LOCAL_VARIABLES
217 /* OSPF-MIB instances. */
218 oid ospf_oid [] = { OSPF2MIB };
219 oid ospfd_oid [] = { OSPFDOID };
221 /* IP address 0.0.0.0. */
222 static struct in_addr ospf_empty_addr = {0};
224 /* Hook functions. */
225 static u_char *ospfGeneralGroup ();
226 static u_char *ospfAreaEntry ();
227 static u_char *ospfStubAreaEntry ();
228 static u_char *ospfLsdbEntry ();
229 static u_char *ospfAreaRangeEntry ();
230 static u_char *ospfHostEntry ();
231 static u_char *ospfIfEntry ();
232 static u_char *ospfIfMetricEntry ();
233 static u_char *ospfVirtIfEntry ();
234 static u_char *ospfNbrEntry ();
235 static u_char *ospfVirtNbrEntry ();
236 static u_char *ospfExtLsdbEntry ();
237 static u_char *ospfAreaAggregateEntry ();
239 struct variable ospf_variables[] =
241 /* OSPF general variables */
242 {OSPFROUTERID, IPADDRESS, RWRITE, ospfGeneralGroup,
243 2, {1, 1}},
244 {OSPFADMINSTAT, INTEGER, RWRITE, ospfGeneralGroup,
245 2, {1, 2}},
246 {OSPFVERSIONNUMBER, INTEGER, RONLY, ospfGeneralGroup,
247 2, {1, 3}},
248 {OSPFAREABDRRTRSTATUS, INTEGER, RONLY, ospfGeneralGroup,
249 2, {1, 4}},
250 {OSPFASBDRRTRSTATUS, INTEGER, RWRITE, ospfGeneralGroup,
251 2, {1, 5}},
252 {OSPFEXTERNLSACOUNT, GAUGE, RONLY, ospfGeneralGroup,
253 2, {1, 6}},
254 {OSPFEXTERNLSACKSUMSUM, INTEGER, RONLY, ospfGeneralGroup,
255 2, {1, 7}},
256 {OSPFTOSSUPPORT, INTEGER, RWRITE, ospfGeneralGroup,
257 2, {1, 8}},
258 {OSPFORIGINATENEWLSAS, COUNTER, RONLY, ospfGeneralGroup,
259 2, {1, 9}},
260 {OSPFRXNEWLSAS, COUNTER, RONLY, ospfGeneralGroup,
261 2, {1, 10}},
262 {OSPFEXTLSDBLIMIT, INTEGER, RWRITE, ospfGeneralGroup,
263 2, {1, 11}},
264 {OSPFMULTICASTEXTENSIONS, INTEGER, RWRITE, ospfGeneralGroup,
265 2, {1, 12}},
266 {OSPFEXITOVERFLOWINTERVAL, INTEGER, RWRITE, ospfGeneralGroup,
267 2, {1, 13}},
268 {OSPFDEMANDEXTENSIONS, INTEGER, RWRITE, ospfGeneralGroup,
269 2, {1, 14}},
271 /* OSPF area data structure. */
272 {OSPFAREAID, IPADDRESS, RONLY, ospfAreaEntry,
273 3, {2, 1, 1}},
274 {OSPFAUTHTYPE, INTEGER, RWRITE, ospfAreaEntry,
275 3, {2, 1, 2}},
276 {OSPFIMPORTASEXTERN, INTEGER, RWRITE, ospfAreaEntry,
277 3, {2, 1, 3}},
278 {OSPFSPFRUNS, COUNTER, RONLY, ospfAreaEntry,
279 3, {2, 1, 4}},
280 {OSPFAREABDRRTRCOUNT, GAUGE, RONLY, ospfAreaEntry,
281 3, {2, 1, 5}},
282 {OSPFASBDRRTRCOUNT, GAUGE, RONLY, ospfAreaEntry,
283 3, {2, 1, 6}},
284 {OSPFAREALSACOUNT, GAUGE, RONLY, ospfAreaEntry,
285 3, {2, 1, 7}},
286 {OSPFAREALSACKSUMSUM, INTEGER, RONLY, ospfAreaEntry,
287 3, {2, 1, 8}},
288 {OSPFAREASUMMARY, INTEGER, RWRITE, ospfAreaEntry,
289 3, {2, 1, 9}},
290 {OSPFAREASTATUS, INTEGER, RWRITE, ospfAreaEntry,
291 3, {2, 1, 10}},
293 /* OSPF stub area information. */
294 {OSPFSTUBAREAID, IPADDRESS, RONLY, ospfStubAreaEntry,
295 3, {3, 1, 1}},
296 {OSPFSTUBTOS, INTEGER, RONLY, ospfStubAreaEntry,
297 3, {3, 1, 2}},
298 {OSPFSTUBMETRIC, INTEGER, RWRITE, ospfStubAreaEntry,
299 3, {3, 1, 3}},
300 {OSPFSTUBSTATUS, INTEGER, RWRITE, ospfStubAreaEntry,
301 3, {3, 1, 4}},
302 {OSPFSTUBMETRICTYPE, INTEGER, RWRITE, ospfStubAreaEntry,
303 3, {3, 1, 5}},
305 /* OSPF link state database. */
306 {OSPFLSDBAREAID, IPADDRESS, RONLY, ospfLsdbEntry,
307 3, {4, 1, 1}},
308 {OSPFLSDBTYPE, INTEGER, RONLY, ospfLsdbEntry,
309 3, {4, 1, 2}},
310 {OSPFLSDBLSID, IPADDRESS, RONLY, ospfLsdbEntry,
311 3, {4, 1, 3}},
312 {OSPFLSDBROUTERID, IPADDRESS, RONLY, ospfLsdbEntry,
313 3, {4, 1, 4}},
314 {OSPFLSDBSEQUENCE, INTEGER, RONLY, ospfLsdbEntry,
315 3, {4, 1, 5}},
316 {OSPFLSDBAGE, INTEGER, RONLY, ospfLsdbEntry,
317 3, {4, 1, 6}},
318 {OSPFLSDBCHECKSUM, INTEGER, RONLY, ospfLsdbEntry,
319 3, {4, 1, 7}},
320 {OSPFLSDBADVERTISEMENT, STRING, RONLY, ospfLsdbEntry,
321 3, {4, 1, 8}},
323 /* Area range table. */
324 {OSPFAREARANGEAREAID, IPADDRESS, RONLY, ospfAreaRangeEntry,
325 3, {5, 1, 1}},
326 {OSPFAREARANGENET, IPADDRESS, RONLY, ospfAreaRangeEntry,
327 3, {5, 1, 2}},
328 {OSPFAREARANGEMASK, IPADDRESS, RWRITE, ospfAreaRangeEntry,
329 3, {5, 1, 3}},
330 {OSPFAREARANGESTATUS, INTEGER, RWRITE, ospfAreaRangeEntry,
331 3, {5, 1, 4}},
332 {OSPFAREARANGEEFFECT, INTEGER, RWRITE, ospfAreaRangeEntry,
333 3, {5, 1, 5}},
335 /* OSPF host table. */
336 {OSPFHOSTIPADDRESS, IPADDRESS, RONLY, ospfHostEntry,
337 3, {6, 1, 1}},
338 {OSPFHOSTTOS, INTEGER, RONLY, ospfHostEntry,
339 3, {6, 1, 2}},
340 {OSPFHOSTMETRIC, INTEGER, RWRITE, ospfHostEntry,
341 3, {6, 1, 3}},
342 {OSPFHOSTSTATUS, INTEGER, RWRITE, ospfHostEntry,
343 3, {6, 1, 4}},
344 {OSPFHOSTAREAID, IPADDRESS, RONLY, ospfHostEntry,
345 3, {6, 1, 5}},
347 /* OSPF interface table. */
348 {OSPFIFIPADDRESS, IPADDRESS, RONLY, ospfIfEntry,
349 3, {7, 1, 1}},
350 {OSPFADDRESSLESSIF, INTEGER, RONLY, ospfIfEntry,
351 3, {7, 1, 2}},
352 {OSPFIFAREAID, IPADDRESS, RWRITE, ospfIfEntry,
353 3, {7, 1, 3}},
354 {OSPFIFTYPE, INTEGER, RWRITE, ospfIfEntry,
355 3, {7, 1, 4}},
356 {OSPFIFADMINSTAT, INTEGER, RWRITE, ospfIfEntry,
357 3, {7, 1, 5}},
358 {OSPFIFRTRPRIORITY, INTEGER, RWRITE, ospfIfEntry,
359 3, {7, 1, 6}},
360 {OSPFIFTRANSITDELAY, INTEGER, RWRITE, ospfIfEntry,
361 3, {7, 1, 7}},
362 {OSPFIFRETRANSINTERVAL, INTEGER, RWRITE, ospfIfEntry,
363 3, {7, 1, 8}},
364 {OSPFIFHELLOINTERVAL, INTEGER, RWRITE, ospfIfEntry,
365 3, {7, 1, 9}},
366 {OSPFIFRTRDEADINTERVAL, INTEGER, RWRITE, ospfIfEntry,
367 3, {7, 1, 10}},
368 {OSPFIFPOLLINTERVAL, INTEGER, RWRITE, ospfIfEntry,
369 3, {7, 1, 11}},
370 {OSPFIFSTATE, INTEGER, RONLY, ospfIfEntry,
371 3, {7, 1, 12}},
372 {OSPFIFDESIGNATEDROUTER, IPADDRESS, RONLY, ospfIfEntry,
373 3, {7, 1, 13}},
374 {OSPFIFBACKUPDESIGNATEDROUTER, IPADDRESS, RONLY, ospfIfEntry,
375 3, {7, 1, 14}},
376 {OSPFIFEVENTS, COUNTER, RONLY, ospfIfEntry,
377 3, {7, 1, 15}},
378 {OSPFIFAUTHKEY, STRING, RWRITE, ospfIfEntry,
379 3, {7, 1, 16}},
380 {OSPFIFSTATUS, INTEGER, RWRITE, ospfIfEntry,
381 3, {7, 1, 17}},
382 {OSPFIFMULTICASTFORWARDING, INTEGER, RWRITE, ospfIfEntry,
383 3, {7, 1, 18}},
384 {OSPFIFDEMAND, INTEGER, RWRITE, ospfIfEntry,
385 3, {7, 1, 19}},
386 {OSPFIFAUTHTYPE, INTEGER, RWRITE, ospfIfEntry,
387 3, {7, 1, 20}},
389 /* OSPF interface metric table. */
390 {OSPFIFMETRICIPADDRESS, IPADDRESS, RONLY, ospfIfMetricEntry,
391 3, {8, 1, 1}},
392 {OSPFIFMETRICADDRESSLESSIF, INTEGER, RONLY, ospfIfMetricEntry,
393 3, {8, 1, 2}},
394 {OSPFIFMETRICTOS, INTEGER, RONLY, ospfIfMetricEntry,
395 3, {8, 1, 3}},
396 {OSPFIFMETRICVALUE, INTEGER, RWRITE, ospfIfMetricEntry,
397 3, {8, 1, 4}},
398 {OSPFIFMETRICSTATUS, INTEGER, RWRITE, ospfIfMetricEntry,
399 3, {8, 1, 5}},
401 /* OSPF virtual interface table. */
402 {OSPFVIRTIFAREAID, IPADDRESS, RONLY, ospfVirtIfEntry,
403 3, {9, 1, 1}},
404 {OSPFVIRTIFNEIGHBOR, IPADDRESS, RONLY, ospfVirtIfEntry,
405 3, {9, 1, 2}},
406 {OSPFVIRTIFTRANSITDELAY, INTEGER, RWRITE, ospfVirtIfEntry,
407 3, {9, 1, 3}},
408 {OSPFVIRTIFRETRANSINTERVAL, INTEGER, RWRITE, ospfVirtIfEntry,
409 3, {9, 1, 4}},
410 {OSPFVIRTIFHELLOINTERVAL, INTEGER, RWRITE, ospfVirtIfEntry,
411 3, {9, 1, 5}},
412 {OSPFVIRTIFRTRDEADINTERVAL, INTEGER, RWRITE, ospfVirtIfEntry,
413 3, {9, 1, 6}},
414 {OSPFVIRTIFSTATE, INTEGER, RONLY, ospfVirtIfEntry,
415 3, {9, 1, 7}},
416 {OSPFVIRTIFEVENTS, COUNTER, RONLY, ospfVirtIfEntry,
417 3, {9, 1, 8}},
418 {OSPFVIRTIFAUTHKEY, STRING, RWRITE, ospfVirtIfEntry,
419 3, {9, 1, 9}},
420 {OSPFVIRTIFSTATUS, INTEGER, RWRITE, ospfVirtIfEntry,
421 3, {9, 1, 10}},
422 {OSPFVIRTIFAUTHTYPE, INTEGER, RWRITE, ospfVirtIfEntry,
423 3, {9, 1, 11}},
425 /* OSPF neighbor table. */
426 {OSPFNBRIPADDR, IPADDRESS, RONLY, ospfNbrEntry,
427 3, {10, 1, 1}},
428 {OSPFNBRADDRESSLESSINDEX, INTEGER, RONLY, ospfNbrEntry,
429 3, {10, 1, 2}},
430 {OSPFNBRRTRID, IPADDRESS, RONLY, ospfNbrEntry,
431 3, {10, 1, 3}},
432 {OSPFNBROPTIONS, INTEGER, RONLY, ospfNbrEntry,
433 3, {10, 1, 4}},
434 {OSPFNBRPRIORITY, INTEGER, RWRITE, ospfNbrEntry,
435 3, {10, 1, 5}},
436 {OSPFNBRSTATE, INTEGER, RONLY, ospfNbrEntry,
437 3, {10, 1, 6}},
438 {OSPFNBREVENTS, COUNTER, RONLY, ospfNbrEntry,
439 3, {10, 1, 7}},
440 {OSPFNBRLSRETRANSQLEN, GAUGE, RONLY, ospfNbrEntry,
441 3, {10, 1, 8}},
442 {OSPFNBMANBRSTATUS, INTEGER, RWRITE, ospfNbrEntry,
443 3, {10, 1, 9}},
444 {OSPFNBMANBRPERMANENCE, INTEGER, RONLY, ospfNbrEntry,
445 3, {10, 1, 10}},
446 {OSPFNBRHELLOSUPPRESSED, INTEGER, RONLY, ospfNbrEntry,
447 3, {10, 1, 11}},
449 /* OSPF virtual neighbor table. */
450 {OSPFVIRTNBRAREA, IPADDRESS, RONLY, ospfVirtNbrEntry,
451 3, {11, 1, 1}},
452 {OSPFVIRTNBRRTRID, IPADDRESS, RONLY, ospfVirtNbrEntry,
453 3, {11, 1, 2}},
454 {OSPFVIRTNBRIPADDR, IPADDRESS, RONLY, ospfVirtNbrEntry,
455 3, {11, 1, 3}},
456 {OSPFVIRTNBROPTIONS, INTEGER, RONLY, ospfVirtNbrEntry,
457 3, {11, 1, 4}},
458 {OSPFVIRTNBRSTATE, INTEGER, RONLY, ospfVirtNbrEntry,
459 3, {11, 1, 5}},
460 {OSPFVIRTNBREVENTS, COUNTER, RONLY, ospfVirtNbrEntry,
461 3, {11, 1, 6}},
462 {OSPFVIRTNBRLSRETRANSQLEN, INTEGER, RONLY, ospfVirtNbrEntry,
463 3, {11, 1, 7}},
464 {OSPFVIRTNBRHELLOSUPPRESSED, INTEGER, RONLY, ospfVirtNbrEntry,
465 3, {11, 1, 8}},
467 /* OSPF link state database, external. */
468 {OSPFEXTLSDBTYPE, INTEGER, RONLY, ospfExtLsdbEntry,
469 3, {12, 1, 1}},
470 {OSPFEXTLSDBLSID, IPADDRESS, RONLY, ospfExtLsdbEntry,
471 3, {12, 1, 2}},
472 {OSPFEXTLSDBROUTERID, IPADDRESS, RONLY, ospfExtLsdbEntry,
473 3, {12, 1, 3}},
474 {OSPFEXTLSDBSEQUENCE, INTEGER, RONLY, ospfExtLsdbEntry,
475 3, {12, 1, 4}},
476 {OSPFEXTLSDBAGE, INTEGER, RONLY, ospfExtLsdbEntry,
477 3, {12, 1, 5}},
478 {OSPFEXTLSDBCHECKSUM, INTEGER, RONLY, ospfExtLsdbEntry,
479 3, {12, 1, 6}},
480 {OSPFEXTLSDBADVERTISEMENT, STRING, RONLY, ospfExtLsdbEntry,
481 3, {12, 1, 7}},
483 /* OSPF area aggregate table. */
484 {OSPFAREAAGGREGATEAREAID, IPADDRESS, RONLY, ospfAreaAggregateEntry,
485 3, {14, 1, 1}},
486 {OSPFAREAAGGREGATELSDBTYPE, INTEGER, RONLY, ospfAreaAggregateEntry,
487 3, {14, 1, 2}},
488 {OSPFAREAAGGREGATENET, IPADDRESS, RONLY, ospfAreaAggregateEntry,
489 3, {14, 1, 3}},
490 {OSPFAREAAGGREGATEMASK, IPADDRESS, RONLY, ospfAreaAggregateEntry,
491 3, {14, 1, 4}},
492 {OSPFAREAAGGREGATESTATUS, INTEGER, RWRITE, ospfAreaAggregateEntry,
493 3, {14, 1, 5}},
494 {OSPFAREAAGGREGATEEFFECT, INTEGER, RWRITE, ospfAreaAggregateEntry,
495 3, {14, 1, 6}}
498 /* The administrative status of OSPF. When OSPF is enbled on at least
499 one interface return 1. */
501 ospf_admin_stat (struct ospf *ospf)
503 listnode node;
504 struct ospf_interface *oi;
506 if (ospf == NULL)
507 return 0;
509 for (node = listhead (ospf->oiflist); node; nextnode (node))
511 oi = getdata (node);
513 if (oi && oi->address)
514 return 1;
516 return 0;
519 static u_char *
520 ospfGeneralGroup (struct variable *v, oid *name, size_t *length,
521 int exact, size_t *var_len, WriteMethod **write_method)
523 struct ospf *ospf;
525 ospf = ospf_lookup ();
527 /* Check whether the instance identifier is valid */
528 if (smux_header_generic (v, name, length, exact, var_len, write_method)
529 == MATCH_FAILED)
530 return NULL;
532 /* Return the current value of the variable */
533 switch (v->magic)
535 case OSPFROUTERID: /* 1 */
536 /* Router-ID of this OSPF instance. */
537 if (ospf)
538 return SNMP_IPADDRESS (ospf->router_id);
539 else
540 return SNMP_IPADDRESS (ospf_empty_addr);
541 break;
542 case OSPFADMINSTAT: /* 2 */
543 /* The administrative status of OSPF in the router. */
544 if (ospf_admin_stat (ospf))
545 return SNMP_INTEGER (OSPF_STATUS_ENABLED);
546 else
547 return SNMP_INTEGER (OSPF_STATUS_DISABLED);
548 break;
549 case OSPFVERSIONNUMBER: /* 3 */
550 /* OSPF version 2. */
551 return SNMP_INTEGER (OSPF_VERSION);
552 break;
553 case OSPFAREABDRRTRSTATUS: /* 4 */
554 /* Area Border router status. */
555 if (ospf && CHECK_FLAG (ospf->flags, OSPF_FLAG_ABR))
556 return SNMP_INTEGER (SNMP_TRUE);
557 else
558 return SNMP_INTEGER (SNMP_FALSE);
559 break;
560 case OSPFASBDRRTRSTATUS: /* 5 */
561 /* AS Border router status. */
562 if (ospf && CHECK_FLAG (ospf->flags, OSPF_FLAG_ASBR))
563 return SNMP_INTEGER (SNMP_TRUE);
564 else
565 return SNMP_INTEGER (SNMP_FALSE);
566 break;
567 case OSPFEXTERNLSACOUNT: /* 6 */
568 /* External LSA counts. */
569 if (ospf)
570 return SNMP_INTEGER (ospf_lsdb_count_all (ospf->lsdb));
571 else
572 return SNMP_INTEGER (0);
573 break;
574 case OSPFEXTERNLSACKSUMSUM: /* 7 */
575 /* External LSA checksum. */
576 return SNMP_INTEGER (0);
577 break;
578 case OSPFTOSSUPPORT: /* 8 */
579 /* TOS is not supported. */
580 return SNMP_INTEGER (SNMP_FALSE);
581 break;
582 case OSPFORIGINATENEWLSAS: /* 9 */
583 /* The number of new link-state advertisements. */
584 if (ospf)
585 return SNMP_INTEGER (ospf->lsa_originate_count);
586 else
587 return SNMP_INTEGER (0);
588 break;
589 case OSPFRXNEWLSAS: /* 10 */
590 /* The number of link-state advertisements received determined
591 to be new instantiations. */
592 if (ospf)
593 return SNMP_INTEGER (ospf->rx_lsa_count);
594 else
595 return SNMP_INTEGER (0);
596 break;
597 case OSPFEXTLSDBLIMIT: /* 11 */
598 /* There is no limit for the number of non-default
599 AS-external-LSAs. */
600 return SNMP_INTEGER (-1);
601 break;
602 case OSPFMULTICASTEXTENSIONS: /* 12 */
603 /* Multicast Extensions to OSPF is not supported. */
604 return SNMP_INTEGER (0);
605 break;
606 case OSPFEXITOVERFLOWINTERVAL: /* 13 */
607 /* Overflow is not supported. */
608 return SNMP_INTEGER (0);
609 break;
610 case OSPFDEMANDEXTENSIONS: /* 14 */
611 /* Demand routing is not supported. */
612 return SNMP_INTEGER (SNMP_FALSE);
613 break;
614 default:
615 return NULL;
617 return NULL;
620 struct ospf_area *
621 ospf_area_lookup_next (struct ospf *ospf, struct in_addr *area_id, int first)
623 struct ospf_area *area;
624 listnode node;
626 if (ospf == NULL)
627 return NULL;
629 if (first)
631 node = listhead (ospf->areas);
632 if (node)
634 area = getdata (node);
635 *area_id = area->area_id;
636 return area;
638 return NULL;
640 for (node = listhead (ospf->areas); node; nextnode (node))
642 area = getdata (node);
644 if (ntohl (area->area_id.s_addr) > ntohl (area_id->s_addr))
646 *area_id = area->area_id;
647 return area;
650 return NULL;
653 struct ospf_area *
654 ospfAreaLookup (struct variable *v, oid name[], size_t *length,
655 struct in_addr *addr, int exact)
657 struct ospf *ospf;
658 struct ospf_area *area;
659 int len;
661 ospf = ospf_lookup ();
662 if (ospf == NULL)
663 return NULL;
665 if (exact)
667 /* Length is insufficient to lookup OSPF area. */
668 if (*length - v->namelen != sizeof (struct in_addr))
669 return NULL;
671 oid2in_addr (name + v->namelen, sizeof (struct in_addr), addr);
673 area = ospf_area_lookup_by_area_id (ospf, *addr);
675 return area;
677 else
679 len = *length - v->namelen;
680 if (len > 4)
681 len = 4;
683 oid2in_addr (name + v->namelen, len, addr);
685 area = ospf_area_lookup_next (ospf, addr, len == 0 ? 1 : 0);
687 if (area == NULL)
688 return NULL;
690 oid_copy_addr (name + v->namelen, addr, sizeof (struct in_addr));
691 *length = sizeof (struct in_addr) + v->namelen;
693 return area;
695 return NULL;
698 static u_char *
699 ospfAreaEntry (struct variable *v, oid *name, size_t *length, int exact,
700 size_t *var_len, WriteMethod **write_method)
702 struct ospf_area *area;
703 struct in_addr addr;
705 memset (&addr, 0, sizeof (struct in_addr));
707 area = ospfAreaLookup (v, name, length, &addr, exact);
708 if (! area)
709 return NULL;
711 /* Return the current value of the variable */
712 switch (v->magic)
714 case OSPFAREAID: /* 1 */
715 return SNMP_IPADDRESS (area->area_id);
716 break;
717 case OSPFAUTHTYPE: /* 2 */
718 return SNMP_INTEGER (area->auth_type);
719 break;
720 case OSPFIMPORTASEXTERN: /* 3 */
721 return SNMP_INTEGER (area->external_routing + 1);
722 break;
723 case OSPFSPFRUNS: /* 4 */
724 return SNMP_INTEGER (area->spf_calculation);
725 break;
726 case OSPFAREABDRRTRCOUNT: /* 5 */
727 return SNMP_INTEGER (area->abr_count);
728 break;
729 case OSPFASBDRRTRCOUNT: /* 6 */
730 return SNMP_INTEGER (area->asbr_count);
731 break;
732 case OSPFAREALSACOUNT: /* 7 */
733 return SNMP_INTEGER (area->lsdb->total);
734 break;
735 case OSPFAREALSACKSUMSUM: /* 8 */
736 return SNMP_INTEGER (0);
737 break;
738 case OSPFAREASUMMARY: /* 9 */
739 #define OSPF_noAreaSummary 1
740 #define OSPF_sendAreaSummary 2
741 if (area->no_summary)
742 return SNMP_INTEGER (OSPF_noAreaSummary);
743 else
744 return SNMP_INTEGER (OSPF_sendAreaSummary);
745 break;
746 case OSPFAREASTATUS: /* 10 */
747 return SNMP_INTEGER (SNMP_VALID);
748 break;
749 default:
750 return NULL;
751 break;
753 return NULL;
756 struct ospf_area *
757 ospf_stub_area_lookup_next (struct in_addr *area_id, int first)
759 struct ospf_area *area;
760 listnode node;
761 struct ospf *ospf;
763 ospf = ospf_lookup ();
764 if (ospf == NULL)
765 return NULL;
767 for (node = listhead (ospf->areas); node; nextnode (node))
769 area = getdata (node);
771 if (area->external_routing == OSPF_AREA_STUB)
773 if (first)
775 *area_id = area->area_id;
776 return area;
778 else if (ntohl (area->area_id.s_addr) > ntohl (area_id->s_addr))
780 *area_id = area->area_id;
781 return area;
785 return NULL;
788 struct ospf_area *
789 ospfStubAreaLookup (struct variable *v, oid name[], size_t *length,
790 struct in_addr *addr, int exact)
792 struct ospf *ospf;
793 struct ospf_area *area;
794 int len;
796 ospf = ospf_lookup ();
797 if (ospf == NULL)
798 return NULL;
800 /* Exact lookup. */
801 if (exact)
803 /* ospfStubAreaID + ospfStubTOS. */
804 if (*length != v->namelen + sizeof (struct in_addr) + 1)
805 return NULL;
807 /* Check ospfStubTOS is zero. */
808 if (name[*length - 1] != 0)
809 return NULL;
811 oid2in_addr (name + v->namelen, sizeof (struct in_addr), addr);
813 area = ospf_area_lookup_by_area_id (ospf, *addr);
815 if (area->external_routing == OSPF_AREA_STUB)
816 return area;
817 else
818 return NULL;
820 else
822 len = *length - v->namelen;
823 if (len > 4)
824 len = 4;
826 oid2in_addr (name + v->namelen, len, addr);
828 area = ospf_stub_area_lookup_next (addr, len == 0 ? 1 : 0);
830 if (area == NULL)
831 return NULL;
833 oid_copy_addr (name + v->namelen, addr, sizeof (struct in_addr));
834 /* Set TOS 0. */
835 name[v->namelen + sizeof (struct in_addr)] = 0;
836 *length = v->namelen + sizeof (struct in_addr) + 1;
838 return area;
840 return NULL;
843 static u_char *
844 ospfStubAreaEntry (struct variable *v, oid *name, size_t *length,
845 int exact, size_t *var_len, WriteMethod **write_method)
847 struct ospf_area *area;
848 struct in_addr addr;
850 memset (&addr, 0, sizeof (struct in_addr));
852 area = ospfStubAreaLookup (v, name, length, &addr, exact);
853 if (! area)
854 return NULL;
856 /* Return the current value of the variable */
857 switch (v->magic)
859 case OSPFSTUBAREAID: /* 1 */
860 /* OSPF stub area id. */
861 return SNMP_IPADDRESS (area->area_id);
862 break;
863 case OSPFSTUBTOS: /* 2 */
864 /* TOS value is not supported. */
865 return SNMP_INTEGER (0);
866 break;
867 case OSPFSTUBMETRIC: /* 3 */
868 /* Default cost to stub area. */
869 return SNMP_INTEGER (area->default_cost);
870 break;
871 case OSPFSTUBSTATUS: /* 4 */
872 /* Status of the stub area. */
873 return SNMP_INTEGER (SNMP_VALID);
874 break;
875 case OSPFSTUBMETRICTYPE: /* 5 */
876 /* OSPF Metric type. */
877 #define OSPF_ospfMetric 1
878 #define OSPF_comparableCost 2
879 #define OSPF_nonComparable 3
880 return SNMP_INTEGER (OSPF_ospfMetric);
881 break;
882 default:
883 return NULL;
884 break;
886 return NULL;
889 struct ospf_lsa *
890 lsdb_lookup_next (struct ospf_area *area, u_char *type, int type_next,
891 struct in_addr *ls_id, int ls_id_next,
892 struct in_addr *router_id, int router_id_next)
894 struct ospf_lsa *lsa;
895 int i;
897 if (type_next)
898 i = OSPF_MIN_LSA;
899 else
900 i = *type;
902 for (; i < OSPF_MAX_LSA; i++)
904 *type = i;
906 lsa = ospf_lsdb_lookup_by_id_next (area->lsdb, *type, *ls_id, *router_id,
907 ls_id_next);
908 if (lsa)
909 return lsa;
911 ls_id_next = 1;
913 return NULL;
916 struct ospf_lsa *
917 ospfLsdbLookup (struct variable *v, oid *name, size_t *length,
918 struct in_addr *area_id, u_char *type,
919 struct in_addr *ls_id, struct in_addr *router_id, int exact)
921 struct ospf *ospf;
922 struct ospf_area *area;
923 struct ospf_lsa *lsa;
924 int len;
925 int type_next;
926 int ls_id_next;
927 int router_id_next;
928 oid *offset;
929 int offsetlen;
931 ospf = ospf_lookup ();
933 #define OSPF_LSDB_ENTRY_OFFSET \
934 (IN_ADDR_SIZE + 1 + IN_ADDR_SIZE + IN_ADDR_SIZE)
936 if (exact)
938 /* Area ID + Type + LS ID + Router ID. */
939 if (*length - v->namelen != OSPF_LSDB_ENTRY_OFFSET)
940 return NULL;
942 /* Set OID offset for Area ID. */
943 offset = name + v->namelen;
945 /* Lookup area first. */
946 oid2in_addr (offset, IN_ADDR_SIZE, area_id);
947 area = ospf_area_lookup_by_area_id (ospf, *area_id);
948 if (! area)
949 return NULL;
950 offset += IN_ADDR_SIZE;
952 /* Type. */
953 *type = *offset;
954 offset++;
956 /* LS ID. */
957 oid2in_addr (offset, IN_ADDR_SIZE, ls_id);
958 offset += IN_ADDR_SIZE;
960 /* Router ID. */
961 oid2in_addr (offset, IN_ADDR_SIZE, router_id);
963 /* Lookup LSDB. */
964 return ospf_lsdb_lookup_by_id (area->lsdb, *type, *ls_id, *router_id);
966 else
968 /* Get variable length. */
969 offset = name + v->namelen;
970 offsetlen = *length - v->namelen;
971 len = offsetlen;
973 if (len > IN_ADDR_SIZE)
974 len = IN_ADDR_SIZE;
976 oid2in_addr (offset, len, area_id);
978 /* First we search area. */
979 if (len == IN_ADDR_SIZE)
980 area = ospf_area_lookup_by_area_id (ospf, *area_id);
981 else
982 area = ospf_area_lookup_next (ospf, area_id, len == 0 ? 1 : 0);
984 if (area == NULL)
985 return NULL;
989 /* Next we lookup type. */
990 offset += IN_ADDR_SIZE;
991 offsetlen -= IN_ADDR_SIZE;
992 len = offsetlen;
994 if (len <= 0)
995 type_next = 1;
996 else
998 len = 1;
999 type_next = 0;
1000 *type = *offset;
1003 /* LS ID. */
1004 offset++;
1005 offsetlen--;
1006 len = offsetlen;
1008 if (len <= 0)
1009 ls_id_next = 1;
1010 else
1012 ls_id_next = 0;
1013 if (len > IN_ADDR_SIZE)
1014 len = IN_ADDR_SIZE;
1016 oid2in_addr (offset, len, ls_id);
1019 /* Router ID. */
1020 offset += IN_ADDR_SIZE;
1021 offsetlen -= IN_ADDR_SIZE;
1022 len = offsetlen;
1024 if (len <= 0)
1025 router_id_next = 1;
1026 else
1028 router_id_next = 0;
1029 if (len > IN_ADDR_SIZE)
1030 len = IN_ADDR_SIZE;
1032 oid2in_addr (offset, len, router_id);
1035 lsa = lsdb_lookup_next (area, type, type_next, ls_id, ls_id_next,
1036 router_id, router_id_next);
1038 if (lsa)
1040 /* Fill in length. */
1041 *length = v->namelen + OSPF_LSDB_ENTRY_OFFSET;
1043 /* Fill in value. */
1044 offset = name + v->namelen;
1045 oid_copy_addr (offset, area_id, IN_ADDR_SIZE);
1046 offset += IN_ADDR_SIZE;
1047 *offset = lsa->data->type;
1048 offset++;
1049 oid_copy_addr (offset, &lsa->data->id, IN_ADDR_SIZE);
1050 offset += IN_ADDR_SIZE;
1051 oid_copy_addr (offset, &lsa->data->adv_router, IN_ADDR_SIZE);
1053 return lsa;
1056 while ((area = ospf_area_lookup_next (ospf, area_id, 0)) != NULL);
1058 return NULL;
1061 static u_char *
1062 ospfLsdbEntry (struct variable *v, oid *name, size_t *length, int exact,
1063 size_t *var_len, WriteMethod **write_method)
1065 struct ospf_lsa *lsa;
1066 struct lsa_header *lsah;
1067 struct in_addr area_id;
1068 u_char type;
1069 struct in_addr ls_id;
1070 struct in_addr router_id;
1071 struct ospf *ospf;
1073 /* INDEX { ospfLsdbAreaId, ospfLsdbType,
1074 ospfLsdbLsid, ospfLsdbRouterId } */
1076 memset (&area_id, 0, sizeof (struct in_addr));
1077 type = 0;
1078 memset (&ls_id, 0, sizeof (struct in_addr));
1079 memset (&router_id, 0, sizeof (struct in_addr));
1081 /* Check OSPF instance. */
1082 ospf = ospf_lookup ();
1083 if (ospf == NULL)
1084 return NULL;
1086 lsa = ospfLsdbLookup (v, name, length, &area_id, &type, &ls_id, &router_id,
1087 exact);
1088 if (! lsa)
1089 return NULL;
1091 lsah = lsa->data;
1093 /* Return the current value of the variable */
1094 switch (v->magic)
1096 case OSPFLSDBAREAID: /* 1 */
1097 return SNMP_IPADDRESS (lsa->area->area_id);
1098 break;
1099 case OSPFLSDBTYPE: /* 2 */
1100 return SNMP_INTEGER (lsah->type);
1101 break;
1102 case OSPFLSDBLSID: /* 3 */
1103 return SNMP_IPADDRESS (lsah->id);
1104 break;
1105 case OSPFLSDBROUTERID: /* 4 */
1106 return SNMP_IPADDRESS (lsah->adv_router);
1107 break;
1108 case OSPFLSDBSEQUENCE: /* 5 */
1109 return SNMP_INTEGER (lsah->ls_seqnum);
1110 break;
1111 case OSPFLSDBAGE: /* 6 */
1112 return SNMP_INTEGER (lsah->ls_age);
1113 break;
1114 case OSPFLSDBCHECKSUM: /* 7 */
1115 return SNMP_INTEGER (lsah->checksum);
1116 break;
1117 case OSPFLSDBADVERTISEMENT: /* 8 */
1118 *var_len = ntohs (lsah->length);
1119 return (u_char *) lsah;
1120 break;
1121 default:
1122 return NULL;
1123 break;
1125 return NULL;
1128 struct ospf_area_range *
1129 ospfAreaRangeLookup (struct variable *v, oid *name, size_t *length,
1130 struct in_addr *area_id, struct in_addr *range_net,
1131 int exact)
1133 oid *offset;
1134 int offsetlen;
1135 int len;
1136 struct ospf *ospf;
1137 struct ospf_area *area;
1138 struct ospf_area_range *range;
1139 struct prefix_ipv4 p;
1140 p.family = AF_INET;
1141 p.prefixlen = IPV4_MAX_BITLEN;
1143 ospf = ospf_lookup ();
1145 if (exact)
1147 /* Area ID + Range Network. */
1148 if (v->namelen + IN_ADDR_SIZE + IN_ADDR_SIZE != *length)
1149 return NULL;
1151 /* Set OID offset for Area ID. */
1152 offset = name + v->namelen;
1154 /* Lookup area first. */
1155 oid2in_addr (offset, IN_ADDR_SIZE, area_id);
1157 area = ospf_area_lookup_by_area_id (ospf, *area_id);
1158 if (! area)
1159 return NULL;
1161 offset += IN_ADDR_SIZE;
1163 /* Lookup area range. */
1164 oid2in_addr (offset, IN_ADDR_SIZE, range_net);
1165 p.prefix = *range_net;
1167 return ospf_area_range_lookup (area, &p);
1169 else
1171 /* Set OID offset for Area ID. */
1172 offset = name + v->namelen;
1173 offsetlen = *length - v->namelen;
1175 len = offsetlen;
1176 if (len > IN_ADDR_SIZE)
1177 len = IN_ADDR_SIZE;
1179 oid2in_addr (offset, len, area_id);
1181 /* First we search area. */
1182 if (len == IN_ADDR_SIZE)
1183 area = ospf_area_lookup_by_area_id (ospf,*area_id);
1184 else
1185 area = ospf_area_lookup_next (ospf, area_id, len == 0 ? 1 : 0);
1187 if (area == NULL)
1188 return NULL;
1192 offset += IN_ADDR_SIZE;
1193 offsetlen -= IN_ADDR_SIZE;
1194 len = offsetlen;
1196 if (len < 0)
1197 len = 0;
1198 if (len > IN_ADDR_SIZE)
1199 len = IN_ADDR_SIZE;
1201 oid2in_addr (offset, len, range_net);
1203 range = ospf_area_range_lookup_next (area, range_net,
1204 len == 0 ? 1 : 0);
1206 if (range)
1208 /* Fill in length. */
1209 *length = v->namelen + IN_ADDR_SIZE + IN_ADDR_SIZE;
1211 /* Fill in value. */
1212 offset = name + v->namelen;
1213 oid_copy_addr (offset, area_id, IN_ADDR_SIZE);
1214 offset += IN_ADDR_SIZE;
1215 oid_copy_addr (offset, range_net, IN_ADDR_SIZE);
1217 return range;
1220 while ((area = ospf_area_lookup_next (ospf, area_id, 0)) != NULL);
1222 return NULL;
1225 static u_char *
1226 ospfAreaRangeEntry (struct variable *v, oid *name, size_t *length, int exact,
1227 size_t *var_len, WriteMethod **write_method)
1229 struct ospf_area_range *range;
1230 struct in_addr area_id;
1231 struct in_addr range_net;
1232 struct in_addr mask;
1233 struct ospf *ospf;
1235 /* Check OSPF instance. */
1236 ospf = ospf_lookup ();
1237 if (ospf == NULL)
1238 return NULL;
1240 memset (&area_id, 0, IN_ADDR_SIZE);
1241 memset (&range_net, 0, IN_ADDR_SIZE);
1243 range = ospfAreaRangeLookup (v, name, length, &area_id, &range_net, exact);
1244 if (! range)
1245 return NULL;
1247 /* Convert prefixlen to network mask format. */
1248 masklen2ip (range->subst_masklen, &mask);
1250 /* Return the current value of the variable */
1251 switch (v->magic)
1253 case OSPFAREARANGEAREAID: /* 1 */
1254 return SNMP_IPADDRESS (area_id);
1255 break;
1256 case OSPFAREARANGENET: /* 2 */
1257 return SNMP_IPADDRESS (range_net);
1258 break;
1259 case OSPFAREARANGEMASK: /* 3 */
1260 return SNMP_IPADDRESS (mask);
1261 break;
1262 case OSPFAREARANGESTATUS: /* 4 */
1263 return SNMP_INTEGER (SNMP_VALID);
1264 break;
1265 case OSPFAREARANGEEFFECT: /* 5 */
1266 #define OSPF_advertiseMatching 1
1267 #define OSPF_doNotAdvertiseMatching 2
1268 return SNMP_INTEGER (OSPF_advertiseMatching);
1269 break;
1270 default:
1271 return NULL;
1272 break;
1274 return NULL;
1277 struct ospf_nbr_nbma *
1278 ospf_nbr_nbma_lookup_next (struct ospf *ospf, struct in_addr *nbr_addr,
1279 int first)
1281 struct route_node *rn;
1282 struct ospf_nbr_nbma *nbr_nbma;
1283 struct ospf_nbr_nbma *min = NULL;
1285 for (rn = route_top (ospf->nbr_nbma); rn; rn = route_next (rn))
1286 if ((nbr_nbma = rn->info) != NULL
1287 && nbr_nbma->nbr != nbr_nbma->oi->nbr_self /* just make sure */
1288 && nbr_nbma->nbr->state != NSM_Down /* xxx */
1289 && nbr_nbma->addr.s_addr != 0)
1291 if (first)
1293 if (! min)
1294 min = nbr_nbma;
1295 else if (ntohl (nbr_nbma->addr.s_addr) < ntohl (min->addr.s_addr))
1296 min = nbr_nbma;
1298 else if (ntohl (nbr_nbma->addr.s_addr) > ntohl (nbr_addr->s_addr))
1300 if (! min)
1301 min = nbr_nbma;
1302 else if (ntohl (nbr_nbma->addr.s_addr) < ntohl (min->addr.s_addr))
1303 min = nbr_nbma;
1307 if (min)
1309 *nbr_addr = min->addr;
1310 return min;
1313 return NULL;
1316 struct ospf_nbr_nbma *
1317 ospfHostLookup (struct variable *v, oid *name, size_t *length,
1318 struct in_addr *addr, int exact)
1320 int len;
1321 struct ospf_nbr_nbma *nbr_nbma;
1322 struct ospf *ospf;
1324 ospf = ospf_lookup ();
1325 if (ospf == NULL)
1326 return NULL;
1328 if (exact)
1330 /* INDEX { ospfHostIpAddress, ospfHostTOS } */
1331 if (*length != v->namelen + IN_ADDR_SIZE + 1)
1332 return NULL;
1334 /* Check ospfHostTOS. */
1335 if (name[*length - 1] != 0)
1336 return NULL;
1338 oid2in_addr (name + v->namelen, IN_ADDR_SIZE, addr);
1340 nbr_nbma = ospf_nbr_nbma_lookup (ospf, *addr);
1342 return nbr_nbma;
1344 else
1346 len = *length - v->namelen;
1347 if (len > 4)
1348 len = 4;
1350 oid2in_addr (name + v->namelen, len, addr);
1352 nbr_nbma = ospf_nbr_nbma_lookup_next (ospf, addr, len == 0 ? 1 : 0);
1354 if (nbr_nbma == NULL)
1355 return NULL;
1357 oid_copy_addr (name + v->namelen, addr, IN_ADDR_SIZE);
1359 /* Set TOS 0. */
1360 name[v->namelen + IN_ADDR_SIZE] = 0;
1362 *length = v->namelen + IN_ADDR_SIZE + 1;
1364 return nbr_nbma;
1366 return NULL;
1369 static u_char *
1370 ospfHostEntry (struct variable *v, oid *name, size_t *length, int exact,
1371 size_t *var_len, WriteMethod **write_method)
1373 struct ospf_nbr_nbma *nbr_nbma;
1374 struct ospf_interface *oi;
1375 struct in_addr addr;
1376 struct ospf *ospf;
1378 /* Check OSPF instance. */
1379 ospf = ospf_lookup ();
1380 if (ospf == NULL)
1381 return NULL;
1383 memset (&addr, 0, sizeof (struct in_addr));
1385 nbr_nbma = ospfHostLookup (v, name, length, &addr, exact);
1386 if (nbr_nbma == NULL)
1387 return NULL;
1389 oi = nbr_nbma->oi;
1391 /* Return the current value of the variable */
1392 switch (v->magic)
1394 case OSPFHOSTIPADDRESS: /* 1 */
1395 return SNMP_IPADDRESS (nbr_nbma->addr);
1396 break;
1397 case OSPFHOSTTOS: /* 2 */
1398 return SNMP_INTEGER (0);
1399 break;
1400 case OSPFHOSTMETRIC: /* 3 */
1401 if (oi)
1402 return SNMP_INTEGER (oi->output_cost);
1403 else
1404 return SNMP_INTEGER (1);
1405 break;
1406 case OSPFHOSTSTATUS: /* 4 */
1407 return SNMP_INTEGER (SNMP_VALID);
1408 break;
1409 case OSPFHOSTAREAID: /* 5 */
1410 if (oi && oi->area)
1411 return SNMP_IPADDRESS (oi->area->area_id);
1412 else
1413 return SNMP_IPADDRESS (ospf_empty_addr);
1414 break;
1415 default:
1416 return NULL;
1417 break;
1419 return NULL;
1422 struct list *ospf_snmp_iflist;
1424 struct ospf_snmp_if
1426 struct in_addr addr;
1427 unsigned int ifindex;
1428 struct interface *ifp;
1431 struct ospf_snmp_if *
1432 ospf_snmp_if_new ()
1434 struct ospf_snmp_if *osif;
1436 osif = XMALLOC (0, sizeof (struct ospf_snmp_if));
1437 memset (osif, 0, sizeof (struct ospf_snmp_if));
1438 return osif;
1441 void
1442 ospf_snmp_if_free (struct ospf_snmp_if *osif)
1444 XFREE (0, osif);
1447 void
1448 ospf_snmp_if_delete (struct interface *ifp)
1450 struct listnode *nn;
1451 struct ospf_snmp_if *osif;
1453 LIST_LOOP (ospf_snmp_iflist, osif, nn)
1455 if (osif->ifp == ifp)
1457 list_delete_node (ospf_snmp_iflist, nn);
1458 ospf_snmp_if_free (osif);
1459 return;
1464 void
1465 ospf_snmp_if_update (struct interface *ifp)
1467 struct listnode *nn;
1468 struct listnode *pn;
1469 struct connected *ifc;
1470 struct prefix *p;
1471 struct ospf_snmp_if *osif;
1472 struct in_addr *addr;
1473 unsigned int ifindex;
1475 ospf_snmp_if_delete (ifp);
1477 p = NULL;
1478 addr = NULL;
1479 ifindex = 0;
1481 /* Lookup first IPv4 address entry. */
1482 LIST_LOOP (ifp->connected, ifc, nn)
1484 if (if_is_pointopoint (ifp))
1485 p = ifc->destination;
1486 else
1487 p = ifc->address;
1489 if (p->family == AF_INET)
1491 addr = &p->u.prefix4;
1492 break;
1495 if (! addr)
1496 ifindex = ifp->ifindex;
1498 /* Add interface to the list. */
1499 pn = NULL;
1500 LIST_LOOP (ospf_snmp_iflist, osif, nn)
1502 if (addr)
1504 if (ntohl (osif->addr.s_addr) > ntohl (addr->s_addr))
1505 break;
1507 else
1509 /* Unnumbered interface. */
1510 if (osif->addr.s_addr != 0 || osif->ifindex > ifindex)
1511 break;
1513 pn = nn;
1516 osif = ospf_snmp_if_new ();
1517 if (addr)
1518 osif->addr = *addr;
1519 else
1520 osif->ifindex = ifindex;
1521 osif->ifp = ifp;
1523 listnode_add_after (ospf_snmp_iflist, pn, osif);
1526 struct interface *
1527 ospf_snmp_if_lookup (struct in_addr *ifaddr, unsigned int *ifindex)
1529 struct listnode *nn;
1530 struct ospf_snmp_if *osif;
1532 LIST_LOOP (ospf_snmp_iflist, osif, nn)
1534 if (ifaddr->s_addr)
1536 if (IPV4_ADDR_SAME (&osif->addr, ifaddr))
1537 return osif->ifp;
1539 else
1541 if (osif->ifindex == *ifindex)
1542 return osif->ifp;
1545 return NULL;
1548 struct interface *
1549 ospf_snmp_if_lookup_next (struct in_addr *ifaddr, unsigned int *ifindex,
1550 int ifaddr_next, int ifindex_next)
1552 struct ospf_snmp_if *osif;
1553 struct listnode *nn;
1555 if (ifaddr_next)
1557 nn = listhead (ospf_snmp_iflist);
1558 if (nn)
1560 osif = getdata (nn);
1561 *ifaddr = osif->addr;
1562 *ifindex = osif->ifindex;
1563 return osif->ifp;
1565 return NULL;
1568 LIST_LOOP (ospf_snmp_iflist, osif, nn)
1570 if (ifaddr->s_addr)
1572 if (ntohl (osif->addr.s_addr) > ntohl (ifaddr->s_addr))
1574 *ifaddr = osif->addr;
1575 *ifindex = osif->ifindex;
1576 return osif->ifp;
1579 else
1581 if (osif->ifindex > *ifindex || osif->addr.s_addr)
1583 *ifaddr = osif->addr;
1584 *ifindex = osif->ifindex;
1585 return osif->ifp;
1589 return NULL;
1593 ospf_snmp_iftype (struct interface *ifp)
1595 #define ospf_snmp_iftype_broadcast 1
1596 #define ospf_snmp_iftype_nbma 2
1597 #define ospf_snmp_iftype_pointToPoint 3
1598 #define ospf_snmp_iftype_pointToMultipoint 5
1599 if (if_is_broadcast (ifp))
1600 return ospf_snmp_iftype_broadcast;
1601 if (if_is_pointopoint (ifp))
1602 return ospf_snmp_iftype_pointToPoint;
1603 return ospf_snmp_iftype_broadcast;
1606 struct interface *
1607 ospfIfLookup (struct variable *v, oid *name, size_t *length,
1608 struct in_addr *ifaddr, unsigned int *ifindex, int exact)
1610 int len;
1611 int ifaddr_next = 0;
1612 int ifindex_next = 0;
1613 struct interface *ifp;
1614 oid *offset;
1616 if (exact)
1618 if (*length != v->namelen + IN_ADDR_SIZE + 1)
1619 return NULL;
1621 oid2in_addr (name + v->namelen, IN_ADDR_SIZE, ifaddr);
1622 *ifindex = name[v->namelen + IN_ADDR_SIZE];
1624 return ospf_snmp_if_lookup (ifaddr, ifindex);
1626 else
1628 len = *length - v->namelen;
1629 if (len >= IN_ADDR_SIZE)
1630 len = IN_ADDR_SIZE;
1631 if (len <= 0)
1632 ifaddr_next = 1;
1634 oid2in_addr (name + v->namelen, len, ifaddr);
1636 len = *length - v->namelen - IN_ADDR_SIZE;
1637 if (len >= 1)
1638 len = 1;
1639 else
1640 ifindex_next = 1;
1642 if (len == 1)
1643 *ifindex = name[v->namelen + IN_ADDR_SIZE];
1645 ifp = ospf_snmp_if_lookup_next (ifaddr, ifindex, ifaddr_next,
1646 ifindex_next);
1647 if (ifp)
1649 *length = v->namelen + IN_ADDR_SIZE + 1;
1650 offset = name + v->namelen;
1651 oid_copy_addr (offset, ifaddr, IN_ADDR_SIZE);
1652 offset += IN_ADDR_SIZE;
1653 *offset = *ifindex;
1654 return ifp;
1657 return NULL;
1660 static u_char *
1661 ospfIfEntry (struct variable *v, oid *name, size_t *length, int exact,
1662 size_t *var_len, WriteMethod **write_method)
1664 struct interface *ifp;
1665 unsigned int ifindex;
1666 struct in_addr ifaddr;
1667 struct ospf_interface *oi;
1668 struct ospf *ospf;
1670 ifindex = 0;
1671 memset (&ifaddr, 0, sizeof (struct in_addr));
1673 /* Check OSPF instance. */
1674 ospf = ospf_lookup ();
1675 if (ospf == NULL)
1676 return NULL;
1678 ifp = ospfIfLookup (v, name, length, &ifaddr, &ifindex, exact);
1679 if (ifp == NULL)
1680 return NULL;
1682 oi = ospf_if_lookup_by_local_addr (ospf, ifp, ifaddr);
1683 if (oi == NULL)
1684 return NULL;
1686 /* Return the current value of the variable */
1687 switch (v->magic)
1689 case OSPFIFIPADDRESS: /* 1 */
1690 return SNMP_IPADDRESS (ifaddr);
1691 break;
1692 case OSPFADDRESSLESSIF: /* 2 */
1693 return SNMP_INTEGER (ifindex);
1694 break;
1695 case OSPFIFAREAID: /* 3 */
1696 if (oi->area)
1697 return SNMP_IPADDRESS (oi->area->area_id);
1698 else
1699 return SNMP_IPADDRESS (ospf_empty_addr);
1700 break;
1701 case OSPFIFTYPE: /* 4 */
1702 return SNMP_INTEGER (ospf_snmp_iftype (ifp));
1703 break;
1704 case OSPFIFADMINSTAT: /* 5 */
1705 if (oi)
1706 return SNMP_INTEGER (OSPF_STATUS_ENABLED);
1707 else
1708 return SNMP_INTEGER (OSPF_STATUS_DISABLED);
1709 break;
1710 case OSPFIFRTRPRIORITY: /* 6 */
1711 return SNMP_INTEGER (PRIORITY (oi));
1712 break;
1713 case OSPFIFTRANSITDELAY: /* 7 */
1714 return SNMP_INTEGER (OSPF_IF_PARAM (oi, transmit_delay));
1715 break;
1716 case OSPFIFRETRANSINTERVAL: /* 8 */
1717 return SNMP_INTEGER (OSPF_IF_PARAM (oi, retransmit_interval));
1718 break;
1719 case OSPFIFHELLOINTERVAL: /* 9 */
1720 return SNMP_INTEGER (OSPF_IF_PARAM (oi, v_hello));
1721 break;
1722 case OSPFIFRTRDEADINTERVAL: /* 10 */
1723 return SNMP_INTEGER (OSPF_IF_PARAM (oi, v_wait));
1724 break;
1725 case OSPFIFPOLLINTERVAL: /* 11 */
1726 return SNMP_INTEGER (OSPF_POLL_INTERVAL_DEFAULT);
1727 break;
1728 case OSPFIFSTATE: /* 12 */
1729 return SNMP_INTEGER (oi->state);
1730 break;
1731 case OSPFIFDESIGNATEDROUTER: /* 13 */
1732 return SNMP_IPADDRESS (DR (oi));
1733 break;
1734 case OSPFIFBACKUPDESIGNATEDROUTER: /* 14 */
1735 return SNMP_IPADDRESS (BDR (oi));
1736 break;
1737 case OSPFIFEVENTS: /* 15 */
1738 return SNMP_INTEGER (oi->state_change);
1739 break;
1740 case OSPFIFAUTHKEY: /* 16 */
1741 *var_len = 0;
1742 return (u_char *) OSPF_IF_PARAM (oi, auth_simple);
1743 break;
1744 case OSPFIFSTATUS: /* 17 */
1745 return SNMP_INTEGER (SNMP_VALID);
1746 break;
1747 case OSPFIFMULTICASTFORWARDING: /* 18 */
1748 #define ospf_snmp_multiforward_blocked 1
1749 #define ospf_snmp_multiforward_multicast 2
1750 #define ospf_snmp_multiforward_unicast 3
1751 return SNMP_INTEGER (ospf_snmp_multiforward_blocked);
1752 break;
1753 case OSPFIFDEMAND: /* 19 */
1754 return SNMP_INTEGER (SNMP_FALSE);
1755 break;
1756 case OSPFIFAUTHTYPE: /* 20 */
1757 if (oi->area)
1758 return SNMP_INTEGER (oi->area->auth_type);
1759 else
1760 return SNMP_INTEGER (0);
1761 break;
1762 default:
1763 return NULL;
1764 break;
1766 return NULL;
1769 #define OSPF_SNMP_METRIC_VALUE 1
1771 struct interface *
1772 ospfIfMetricLookup (struct variable *v, oid *name, size_t *length,
1773 struct in_addr *ifaddr, unsigned int *ifindex, int exact)
1775 int len;
1776 int ifaddr_next = 0;
1777 int ifindex_next = 0;
1778 struct interface *ifp;
1779 oid *offset;
1780 int metric;
1782 if (exact)
1784 if (*length != v->namelen + IN_ADDR_SIZE + 1 + 1)
1785 return NULL;
1787 oid2in_addr (name + v->namelen, IN_ADDR_SIZE, ifaddr);
1788 *ifindex = name[v->namelen + IN_ADDR_SIZE];
1789 metric = name[v->namelen + IN_ADDR_SIZE + 1];
1791 if (metric != OSPF_SNMP_METRIC_VALUE)
1792 return NULL;
1794 return ospf_snmp_if_lookup (ifaddr, ifindex);
1796 else
1798 len = *length - v->namelen;
1799 if (len >= IN_ADDR_SIZE)
1800 len = IN_ADDR_SIZE;
1801 else
1802 ifaddr_next = 1;
1804 oid2in_addr (name + v->namelen, len, ifaddr);
1806 len = *length - v->namelen - IN_ADDR_SIZE;
1807 if (len >= 1)
1808 len = 1;
1809 else
1810 ifindex_next = 1;
1812 if (len == 1)
1813 *ifindex = name[v->namelen + IN_ADDR_SIZE];
1815 ifp = ospf_snmp_if_lookup_next (ifaddr, ifindex, ifaddr_next,
1816 ifindex_next);
1817 if (ifp)
1819 *length = v->namelen + IN_ADDR_SIZE + 1 + 1;
1820 offset = name + v->namelen;
1821 oid_copy_addr (offset, ifaddr, IN_ADDR_SIZE);
1822 offset += IN_ADDR_SIZE;
1823 *offset = *ifindex;
1824 offset++;
1825 *offset = OSPF_SNMP_METRIC_VALUE;
1826 return ifp;
1829 return NULL;
1832 static u_char *
1833 ospfIfMetricEntry (struct variable *v, oid *name, size_t *length, int exact,
1834 size_t *var_len, WriteMethod **write_method)
1836 /* Currently we support metric 1 only. */
1837 struct interface *ifp;
1838 unsigned int ifindex;
1839 struct in_addr ifaddr;
1840 struct ospf_interface *oi;
1841 struct ospf *ospf;
1843 ifindex = 0;
1844 memset (&ifaddr, 0, sizeof (struct in_addr));
1846 /* Check OSPF instance. */
1847 ospf = ospf_lookup ();
1848 if (ospf == NULL)
1849 return NULL;
1851 ifp = ospfIfMetricLookup (v, name, length, &ifaddr, &ifindex, exact);
1852 if (ifp == NULL)
1853 return NULL;
1855 oi = ospf_if_lookup_by_local_addr (ospf, ifp, ifaddr);
1856 if (oi == NULL)
1857 return NULL;
1859 /* Return the current value of the variable */
1860 switch (v->magic)
1862 case OSPFIFMETRICIPADDRESS:
1863 return SNMP_IPADDRESS (ifaddr);
1864 break;
1865 case OSPFIFMETRICADDRESSLESSIF:
1866 return SNMP_INTEGER (ifindex);
1867 break;
1868 case OSPFIFMETRICTOS:
1869 return SNMP_INTEGER (0);
1870 break;
1871 case OSPFIFMETRICVALUE:
1872 return SNMP_INTEGER (OSPF_SNMP_METRIC_VALUE);
1873 break;
1874 case OSPFIFMETRICSTATUS:
1875 return SNMP_INTEGER (1);
1876 break;
1877 default:
1878 return NULL;
1879 break;
1881 return NULL;
1884 struct route_table *ospf_snmp_vl_table;
1886 void
1887 ospf_snmp_vl_add (struct ospf_vl_data *vl_data)
1889 struct prefix_ls lp;
1890 struct route_node *rn;
1892 memset (&lp, 0, sizeof (struct prefix_ls));
1893 lp.family = 0;
1894 lp.prefixlen = 64;
1895 lp.id = vl_data->vl_area_id;
1896 lp.adv_router = vl_data->vl_peer;
1898 rn = route_node_get (ospf_snmp_vl_table, (struct prefix *) &lp);
1899 rn->info = vl_data;
1902 void
1903 ospf_snmp_vl_delete (struct ospf_vl_data *vl_data)
1905 struct prefix_ls lp;
1906 struct route_node *rn;
1908 memset (&lp, 0, sizeof (struct prefix_ls));
1909 lp.family = 0;
1910 lp.prefixlen = 64;
1911 lp.id = vl_data->vl_area_id;
1912 lp.adv_router = vl_data->vl_peer;
1914 rn = route_node_lookup (ospf_snmp_vl_table, (struct prefix *) &lp);
1915 if (! rn)
1916 return;
1917 rn->info = NULL;
1918 route_unlock_node (rn);
1919 route_unlock_node (rn);
1922 struct ospf_vl_data *
1923 ospf_snmp_vl_lookup (struct in_addr *area_id, struct in_addr *neighbor)
1925 struct prefix_ls lp;
1926 struct route_node *rn;
1927 struct ospf_vl_data *vl_data;
1929 memset (&lp, 0, sizeof (struct prefix_ls));
1930 lp.family = 0;
1931 lp.prefixlen = 64;
1932 lp.id = *area_id;
1933 lp.adv_router = *neighbor;
1935 rn = route_node_lookup (ospf_snmp_vl_table, (struct prefix *) &lp);
1936 if (rn)
1938 vl_data = rn->info;
1939 route_unlock_node (rn);
1940 return vl_data;
1942 return NULL;
1945 struct ospf_vl_data *
1946 ospf_snmp_vl_lookup_next (struct in_addr *area_id, struct in_addr *neighbor,
1947 int first)
1949 struct prefix_ls lp;
1950 struct route_node *rn;
1951 struct ospf_vl_data *vl_data;
1953 memset (&lp, 0, sizeof (struct prefix_ls));
1954 lp.family = 0;
1955 lp.prefixlen = 64;
1956 lp.id = *area_id;
1957 lp.adv_router = *neighbor;
1959 if (first)
1960 rn = route_top (ospf_snmp_vl_table);
1961 else
1963 rn = route_node_get (ospf_snmp_vl_table, (struct prefix *) &lp);
1964 rn = route_next (rn);
1967 for (; rn; rn = route_next (rn))
1968 if (rn->info)
1969 break;
1971 if (rn && rn->info)
1973 vl_data = rn->info;
1974 *area_id = vl_data->vl_area_id;
1975 *neighbor = vl_data->vl_peer;
1976 route_unlock_node (rn);
1977 return vl_data;
1979 return NULL;
1982 struct ospf_vl_data *
1983 ospfVirtIfLookup (struct variable *v, oid *name, size_t *length,
1984 struct in_addr *area_id, struct in_addr *neighbor, int exact)
1986 int first;
1987 int len;
1988 struct ospf_vl_data *vl_data;
1990 if (exact)
1992 if (*length != v->namelen + IN_ADDR_SIZE + IN_ADDR_SIZE)
1993 return NULL;
1995 oid2in_addr (name + v->namelen, IN_ADDR_SIZE, area_id);
1996 oid2in_addr (name + v->namelen + IN_ADDR_SIZE, IN_ADDR_SIZE, neighbor);
1998 return ospf_snmp_vl_lookup (area_id, neighbor);
2000 else
2002 first = 0;
2004 len = *length - v->namelen;
2005 if (len <= 0)
2006 first = 1;
2007 if (len > IN_ADDR_SIZE)
2008 len = IN_ADDR_SIZE;
2009 oid2in_addr (name + v->namelen, len, area_id);
2011 len = *length - v->namelen - IN_ADDR_SIZE;
2012 if (len > IN_ADDR_SIZE)
2013 len = IN_ADDR_SIZE;
2014 oid2in_addr (name + v->namelen + IN_ADDR_SIZE, len, neighbor);
2016 vl_data = ospf_snmp_vl_lookup_next (area_id, neighbor, first);
2018 if (vl_data)
2020 *length = v->namelen + IN_ADDR_SIZE + IN_ADDR_SIZE;
2021 oid_copy_addr (name + v->namelen, area_id, IN_ADDR_SIZE);
2022 oid_copy_addr (name + v->namelen + IN_ADDR_SIZE, neighbor,
2023 IN_ADDR_SIZE);
2024 return vl_data;
2027 return NULL;
2030 static u_char *
2031 ospfVirtIfEntry (struct variable *v, oid *name, size_t *length, int exact,
2032 size_t *var_len, WriteMethod **write_method)
2034 struct ospf_vl_data *vl_data;
2035 struct ospf_interface *oi;
2036 struct in_addr area_id;
2037 struct in_addr neighbor;
2039 memset (&area_id, 0, sizeof (struct in_addr));
2040 memset (&neighbor, 0, sizeof (struct in_addr));
2042 vl_data = ospfVirtIfLookup (v, name, length, &area_id, &neighbor, exact);
2043 if (! vl_data)
2044 return NULL;
2045 oi = vl_data->vl_oi;
2046 if (! oi)
2047 return NULL;
2049 /* Return the current value of the variable */
2050 switch (v->magic)
2052 case OSPFVIRTIFAREAID:
2053 return SNMP_IPADDRESS (area_id);
2054 break;
2055 case OSPFVIRTIFNEIGHBOR:
2056 return SNMP_IPADDRESS (neighbor);
2057 break;
2058 case OSPFVIRTIFTRANSITDELAY:
2059 return SNMP_INTEGER (OSPF_IF_PARAM (oi, transmit_delay));
2060 break;
2061 case OSPFVIRTIFRETRANSINTERVAL:
2062 return SNMP_INTEGER (OSPF_IF_PARAM (oi, retransmit_interval));
2063 break;
2064 case OSPFVIRTIFHELLOINTERVAL:
2065 return SNMP_INTEGER (OSPF_IF_PARAM (oi, v_hello));
2066 break;
2067 case OSPFVIRTIFRTRDEADINTERVAL:
2068 return SNMP_INTEGER (OSPF_IF_PARAM (oi, v_wait));
2069 break;
2070 case OSPFVIRTIFSTATE:
2071 return SNMP_INTEGER (oi->state);
2072 break;
2073 case OSPFVIRTIFEVENTS:
2074 return SNMP_INTEGER (oi->state_change);
2075 break;
2076 case OSPFVIRTIFAUTHKEY:
2077 *var_len = 0;
2078 return (u_char *) OSPF_IF_PARAM (oi, auth_simple);
2079 break;
2080 case OSPFVIRTIFSTATUS:
2081 return SNMP_INTEGER (SNMP_VALID);
2082 break;
2083 case OSPFVIRTIFAUTHTYPE:
2084 if (oi->area)
2085 return SNMP_INTEGER (oi->area->auth_type);
2086 else
2087 return SNMP_INTEGER (0);
2088 break;
2089 default:
2090 return NULL;
2091 break;
2093 return NULL;
2096 struct ospf_neighbor *
2097 ospf_snmp_nbr_lookup (struct ospf *ospf, struct in_addr *nbr_addr,
2098 unsigned int *ifindex)
2100 struct listnode *nn;
2101 struct ospf_interface *oi;
2102 struct ospf_neighbor *nbr;
2103 struct route_node *rn;
2105 LIST_LOOP (ospf->oiflist, oi, nn)
2107 for (rn = route_top (oi->nbrs); rn; rn = route_next (rn))
2108 if ((nbr = rn->info) != NULL
2109 && nbr != oi->nbr_self
2110 && nbr->state != NSM_Down
2111 && nbr->src.s_addr != 0)
2113 if (IPV4_ADDR_SAME (&nbr->src, nbr_addr))
2115 route_unlock_node (rn);
2116 return nbr;
2120 return NULL;
2123 struct ospf_neighbor *
2124 ospf_snmp_nbr_lookup_next (struct in_addr *nbr_addr, unsigned int *ifindex,
2125 int first)
2127 struct listnode *nn;
2128 struct ospf_interface *oi;
2129 struct ospf_neighbor *nbr;
2130 struct route_node *rn;
2131 struct ospf_neighbor *min = NULL;
2132 struct ospf *ospf = ospf;
2134 ospf = ospf_lookup ();
2135 LIST_LOOP (ospf->oiflist, oi, nn)
2137 for (rn = route_top (oi->nbrs); rn; rn = route_next (rn))
2138 if ((nbr = rn->info) != NULL
2139 && nbr != oi->nbr_self
2140 && nbr->state != NSM_Down
2141 && nbr->src.s_addr != 0)
2143 if (first)
2145 if (! min)
2146 min = nbr;
2147 else if (ntohl (nbr->src.s_addr) < ntohl (min->src.s_addr))
2148 min = nbr;
2150 else if (ntohl (nbr->src.s_addr) > ntohl (nbr_addr->s_addr))
2152 if (! min)
2153 min = nbr;
2154 else if (ntohl (nbr->src.s_addr) < ntohl (min->src.s_addr))
2155 min = nbr;
2159 if (min)
2161 *nbr_addr = min->src;
2162 *ifindex = 0;
2163 return min;
2165 return NULL;
2168 struct ospf_neighbor *
2169 ospfNbrLookup (struct variable *v, oid *name, size_t *length,
2170 struct in_addr *nbr_addr, unsigned int *ifindex, int exact)
2172 int len;
2173 int first;
2174 struct ospf_neighbor *nbr;
2175 struct ospf *ospf;
2177 ospf = ospf_lookup ();
2179 if (exact)
2181 if (*length != v->namelen + IN_ADDR_SIZE + 1)
2182 return NULL;
2184 oid2in_addr (name + v->namelen, IN_ADDR_SIZE, nbr_addr);
2185 *ifindex = name[v->namelen + IN_ADDR_SIZE];
2187 return ospf_snmp_nbr_lookup (ospf, nbr_addr, ifindex);
2189 else
2191 first = 0;
2192 len = *length - v->namelen;
2194 if (len <= 0)
2195 first = 1;
2197 if (len > IN_ADDR_SIZE)
2198 len = IN_ADDR_SIZE;
2200 oid2in_addr (name + v->namelen, len, nbr_addr);
2202 len = *length - v->namelen - IN_ADDR_SIZE;
2203 if (len >= 1)
2204 *ifindex = name[v->namelen + IN_ADDR_SIZE];
2206 nbr = ospf_snmp_nbr_lookup_next (nbr_addr, ifindex, first);
2208 if (nbr)
2210 *length = v->namelen + IN_ADDR_SIZE + 1;
2211 oid_copy_addr (name + v->namelen, nbr_addr, IN_ADDR_SIZE);
2212 name[v->namelen + IN_ADDR_SIZE] = *ifindex;
2213 return nbr;
2216 return NULL;
2219 static u_char *
2220 ospfNbrEntry (struct variable *v, oid *name, size_t *length, int exact,
2221 size_t *var_len, WriteMethod **write_method)
2223 struct in_addr nbr_addr;
2224 unsigned int ifindex;
2225 struct ospf_neighbor *nbr;
2226 struct ospf_interface *oi;
2228 memset (&nbr_addr, 0, sizeof (struct in_addr));
2229 ifindex = 0;
2231 nbr = ospfNbrLookup (v, name, length, &nbr_addr, &ifindex, exact);
2232 if (! nbr)
2233 return NULL;
2234 oi = nbr->oi;
2235 if (! oi)
2236 return NULL;
2238 /* Return the current value of the variable */
2239 switch (v->magic)
2241 case OSPFNBRIPADDR:
2242 return SNMP_IPADDRESS (nbr_addr);
2243 break;
2244 case OSPFNBRADDRESSLESSINDEX:
2245 return SNMP_INTEGER (ifindex);
2246 break;
2247 case OSPFNBRRTRID:
2248 return SNMP_IPADDRESS (nbr->router_id);
2249 break;
2250 case OSPFNBROPTIONS:
2251 return SNMP_INTEGER (oi->nbr_self->options);
2252 break;
2253 case OSPFNBRPRIORITY:
2254 return SNMP_INTEGER (nbr->priority);
2255 break;
2256 case OSPFNBRSTATE:
2257 return SNMP_INTEGER (nbr->state);
2258 break;
2259 case OSPFNBREVENTS:
2260 return SNMP_INTEGER (nbr->state_change);
2261 break;
2262 case OSPFNBRLSRETRANSQLEN:
2263 return SNMP_INTEGER (ospf_ls_retransmit_count (nbr));
2264 break;
2265 case OSPFNBMANBRSTATUS:
2266 return SNMP_INTEGER (SNMP_VALID);
2267 break;
2268 case OSPFNBMANBRPERMANENCE:
2269 return SNMP_INTEGER (2);
2270 break;
2271 case OSPFNBRHELLOSUPPRESSED:
2272 return SNMP_INTEGER (SNMP_FALSE);
2273 break;
2274 default:
2275 return NULL;
2276 break;
2278 return NULL;
2281 static u_char *
2282 ospfVirtNbrEntry (struct variable *v, oid *name, size_t *length, int exact,
2283 size_t *var_len, WriteMethod **write_method)
2285 struct ospf_vl_data *vl_data;
2286 struct in_addr area_id;
2287 struct in_addr neighbor;
2288 struct ospf *ospf;
2290 memset (&area_id, 0, sizeof (struct in_addr));
2291 memset (&neighbor, 0, sizeof (struct in_addr));
2293 /* Check OSPF instance. */
2294 ospf = ospf_lookup ();
2295 if (ospf == NULL)
2296 return NULL;
2298 vl_data = ospfVirtIfLookup (v, name, length, &area_id, &neighbor, exact);
2299 if (! vl_data)
2300 return NULL;
2302 /* Return the current value of the variable */
2303 switch (v->magic)
2305 case OSPFVIRTNBRAREA:
2306 return (u_char *) NULL;
2307 break;
2308 case OSPFVIRTNBRRTRID:
2309 return (u_char *) NULL;
2310 break;
2311 case OSPFVIRTNBRIPADDR:
2312 return (u_char *) NULL;
2313 break;
2314 case OSPFVIRTNBROPTIONS:
2315 return (u_char *) NULL;
2316 break;
2317 case OSPFVIRTNBRSTATE:
2318 return (u_char *) NULL;
2319 break;
2320 case OSPFVIRTNBREVENTS:
2321 return (u_char *) NULL;
2322 break;
2323 case OSPFVIRTNBRLSRETRANSQLEN:
2324 return (u_char *) NULL;
2325 break;
2326 case OSPFVIRTNBRHELLOSUPPRESSED:
2327 return (u_char *) NULL;
2328 break;
2329 default:
2330 return NULL;
2331 break;
2333 return NULL;
2336 struct ospf_lsa *
2337 ospfExtLsdbLookup (struct variable *v, oid *name, size_t *length, u_char *type,
2338 struct in_addr *ls_id, struct in_addr *router_id, int exact)
2340 int first;
2341 oid *offset;
2342 int offsetlen;
2343 u_char lsa_type;
2344 int len;
2345 struct ospf_lsa *lsa;
2346 struct ospf *ospf;
2348 ospf = ospf_lookup ();
2349 if (exact)
2351 if (*length != v->namelen + 1 + IN_ADDR_SIZE + IN_ADDR_SIZE)
2352 return NULL;
2354 offset = name + v->namelen;
2356 /* Make it sure given value match to type. */
2357 lsa_type = *offset;
2358 offset++;
2360 if (lsa_type != *type)
2361 return NULL;
2363 /* LS ID. */
2364 oid2in_addr (offset, IN_ADDR_SIZE, ls_id);
2365 offset += IN_ADDR_SIZE;
2367 /* Router ID. */
2368 oid2in_addr (offset, IN_ADDR_SIZE, router_id);
2370 return ospf_lsdb_lookup_by_id (ospf->lsdb, *type, *ls_id, *router_id);
2372 else
2374 /* Get variable length. */
2375 first = 0;
2376 offset = name + v->namelen;
2377 offsetlen = *length - v->namelen;
2379 /* LSA type value. */
2380 lsa_type = *offset;
2381 offset++;
2382 offsetlen--;
2384 if (offsetlen <= 0 || lsa_type < OSPF_AS_EXTERNAL_LSA)
2385 first = 1;
2387 /* LS ID. */
2388 len = offsetlen;
2389 if (len > IN_ADDR_SIZE)
2390 len = IN_ADDR_SIZE;
2392 oid2in_addr (offset, len, ls_id);
2394 offset += IN_ADDR_SIZE;
2395 offsetlen -= IN_ADDR_SIZE;
2397 /* Router ID. */
2398 len = offsetlen;
2399 if (len > IN_ADDR_SIZE)
2400 len = IN_ADDR_SIZE;
2402 oid2in_addr (offset, len, router_id);
2404 lsa = ospf_lsdb_lookup_by_id_next (ospf->lsdb, *type, *ls_id,
2405 *router_id, first);
2407 if (lsa)
2409 /* Fill in length. */
2410 *length = v->namelen + 1 + IN_ADDR_SIZE + IN_ADDR_SIZE;
2412 /* Fill in value. */
2413 offset = name + v->namelen;
2415 *offset = OSPF_AS_EXTERNAL_LSA;
2416 offset++;
2417 oid_copy_addr (offset, &lsa->data->id, IN_ADDR_SIZE);
2418 offset += IN_ADDR_SIZE;
2419 oid_copy_addr (offset, &lsa->data->adv_router, IN_ADDR_SIZE);
2421 return lsa;
2424 return NULL;
2427 static u_char *
2428 ospfExtLsdbEntry (struct variable *v, oid *name, size_t *length, int exact,
2429 size_t *var_len, WriteMethod **write_method)
2431 struct ospf_lsa *lsa;
2432 struct lsa_header *lsah;
2433 u_char type;
2434 struct in_addr ls_id;
2435 struct in_addr router_id;
2436 struct ospf *ospf;
2438 type = OSPF_AS_EXTERNAL_LSA;
2439 memset (&ls_id, 0, sizeof (struct in_addr));
2440 memset (&router_id, 0, sizeof (struct in_addr));
2442 /* Check OSPF instance. */
2443 ospf = ospf_lookup ();
2444 if (ospf == NULL)
2445 return NULL;
2447 lsa = ospfExtLsdbLookup (v, name, length, &type, &ls_id, &router_id, exact);
2448 if (! lsa)
2449 return NULL;
2451 lsah = lsa->data;
2453 /* Return the current value of the variable */
2454 switch (v->magic)
2456 case OSPFEXTLSDBTYPE:
2457 return SNMP_INTEGER (OSPF_AS_EXTERNAL_LSA);
2458 break;
2459 case OSPFEXTLSDBLSID:
2460 return SNMP_IPADDRESS (lsah->id);
2461 break;
2462 case OSPFEXTLSDBROUTERID:
2463 return SNMP_IPADDRESS (lsah->adv_router);
2464 break;
2465 case OSPFEXTLSDBSEQUENCE:
2466 return SNMP_INTEGER (lsah->ls_seqnum);
2467 break;
2468 case OSPFEXTLSDBAGE:
2469 return SNMP_INTEGER (lsah->ls_age);
2470 break;
2471 case OSPFEXTLSDBCHECKSUM:
2472 return SNMP_INTEGER (lsah->checksum);
2473 break;
2474 case OSPFEXTLSDBADVERTISEMENT:
2475 *var_len = ntohs (lsah->length);
2476 return (u_char *) lsah;
2477 break;
2478 default:
2479 return NULL;
2480 break;
2482 return NULL;
2485 static u_char *
2486 ospfAreaAggregateEntry (struct variable *v, oid *name, size_t *length,
2487 int exact, size_t *var_len, WriteMethod **write_method)
2489 /* Return the current value of the variable */
2490 switch (v->magic)
2492 case OSPFAREAAGGREGATEAREAID:
2493 return (u_char *) NULL;
2494 break;
2495 case OSPFAREAAGGREGATELSDBTYPE:
2496 return (u_char *) NULL;
2497 break;
2498 case OSPFAREAAGGREGATENET:
2499 return (u_char *) NULL;
2500 break;
2501 case OSPFAREAAGGREGATEMASK:
2502 return (u_char *) NULL;
2503 break;
2504 case OSPFAREAAGGREGATESTATUS:
2505 return (u_char *) NULL;
2506 break;
2507 case OSPFAREAAGGREGATEEFFECT:
2508 return (u_char *) NULL;
2509 break;
2510 default:
2511 return NULL;
2512 break;
2514 return NULL;
2517 /* Register OSPF2-MIB. */
2518 void
2519 ospf_snmp_init ()
2521 ospf_snmp_iflist = list_new ();
2522 ospf_snmp_vl_table = route_table_init ();
2523 smux_init (ospfd_oid, sizeof (ospfd_oid) / sizeof (oid));
2524 REGISTER_MIB("mibII/ospf", ospf_variables, variable, ospf_oid);
2525 smux_start ();
2527 #endif /* HAVE_SNMP */