]> git.proxmox.com Git - mirror_frr.git/blob - isisd/isis_circuit.c
e34d491a6eaaf3f403e63d5e7f40f6d7c9981342
[mirror_frr.git] / isisd / isis_circuit.c
1 /*
2 * IS-IS Rout(e)ing protocol - isis_circuit.h
3 *
4 * Copyright (C) 2001,2002 Sampo Saaristo
5 * Tampere University of Technology
6 * Institute of Communications Engineering
7 *
8 * This program is free software; you can redistribute it and/or modify it
9 * under the terms of the GNU General Public Licenseas published by the Free
10 * Software Foundation; either version 2 of the License, or (at your option)
11 * any later version.
12 *
13 * This program is distributed in the hope that it will be useful,but WITHOUT
14 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
15 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
16 * more details.
17
18 * You should have received a copy of the GNU General Public License along
19 * with this program; if not, write to the Free Software Foundation, Inc.,
20 * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
21 */
22 #include <zebra.h>
23 #ifdef GNU_LINUX
24 #include <net/ethernet.h>
25 #else
26 #include <netinet/if_ether.h>
27 #endif
28
29 #ifndef ETHER_ADDR_LEN
30 #define ETHER_ADDR_LEN ETHERADDRL
31 #endif
32
33 #include "log.h"
34 #include "memory.h"
35 #include "if.h"
36 #include "linklist.h"
37 #include "command.h"
38 #include "thread.h"
39 #include "hash.h"
40 #include "prefix.h"
41 #include "stream.h"
42
43 #include "isisd/dict.h"
44 #include "isisd/include-netbsd/iso.h"
45 #include "isisd/isis_constants.h"
46 #include "isisd/isis_common.h"
47 #include "isisd/isis_circuit.h"
48 #include "isisd/isis_tlv.h"
49 #include "isisd/isis_lsp.h"
50 #include "isisd/isis_pdu.h"
51 #include "isisd/isis_network.h"
52 #include "isisd/isis_misc.h"
53 #include "isisd/isis_constants.h"
54 #include "isisd/isis_adjacency.h"
55 #include "isisd/isis_dr.h"
56 #include "isisd/isis_flags.h"
57 #include "isisd/isisd.h"
58 #include "isisd/isis_csm.h"
59 #include "isisd/isis_events.h"
60
61 extern struct thread_master *master;
62 extern struct isis *isis;
63
64 /*
65 * Prototypes.
66 */
67 void isis_circuit_down(struct isis_circuit *);
68 int isis_interface_config_write(struct vty *);
69 int isis_if_new_hook(struct interface *);
70 int isis_if_delete_hook(struct interface *);
71
72 struct isis_circuit *
73 isis_circuit_new ()
74 {
75 struct isis_circuit *circuit;
76 int i;
77
78 circuit = XCALLOC (MTYPE_ISIS_CIRCUIT, sizeof (struct isis_circuit));
79 if (circuit)
80 {
81 /* set default metrics for circuit */
82 for (i = 0; i < 2; i++)
83 {
84 circuit->metrics[i].metric_default = DEFAULT_CIRCUIT_METRICS;
85 circuit->metrics[i].metric_expense = METRICS_UNSUPPORTED;
86 circuit->metrics[i].metric_error = METRICS_UNSUPPORTED;
87 circuit->metrics[i].metric_delay = METRICS_UNSUPPORTED;
88 circuit->te_metric[i] = DEFAULT_CIRCUIT_METRICS;
89 }
90 }
91 else
92 {
93 zlog_err ("Can't malloc isis circuit");
94 return NULL;
95 }
96
97 return circuit;
98 }
99
100 void
101 isis_circuit_configure (struct isis_circuit *circuit, struct isis_area *area)
102 {
103 int i;
104 circuit->area = area;
105 /*
106 * The level for the circuit is same as for the area, unless configured
107 * otherwise.
108 */
109 circuit->circuit_is_type = area->is_type;
110 /*
111 * Default values
112 */
113 for (i = 0; i < 2; i++)
114 {
115 circuit->hello_interval[i] = HELLO_INTERVAL;
116 circuit->hello_multiplier[i] = HELLO_MULTIPLIER;
117 circuit->csnp_interval[i] = CSNP_INTERVAL;
118 circuit->psnp_interval[i] = PSNP_INTERVAL;
119 circuit->u.bc.priority[i] = DEFAULT_PRIORITY;
120 }
121 if (circuit->circ_type == CIRCUIT_T_BROADCAST)
122 {
123 circuit->u.bc.adjdb[0] = list_new ();
124 circuit->u.bc.adjdb[1] = list_new ();
125 circuit->u.bc.pad_hellos = 1;
126 }
127 circuit->lsp_interval = LSP_INTERVAL;
128
129 /*
130 * Add the circuit into area
131 */
132 listnode_add (area->circuit_list, circuit);
133
134 circuit->idx = flags_get_index (&area->flags);
135 circuit->lsp_queue = list_new ();
136
137 return;
138 }
139
140 void
141 isis_circuit_deconfigure (struct isis_circuit *circuit,
142 struct isis_area *area)
143 {
144
145 /* destroy adjacencies */
146 if (circuit->u.bc.adjdb[0])
147 isis_adjdb_iterate (circuit->u.bc.adjdb[0], (void(*) (struct isis_adjacency *, void *)) isis_delete_adj, circuit->u.bc.adjdb[0]);
148 if (circuit->u.bc.adjdb[1])
149 isis_adjdb_iterate (circuit->u.bc.adjdb[1], (void(*) (struct isis_adjacency *, void *)) isis_delete_adj, circuit->u.bc.adjdb[1]);
150 /* Remove circuit from area */
151 listnode_delete (area->circuit_list, circuit);
152 /* Free the index of SRM and SSN flags */
153 flags_free_index (&area->flags, circuit->idx);
154
155 return;
156 }
157
158 struct isis_circuit *
159 circuit_lookup_by_ifp (struct interface *ifp, struct list *list)
160 {
161 struct isis_circuit *circuit = NULL;
162 struct listnode *node;
163
164 if (!list)
165 return NULL;
166
167 for (ALL_LIST_ELEMENTS_RO (list, node, circuit))
168 if (circuit->interface == ifp)
169 return circuit;
170
171 return NULL;
172 }
173
174 struct isis_circuit *
175 circuit_scan_by_ifp (struct interface *ifp)
176 {
177 struct isis_area *area;
178 struct listnode *node;
179 struct isis_circuit *circuit;
180
181 if (!isis->area_list)
182 return NULL;
183
184 for (ALL_LIST_ELEMENTS_RO (isis->area_list, node, area))
185 {
186 circuit = circuit_lookup_by_ifp (ifp, area->circuit_list);
187 if (circuit)
188 return circuit;
189 }
190
191 return circuit_lookup_by_ifp (ifp, isis->init_circ_list);
192 }
193
194 void
195 isis_circuit_del (struct isis_circuit *circuit)
196 {
197
198 if (!circuit)
199 return;
200
201 if (circuit->circ_type == CIRCUIT_T_BROADCAST)
202 {
203 /* destroy adjacency databases */
204 if (circuit->u.bc.adjdb[0])
205 list_delete (circuit->u.bc.adjdb[0]);
206 if (circuit->u.bc.adjdb[1])
207 list_delete (circuit->u.bc.adjdb[1]);
208 /* destroy neighbour lists */
209 if (circuit->u.bc.lan_neighs[0])
210 list_delete (circuit->u.bc.lan_neighs[0]);
211 if (circuit->u.bc.lan_neighs[1])
212 list_delete (circuit->u.bc.lan_neighs[1]);
213 /* destroy addresses */
214 }
215 if (circuit->ip_addrs)
216 list_delete (circuit->ip_addrs);
217 #ifdef HAVE_IPV6
218 if (circuit->ipv6_link)
219 list_delete (circuit->ipv6_link);
220 if (circuit->ipv6_non_link)
221 list_delete (circuit->ipv6_non_link);
222 #endif /* HAVE_IPV6 */
223
224 /* and lastly the circuit itself */
225 XFREE (MTYPE_ISIS_CIRCUIT, circuit);
226
227 return;
228 }
229
230 void
231 isis_circuit_add_addr (struct isis_circuit *circuit,
232 struct connected *connected)
233 {
234 struct prefix_ipv4 *ipv4;
235 u_char buf[BUFSIZ];
236 #ifdef HAVE_IPV6
237 struct prefix_ipv6 *ipv6;
238 #endif /* HAVE_IPV6 */
239
240 if (!circuit->ip_addrs)
241 circuit->ip_addrs = list_new ();
242 #ifdef HAVE_IPV6
243 if (!circuit->ipv6_link)
244 circuit->ipv6_link = list_new ();
245 if (!circuit->ipv6_non_link)
246 circuit->ipv6_non_link = list_new ();
247 #endif /* HAVE_IPV6 */
248
249 memset (&buf, 0, BUFSIZ);
250 if (connected->address->family == AF_INET)
251 {
252 ipv4 = prefix_ipv4_new ();
253 ipv4->prefixlen = connected->address->prefixlen;
254 ipv4->prefix = connected->address->u.prefix4;
255 listnode_add (circuit->ip_addrs, ipv4);
256 if (circuit->area)
257 lsp_regenerate_schedule (circuit->area);
258
259 #ifdef EXTREME_DEBUG
260 prefix2str (connected->address, buf, BUFSIZ);
261 zlog_debug ("Added IP address %s to circuit %d", buf,
262 circuit->circuit_id);
263 #endif /* EXTREME_DEBUG */
264 }
265 #ifdef HAVE_IPV6
266 if (connected->address->family == AF_INET6)
267 {
268 ipv6 = prefix_ipv6_new ();
269 ipv6->prefixlen = connected->address->prefixlen;
270 ipv6->prefix = connected->address->u.prefix6;
271
272 if (IN6_IS_ADDR_LINKLOCAL (&ipv6->prefix))
273 listnode_add (circuit->ipv6_link, ipv6);
274 else
275 listnode_add (circuit->ipv6_non_link, ipv6);
276 if (circuit->area)
277 lsp_regenerate_schedule (circuit->area);
278
279 #ifdef EXTREME_DEBUG
280 prefix2str (connected->address, buf, BUFSIZ);
281 zlog_debug ("Added IPv6 address %s to circuit %d", buf,
282 circuit->circuit_id);
283 #endif /* EXTREME_DEBUG */
284 }
285 #endif /* HAVE_IPV6 */
286 return;
287 }
288
289 void
290 isis_circuit_del_addr (struct isis_circuit *circuit,
291 struct connected *connected)
292 {
293 struct prefix_ipv4 *ipv4, *ip = NULL;
294 struct listnode *node;
295 u_char buf[BUFSIZ];
296 #ifdef HAVE_IPV6
297 struct prefix_ipv6 *ipv6, *ip6 = NULL;
298 int found = 0;
299 #endif /* HAVE_IPV6 */
300
301 memset (&buf, 0, BUFSIZ);
302 if (connected->address->family == AF_INET)
303 {
304 ipv4 = prefix_ipv4_new ();
305 ipv4->prefixlen = connected->address->prefixlen;
306 ipv4->prefix = connected->address->u.prefix4;
307
308 for (ALL_LIST_ELEMENTS_RO (circuit->ip_addrs, node, ip))
309 if (prefix_same ((struct prefix *) ip, (struct prefix *) &ipv4))
310 break;
311
312 if (ip)
313 {
314 listnode_delete (circuit->ip_addrs, ip);
315 if (circuit->area)
316 lsp_regenerate_schedule (circuit->area);
317 }
318 else
319 {
320 prefix2str (connected->address, (char *)buf, BUFSIZ);
321 zlog_warn("Nonexitant ip address %s removal attempt from circuit \
322 %d", buf, circuit->circuit_id);
323 }
324 }
325 #ifdef HAVE_IPV6
326 if (connected->address->family == AF_INET6)
327 {
328 ipv6 = prefix_ipv6_new ();
329 ipv6->prefixlen = connected->address->prefixlen;
330 ipv6->prefix = connected->address->u.prefix6;
331
332 if (IN6_IS_ADDR_LINKLOCAL (&ipv6->prefix))
333 {
334 for (ALL_LIST_ELEMENTS_RO (circuit->ipv6_link, node, ip6))
335 {
336 if (prefix_same ((struct prefix *) ip6, (struct prefix *) ipv6))
337 break;
338 }
339 if (ip6)
340 {
341 listnode_delete (circuit->ipv6_link, ip6);
342 found = 1;
343 }
344 }
345 else
346 {
347 for (ALL_LIST_ELEMENTS_RO (circuit->ipv6_non_link, node, ip6))
348 {
349 if (prefix_same ((struct prefix *) ip6, (struct prefix *) ipv6))
350 break;
351 }
352 if (ip6)
353 {
354 listnode_delete (circuit->ipv6_non_link, ip6);
355 found = 1;
356 }
357 }
358
359 if (!found)
360 {
361 prefix2str (connected->address, (char *)buf, BUFSIZ);
362 zlog_warn("Nonexitant ip address %s removal attempt from \
363 circuit %d", buf, circuit->circuit_id);
364 }
365 else
366 if (circuit->area)
367 lsp_regenerate_schedule (circuit->area);
368 }
369 #endif /* HAVE_IPV6 */
370 return;
371 }
372
373 void
374 isis_circuit_if_add (struct isis_circuit *circuit, struct interface *ifp)
375 {
376 struct listnode *node, *nnode;
377 struct connected *conn;
378
379 circuit->interface = ifp;
380 ifp->info = circuit;
381
382 circuit->circuit_id = ifp->ifindex % 255; /* FIXME: Why not ? */
383
384 /* isis_circuit_update_addrs (circuit, ifp); */
385
386 if (if_is_broadcast (ifp))
387 {
388 circuit->circ_type = CIRCUIT_T_BROADCAST;
389 /*
390 * Get the Hardware Address
391 */
392 #ifdef HAVE_STRUCT_SOCKADDR_DL
393 #ifndef SUNOS_5
394 if (circuit->interface->sdl.sdl_alen != ETHER_ADDR_LEN)
395 zlog_warn ("unsupported link layer");
396 else
397 memcpy (circuit->u.bc.snpa, LLADDR (&circuit->interface->sdl),
398 ETH_ALEN);
399 #endif
400 #else
401 if (circuit->interface->hw_addr_len != ETH_ALEN)
402 {
403 zlog_warn ("unsupported link layer");
404 }
405 else
406 {
407 memcpy (circuit->u.bc.snpa, circuit->interface->hw_addr, ETH_ALEN);
408 }
409 #ifdef EXTREME_DEGUG
410 zlog_debug ("isis_circuit_if_add: if_id %d, isomtu %d snpa %s",
411 circuit->interface->ifindex, ISO_MTU (circuit),
412 snpa_print (circuit->u.bc.snpa));
413
414 #endif /* EXTREME_DEBUG */
415 #endif /* HAVE_STRUCT_SOCKADDR_DL */
416 }
417 else if (if_is_pointopoint (ifp))
418 {
419 circuit->circ_type = CIRCUIT_T_P2P;
420 }
421 else
422 {
423 /* It's normal in case of loopback etc. */
424 if (isis->debugs & DEBUG_EVENTS)
425 zlog_debug ("isis_circuit_if_add: unsupported media");
426 }
427
428 for (ALL_LIST_ELEMENTS (ifp->connected, node, nnode, conn))
429 isis_circuit_add_addr (circuit, conn);
430
431 return;
432 }
433
434 void
435 isis_circuit_update_params (struct isis_circuit *circuit,
436 struct interface *ifp)
437 {
438 assert (circuit);
439
440 if (circuit->circuit_id != ifp->ifindex)
441 {
442 zlog_warn ("changing circuit_id %d->%d", circuit->circuit_id,
443 ifp->ifindex);
444 circuit->circuit_id = ifp->ifindex % 255;
445 }
446
447 /* FIXME: Why is this needed? shouldn't we compare to the area's mtu */
448 /* Ofer, this was here in case someone changes the mtu (e.g. with ifconfig)
449 The areas MTU is the minimum of mtu's of circuits in the area
450 now we can't catch the change
451 if (circuit->mtu != ifp->mtu) {
452 zlog_warn ("changing circuit mtu %d->%d", circuit->mtu,
453 ifp->mtu);
454 circuit->mtu = ifp->mtu;
455 }
456 */
457 /*
458 * Get the Hardware Address
459 */
460 #ifdef HAVE_STRUCT_SOCKADDR_DL
461 #ifndef SUNOS_5
462 if (circuit->interface->sdl.sdl_alen != ETHER_ADDR_LEN)
463 zlog_warn ("unsupported link layer");
464 else
465 memcpy (circuit->u.bc.snpa, LLADDR (&circuit->interface->sdl), ETH_ALEN);
466 #endif
467 #else
468 if (circuit->interface->hw_addr_len != ETH_ALEN)
469 {
470 zlog_warn ("unsupported link layer");
471 }
472 else
473 {
474 if (memcmp (circuit->u.bc.snpa, circuit->interface->hw_addr, ETH_ALEN))
475 {
476 zlog_warn ("changing circuit snpa %s->%s",
477 snpa_print (circuit->u.bc.snpa),
478 snpa_print (circuit->interface->hw_addr));
479 }
480 }
481 #endif
482
483 if (if_is_broadcast (ifp))
484 {
485 circuit->circ_type = CIRCUIT_T_BROADCAST;
486 }
487 else if (if_is_pointopoint (ifp))
488 {
489 circuit->circ_type = CIRCUIT_T_P2P;
490 }
491 else
492 {
493 zlog_warn ("isis_circuit_update_params: unsupported media");
494 }
495
496 return;
497 }
498
499 void
500 isis_circuit_if_del (struct isis_circuit *circuit)
501 {
502 circuit->interface->info = NULL;
503 circuit->interface = NULL;
504
505 return;
506 }
507
508 void
509 isis_circuit_up (struct isis_circuit *circuit)
510 {
511
512 if (circuit->circ_type == CIRCUIT_T_BROADCAST)
513 {
514 if (circuit->area->min_bcast_mtu == 0 ||
515 ISO_MTU (circuit) < circuit->area->min_bcast_mtu)
516 circuit->area->min_bcast_mtu = ISO_MTU (circuit);
517 /*
518 * ISO 10589 - 8.4.1 Enabling of broadcast circuits
519 */
520
521 /* initilizing the hello sending threads
522 * for a broadcast IF
523 */
524
525 /* 8.4.1 a) commence sending of IIH PDUs */
526
527 if (circuit->circuit_is_type & IS_LEVEL_1)
528 {
529 thread_add_event (master, send_lan_l1_hello, circuit, 0);
530 circuit->u.bc.lan_neighs[0] = list_new ();
531 }
532
533 if (circuit->circuit_is_type & IS_LEVEL_2)
534 {
535 thread_add_event (master, send_lan_l2_hello, circuit, 0);
536 circuit->u.bc.lan_neighs[1] = list_new ();
537 }
538
539 /* 8.4.1 b) FIXME: solicit ES - 8.4.6 */
540 /* 8.4.1 c) FIXME: listen for ESH PDUs */
541
542 /* 8.4.1 d) */
543 /* dr election will commence in... */
544 if (circuit->circuit_is_type & IS_LEVEL_1)
545 THREAD_TIMER_ON (master, circuit->u.bc.t_run_dr[0], isis_run_dr_l1,
546 circuit, 2 * circuit->hello_interval[0]);
547 if (circuit->circuit_is_type & IS_LEVEL_2)
548 THREAD_TIMER_ON (master, circuit->u.bc.t_run_dr[1], isis_run_dr_l2,
549 circuit, 2 * circuit->hello_interval[1]);
550 }
551 else
552 {
553 /* initializing the hello send threads
554 * for a ptp IF
555 */
556 thread_add_event (master, send_p2p_hello, circuit, 0);
557
558 }
559
560 /* initializing PSNP timers */
561 if (circuit->circuit_is_type & IS_LEVEL_1)
562 {
563 THREAD_TIMER_ON (master, circuit->t_send_psnp[0], send_l1_psnp, circuit,
564 isis_jitter (circuit->psnp_interval[0], PSNP_JITTER));
565 }
566
567 if (circuit->circuit_is_type & IS_LEVEL_2)
568 {
569 THREAD_TIMER_ON (master, circuit->t_send_psnp[1], send_l2_psnp, circuit,
570 isis_jitter (circuit->psnp_interval[1], PSNP_JITTER));
571 }
572
573 /* initialize the circuit streams */
574 if (circuit->rcv_stream == NULL)
575 circuit->rcv_stream = stream_new (ISO_MTU (circuit));
576
577 if (circuit->snd_stream == NULL)
578 circuit->snd_stream = stream_new (ISO_MTU (circuit));
579
580 /* unified init for circuits */
581 isis_sock_init (circuit);
582
583 #ifdef GNU_LINUX
584 THREAD_READ_ON (master, circuit->t_read, isis_receive, circuit,
585 circuit->fd);
586 #else
587 THREAD_TIMER_ON (master, circuit->t_read, isis_receive, circuit,
588 circuit->fd);
589 #endif
590 return;
591 }
592
593 void
594 isis_circuit_down (struct isis_circuit *circuit)
595 {
596 /* Cancel all active threads -- FIXME: wrong place */
597 /* HT: Read thread if GNU_LINUX, TIMER thread otherwise. */
598 THREAD_OFF (circuit->t_read);
599 if (circuit->circ_type == CIRCUIT_T_BROADCAST)
600 {
601 THREAD_TIMER_OFF (circuit->u.bc.t_send_lan_hello[0]);
602 THREAD_TIMER_OFF (circuit->u.bc.t_send_lan_hello[1]);
603 THREAD_TIMER_OFF (circuit->u.bc.t_run_dr[0]);
604 THREAD_TIMER_OFF (circuit->u.bc.t_run_dr[1]);
605 }
606 else if (circuit->circ_type == CIRCUIT_T_P2P)
607 {
608 THREAD_TIMER_OFF (circuit->u.p2p.t_send_p2p_hello);
609 }
610
611 if (circuit->t_send_psnp[0]) {
612 THREAD_TIMER_OFF (circuit->t_send_psnp[0]);
613 }
614 if (circuit->t_send_psnp[1]) {
615 THREAD_TIMER_OFF (circuit->t_send_psnp[1]);
616 }
617 /* close the socket */
618 close (circuit->fd);
619
620 return;
621 }
622
623 void
624 circuit_update_nlpids (struct isis_circuit *circuit)
625 {
626 circuit->nlpids.count = 0;
627
628 if (circuit->ip_router)
629 {
630 circuit->nlpids.nlpids[0] = NLPID_IP;
631 circuit->nlpids.count++;
632 }
633 #ifdef HAVE_IPV6
634 if (circuit->ipv6_router)
635 {
636 circuit->nlpids.nlpids[circuit->nlpids.count] = NLPID_IPV6;
637 circuit->nlpids.count++;
638 }
639 #endif /* HAVE_IPV6 */
640 return;
641 }
642
643 int
644 isis_interface_config_write (struct vty *vty)
645 {
646
647 int write = 0;
648 struct listnode *node, *node2;
649 struct interface *ifp;
650 struct isis_area *area;
651 struct isis_circuit *c;
652 int i;
653
654 for (ALL_LIST_ELEMENTS_RO (iflist, node, ifp))
655 {
656 /* IF name */
657 vty_out (vty, "interface %s%s", ifp->name, VTY_NEWLINE);
658 write++;
659 /* IF desc */
660 if (ifp->desc)
661 {
662 vty_out (vty, " description %s%s", ifp->desc, VTY_NEWLINE);
663 write++;
664 }
665 /* ISIS Circuit */
666 for (ALL_LIST_ELEMENTS_RO (isis->area_list, node2, area))
667 {
668 c = circuit_lookup_by_ifp (ifp, area->circuit_list);
669 if (c)
670 {
671 if (c->ip_router)
672 {
673 vty_out (vty, " ip router isis %s%s", area->area_tag,
674 VTY_NEWLINE);
675 write++;
676 }
677 #ifdef HAVE_IPV6
678 if (c->ipv6_router)
679 {
680 vty_out (vty, " ipv6 router isis %s%s", area->area_tag,
681 VTY_NEWLINE);
682 write++;
683 }
684 #endif /* HAVE_IPV6 */
685
686 /* ISIS - circuit type */
687 if (c->circuit_is_type == IS_LEVEL_1)
688 {
689 vty_out (vty, " isis circuit-type level-1%s", VTY_NEWLINE);
690 write++;
691 }
692 else
693 {
694 if (c->circuit_is_type == IS_LEVEL_2)
695 {
696 vty_out (vty, " isis circuit-type level-2-only%s",
697 VTY_NEWLINE);
698 write++;
699 }
700 }
701
702 /* ISIS - CSNP interval - FIXME: compare to cisco */
703 if (c->csnp_interval[0] == c->csnp_interval[1])
704 {
705 if (c->csnp_interval[0] != CSNP_INTERVAL)
706 {
707 vty_out (vty, " isis csnp-interval %d%s",
708 c->csnp_interval[0], VTY_NEWLINE);
709 write++;
710 }
711 }
712 else
713 {
714 for (i = 0; i < 2; i++)
715 {
716 if (c->csnp_interval[1] != CSNP_INTERVAL)
717 {
718 vty_out (vty, " isis csnp-interval %d level-%d%s",
719 c->csnp_interval[1], i + 1, VTY_NEWLINE);
720 write++;
721 }
722 }
723 }
724
725 /* ISIS - Hello padding - Defaults to true so only display if false */
726 if (c->circ_type == CIRCUIT_T_BROADCAST && !c->u.bc.pad_hellos)
727 {
728 vty_out (vty, " no isis hello padding%s", VTY_NEWLINE);
729 write++;
730 }
731
732 /* ISIS - Hello interval - FIXME: compare to cisco */
733 if (c->hello_interval[0] == c->hello_interval[1])
734 {
735 if (c->hello_interval[0] != HELLO_INTERVAL)
736 {
737 vty_out (vty, " isis hello-interval %d%s",
738 c->hello_interval[0], VTY_NEWLINE);
739 write++;
740 }
741 }
742 else
743 {
744 for (i = 0; i < 2; i++)
745 {
746 if (c->hello_interval[i] != HELLO_INTERVAL)
747 {
748 if (c->hello_interval[i] == HELLO_MINIMAL)
749 {
750 vty_out (vty,
751 " isis hello-interval minimal level-%d%s",
752 i + 1, VTY_NEWLINE);
753 }
754 else
755 {
756 vty_out (vty, " isis hello-interval %d level-%d%s",
757 c->hello_interval[i], i + 1, VTY_NEWLINE);
758 }
759 write++;
760 }
761 }
762 }
763
764 /* ISIS - Hello Multiplier */
765 if (c->hello_multiplier[0] == c->hello_multiplier[1])
766 {
767 if (c->hello_multiplier[0] != HELLO_MULTIPLIER)
768 {
769 vty_out (vty, " isis hello-multiplier %d%s",
770 c->hello_multiplier[0], VTY_NEWLINE);
771 write++;
772 }
773 }
774 else
775 {
776 for (i = 0; i < 2; i++)
777 {
778 if (c->hello_multiplier[i] != HELLO_MULTIPLIER)
779 {
780 vty_out (vty, " isis hello-multiplier %d level-%d%s",
781 c->hello_multiplier[i], i + 1, VTY_NEWLINE);
782 write++;
783 }
784 }
785 }
786 /* ISIS - Priority */
787 if (c->circ_type == CIRCUIT_T_BROADCAST)
788 {
789 if (c->u.bc.priority[0] == c->u.bc.priority[1])
790 {
791 if (c->u.bc.priority[0] != DEFAULT_PRIORITY)
792 {
793 vty_out (vty, " isis priority %d%s",
794 c->u.bc.priority[0], VTY_NEWLINE);
795 write++;
796 }
797 }
798 else
799 {
800 for (i = 0; i < 2; i++)
801 {
802 if (c->u.bc.priority[i] != DEFAULT_PRIORITY)
803 {
804 vty_out (vty, " isis priority %d level-%d%s",
805 c->u.bc.priority[i], i + 1, VTY_NEWLINE);
806 write++;
807 }
808 }
809 }
810 }
811 /* ISIS - Metric */
812 if (c->te_metric[0] == c->te_metric[1])
813 {
814 if (c->te_metric[0] != DEFAULT_CIRCUIT_METRICS)
815 {
816 vty_out (vty, " isis metric %d%s", c->te_metric[0],
817 VTY_NEWLINE);
818 write++;
819 }
820 }
821 else
822 {
823 for (i = 0; i < 2; i++)
824 {
825 if (c->te_metric[i] != DEFAULT_CIRCUIT_METRICS)
826 {
827 vty_out (vty, " isis metric %d level-%d%s",
828 c->te_metric[i], i + 1, VTY_NEWLINE);
829 write++;
830 }
831 }
832 }
833
834 }
835 }
836 vty_out (vty, "!%s", VTY_NEWLINE);
837 }
838
839 return write;
840 }
841
842 DEFUN (ip_router_isis,
843 ip_router_isis_cmd,
844 "ip router isis WORD",
845 "Interface Internet Protocol config commands\n"
846 "IP router interface commands\n"
847 "IS-IS Routing for IP\n"
848 "Routing process tag\n")
849 {
850 struct isis_circuit *c;
851 struct interface *ifp;
852 struct isis_area *area;
853
854 ifp = (struct interface *) vty->index;
855 assert (ifp);
856
857 area = isis_area_lookup (argv[0]);
858
859 /* Prevent more than one circuit per interface */
860 if (area)
861 c = circuit_lookup_by_ifp (ifp, area->circuit_list);
862 else
863 c = NULL;
864 if (c && (ifp->info != NULL))
865 {
866 #ifdef HAVE_IPV6
867 if (c->ipv6_router == 0)
868 {
869 #endif /* HAVE_IPV6 */
870 /* FIXME: Find the way to warn only vty users. */
871 /* vty_out (vty, "ISIS circuit is already defined%s", VTY_NEWLINE); */
872 return CMD_WARNING;
873 #ifdef HAVE_IPV6
874 }
875 #endif /* HAVE_IPV6 */
876 }
877
878 /* this is here for ciscopability */
879 if (!area)
880 {
881 /* FIXME: Find the way to warn only vty users. */
882 /* vty_out (vty, "Can't find ISIS instance %s", VTY_NEWLINE); */
883 return CMD_WARNING;
884 }
885
886 if (!c)
887 {
888 c = circuit_lookup_by_ifp (ifp, isis->init_circ_list);
889 c = isis_csm_state_change (ISIS_ENABLE, c, area);
890 c->interface = ifp; /* this is automatic */
891 ifp->info = c; /* hardly related to the FSM */
892 }
893
894 if (!c)
895 return CMD_WARNING;
896
897 c->ip_router = 1;
898 area->ip_circuits++;
899 circuit_update_nlpids (c);
900
901 vty->node = INTERFACE_NODE;
902
903 return CMD_SUCCESS;
904 }
905
906 DEFUN (no_ip_router_isis,
907 no_ip_router_isis_cmd,
908 "no ip router isis WORD",
909 NO_STR
910 "Interface Internet Protocol config commands\n"
911 "IP router interface commands\n"
912 "IS-IS Routing for IP\n"
913 "Routing process tag\n")
914 {
915 struct isis_circuit *circuit = NULL;
916 struct interface *ifp;
917 struct isis_area *area;
918 struct listnode *node;
919
920 ifp = (struct interface *) vty->index;
921 assert (ifp);
922
923 area = isis_area_lookup (argv[0]);
924 if (!area)
925 {
926 vty_out (vty, "Can't find ISIS instance %s", VTY_NEWLINE);
927 return CMD_WARNING;
928 }
929 for (ALL_LIST_ELEMENTS_RO (area->circuit_list, node, circuit))
930 if (circuit->interface == ifp)
931 break;
932 if (!circuit)
933 {
934 vty_out (vty, "Can't find ISIS interface %s", VTY_NEWLINE);
935 return CMD_WARNING;
936 }
937 circuit->ip_router = 0;
938 area->ip_circuits--;
939 #ifdef HAVE_IPV6
940 if (circuit->ipv6_router == 0)
941 #endif
942 isis_csm_state_change (ISIS_DISABLE, circuit, area);
943
944 return CMD_SUCCESS;
945 }
946
947 DEFUN (isis_circuit_type,
948 isis_circuit_type_cmd,
949 "isis circuit-type (level-1|level-1-2|level-2-only)",
950 "IS-IS commands\n"
951 "Configure circuit type for interface\n"
952 "Level-1 only adjacencies are formed\n"
953 "Level-1-2 adjacencies are formed\n"
954 "Level-2 only adjacencies are formed\n")
955 {
956 struct isis_circuit *circuit;
957 struct interface *ifp;
958 int circuit_t;
959 int is_type;
960
961 ifp = vty->index;
962 circuit = ifp->info;
963 /* UGLY - will remove l8r */
964 if (circuit == NULL)
965 {
966 return CMD_WARNING;
967 }
968
969 /* XXX what to do when ip_router_isis is not executed */
970 if (circuit->area == NULL)
971 return CMD_WARNING;
972
973 assert (circuit);
974
975 circuit_t = string2circuit_t (argv[0]);
976
977 if (!circuit_t)
978 {
979 vty_out (vty, "Unknown circuit-type %s", VTY_NEWLINE);
980 return CMD_SUCCESS;
981 }
982
983 is_type = circuit->area->is_type;
984 if (is_type == IS_LEVEL_1_AND_2 || is_type == circuit_t)
985 isis_event_circuit_type_change (circuit, circuit_t);
986 else
987 {
988 vty_out (vty, "invalid circuit level for area %s.%s",
989 circuit->area->area_tag, VTY_NEWLINE);
990 }
991
992 return CMD_SUCCESS;
993 }
994
995 DEFUN (no_isis_circuit_type,
996 no_isis_circuit_type_cmd,
997 "no isis circuit-type (level-1|level-1-2|level-2-only)",
998 NO_STR
999 "IS-IS commands\n"
1000 "Configure circuit type for interface\n"
1001 "Level-1 only adjacencies are formed\n"
1002 "Level-1-2 adjacencies are formed\n"
1003 "Level-2 only adjacencies are formed\n")
1004 {
1005 struct isis_circuit *circuit;
1006 struct interface *ifp;
1007
1008 ifp = vty->index;
1009 circuit = ifp->info;
1010 if (circuit == NULL)
1011 {
1012 return CMD_WARNING;
1013 }
1014
1015 assert (circuit);
1016
1017 /*
1018 * Set the circuits level to its default value which is that of the area
1019 */
1020 isis_event_circuit_type_change (circuit, circuit->area->is_type);
1021
1022 return CMD_SUCCESS;
1023 }
1024
1025 DEFUN (isis_passwd,
1026 isis_passwd_cmd,
1027 "isis password WORD",
1028 "IS-IS commands\n"
1029 "Configure the authentication password for interface\n"
1030 "Password\n")
1031 {
1032 struct isis_circuit *circuit;
1033 struct interface *ifp;
1034 int len;
1035
1036 ifp = vty->index;
1037 circuit = ifp->info;
1038 if (circuit == NULL)
1039 {
1040 return CMD_WARNING;
1041 }
1042
1043 len = strlen (argv[0]);
1044 if (len > 254)
1045 {
1046 vty_out (vty, "Too long circuit password (>254)%s", VTY_NEWLINE);
1047 return CMD_WARNING;
1048 }
1049 circuit->passwd.len = len;
1050 circuit->passwd.type = ISIS_PASSWD_TYPE_CLEARTXT;
1051 strncpy ((char *)circuit->passwd.passwd, argv[0], 255);
1052
1053 return CMD_SUCCESS;
1054 }
1055
1056 DEFUN (no_isis_passwd,
1057 no_isis_passwd_cmd,
1058 "no isis password",
1059 NO_STR
1060 "IS-IS commands\n"
1061 "Configure the authentication password for interface\n")
1062 {
1063 struct isis_circuit *circuit;
1064 struct interface *ifp;
1065
1066 ifp = vty->index;
1067 circuit = ifp->info;
1068 if (circuit == NULL)
1069 {
1070 return CMD_WARNING;
1071 }
1072
1073 memset (&circuit->passwd, 0, sizeof (struct isis_passwd));
1074
1075 return CMD_SUCCESS;
1076 }
1077
1078
1079 DEFUN (isis_priority,
1080 isis_priority_cmd,
1081 "isis priority <0-127>",
1082 "IS-IS commands\n"
1083 "Set priority for Designated Router election\n"
1084 "Priority value\n")
1085 {
1086 struct isis_circuit *circuit;
1087 struct interface *ifp;
1088 int prio;
1089
1090 ifp = vty->index;
1091 circuit = ifp->info;
1092 if (circuit == NULL)
1093 {
1094 return CMD_WARNING;
1095 }
1096 assert (circuit);
1097
1098 prio = atoi (argv[0]);
1099
1100 circuit->u.bc.priority[0] = prio;
1101 circuit->u.bc.priority[1] = prio;
1102
1103 return CMD_SUCCESS;
1104 }
1105
1106 DEFUN (no_isis_priority,
1107 no_isis_priority_cmd,
1108 "no isis priority",
1109 NO_STR
1110 "IS-IS commands\n"
1111 "Set priority for Designated Router election\n")
1112 {
1113 struct isis_circuit *circuit;
1114 struct interface *ifp;
1115
1116 ifp = vty->index;
1117 circuit = ifp->info;
1118 if (circuit == NULL)
1119 {
1120 return CMD_WARNING;
1121 }
1122 assert (circuit);
1123
1124 circuit->u.bc.priority[0] = DEFAULT_PRIORITY;
1125 circuit->u.bc.priority[1] = DEFAULT_PRIORITY;
1126
1127 return CMD_SUCCESS;
1128 }
1129
1130 ALIAS (no_isis_priority,
1131 no_isis_priority_arg_cmd,
1132 "no isis priority <0-127>",
1133 NO_STR
1134 "IS-IS commands\n"
1135 "Set priority for Designated Router election\n"
1136 "Priority value\n")
1137
1138 DEFUN (isis_priority_l1,
1139 isis_priority_l1_cmd,
1140 "isis priority <0-127> level-1",
1141 "IS-IS commands\n"
1142 "Set priority for Designated Router election\n"
1143 "Priority value\n"
1144 "Specify priority for level-1 routing\n")
1145 {
1146 struct isis_circuit *circuit;
1147 struct interface *ifp;
1148 int prio;
1149
1150 ifp = vty->index;
1151 circuit = ifp->info;
1152 if (circuit == NULL)
1153 {
1154 return CMD_WARNING;
1155 }
1156 assert (circuit);
1157
1158 prio = atoi (argv[0]);
1159
1160 circuit->u.bc.priority[0] = prio;
1161
1162 return CMD_SUCCESS;
1163 }
1164
1165 DEFUN (no_isis_priority_l1,
1166 no_isis_priority_l1_cmd,
1167 "no isis priority level-1",
1168 NO_STR
1169 "IS-IS commands\n"
1170 "Set priority for Designated Router election\n"
1171 "Specify priority for level-1 routing\n")
1172 {
1173 struct isis_circuit *circuit;
1174 struct interface *ifp;
1175
1176 ifp = vty->index;
1177 circuit = ifp->info;
1178 if (circuit == NULL)
1179 {
1180 return CMD_WARNING;
1181 }
1182 assert (circuit);
1183
1184 circuit->u.bc.priority[0] = DEFAULT_PRIORITY;
1185
1186 return CMD_SUCCESS;
1187 }
1188
1189 ALIAS (no_isis_priority_l1,
1190 no_isis_priority_l1_arg_cmd,
1191 "no isis priority <0-127> level-1",
1192 NO_STR
1193 "IS-IS commands\n"
1194 "Set priority for Designated Router election\n"
1195 "Priority value\n"
1196 "Specify priority for level-1 routing\n")
1197
1198 DEFUN (isis_priority_l2,
1199 isis_priority_l2_cmd,
1200 "isis priority <0-127> level-2",
1201 "IS-IS commands\n"
1202 "Set priority for Designated Router election\n"
1203 "Priority value\n"
1204 "Specify priority for level-2 routing\n")
1205 {
1206 struct isis_circuit *circuit;
1207 struct interface *ifp;
1208 int prio;
1209
1210 ifp = vty->index;
1211 circuit = ifp->info;
1212 if (circuit == NULL)
1213 {
1214 return CMD_WARNING;
1215 }
1216 assert (circuit);
1217
1218 prio = atoi (argv[0]);
1219
1220 circuit->u.bc.priority[1] = prio;
1221
1222 return CMD_SUCCESS;
1223 }
1224
1225 DEFUN (no_isis_priority_l2,
1226 no_isis_priority_l2_cmd,
1227 "no isis priority level-2",
1228 NO_STR
1229 "IS-IS commands\n"
1230 "Set priority for Designated Router election\n"
1231 "Specify priority for level-2 routing\n")
1232 {
1233 struct isis_circuit *circuit;
1234 struct interface *ifp;
1235
1236 ifp = vty->index;
1237 circuit = ifp->info;
1238 if (circuit == NULL)
1239 {
1240 return CMD_WARNING;
1241 }
1242 assert (circuit);
1243
1244 circuit->u.bc.priority[1] = DEFAULT_PRIORITY;
1245
1246 return CMD_SUCCESS;
1247 }
1248
1249 ALIAS (no_isis_priority_l2,
1250 no_isis_priority_l2_arg_cmd,
1251 "no isis priority <0-127> level-2",
1252 NO_STR
1253 "IS-IS commands\n"
1254 "Set priority for Designated Router election\n"
1255 "Priority value\n"
1256 "Specify priority for level-2 routing\n")
1257
1258 /* Metric command */
1259 DEFUN (isis_metric,
1260 isis_metric_cmd,
1261 "isis metric <0-16777215>",
1262 "IS-IS commands\n"
1263 "Set default metric for circuit\n"
1264 "Default metric value\n")
1265 {
1266 struct isis_circuit *circuit;
1267 struct interface *ifp;
1268 int met;
1269
1270 ifp = vty->index;
1271 circuit = ifp->info;
1272 if (circuit == NULL)
1273 {
1274 return CMD_WARNING;
1275 }
1276 assert (circuit);
1277
1278 met = atoi (argv[0]);
1279
1280 circuit->te_metric[0] = met;
1281 circuit->te_metric[1] = met;
1282
1283 if (met > 63)
1284 met = 63;
1285
1286 circuit->metrics[0].metric_default = met;
1287 circuit->metrics[1].metric_default = met;
1288
1289 return CMD_SUCCESS;
1290 }
1291
1292 DEFUN (no_isis_metric,
1293 no_isis_metric_cmd,
1294 "no isis metric",
1295 NO_STR
1296 "IS-IS commands\n"
1297 "Set default metric for circuit\n")
1298 {
1299 struct isis_circuit *circuit;
1300 struct interface *ifp;
1301
1302 ifp = vty->index;
1303 circuit = ifp->info;
1304 if (circuit == NULL)
1305 {
1306 return CMD_WARNING;
1307 }
1308 assert (circuit);
1309
1310 circuit->te_metric[0] = DEFAULT_CIRCUIT_METRICS;
1311 circuit->te_metric[1] = DEFAULT_CIRCUIT_METRICS;
1312 circuit->metrics[0].metric_default = DEFAULT_CIRCUIT_METRICS;
1313 circuit->metrics[1].metric_default = DEFAULT_CIRCUIT_METRICS;
1314
1315 return CMD_SUCCESS;
1316 }
1317
1318 ALIAS (no_isis_metric,
1319 no_isis_metric_arg_cmd,
1320 "no isis metric <0-16777215>",
1321 NO_STR
1322 "IS-IS commands\n"
1323 "Set default metric for circuit\n"
1324 "Default metric value\n")
1325
1326 /* end of metrics */
1327 DEFUN (isis_hello_interval,
1328 isis_hello_interval_cmd,
1329 "isis hello-interval (<1-65535>|minimal)",
1330 "IS-IS commands\n"
1331 "Set Hello interval\n"
1332 "Hello interval value\n"
1333 "Holdtime 1 seconds, interval depends on multiplier\n")
1334 {
1335 struct isis_circuit *circuit;
1336 struct interface *ifp;
1337 int interval;
1338 char c;
1339
1340 ifp = vty->index;
1341 circuit = ifp->info;
1342 if (circuit == NULL)
1343 {
1344 return CMD_WARNING;
1345 }
1346 assert (circuit);
1347 c = *argv[0];
1348 if (isdigit ((int) c))
1349 {
1350 interval = atoi (argv[0]);
1351 }
1352 else
1353 interval = HELLO_MINIMAL; /* FIXME: should be calculated */
1354
1355 circuit->hello_interval[0] = (u_int16_t) interval;
1356 circuit->hello_interval[1] = (u_int16_t) interval;
1357
1358 return CMD_SUCCESS;
1359 }
1360
1361 DEFUN (no_isis_hello_interval,
1362 no_isis_hello_interval_cmd,
1363 "no isis hello-interval",
1364 NO_STR
1365 "IS-IS commands\n"
1366 "Set Hello interval\n")
1367 {
1368 struct isis_circuit *circuit;
1369 struct interface *ifp;
1370
1371 ifp = vty->index;
1372 circuit = ifp->info;
1373 if (circuit == NULL)
1374 {
1375 return CMD_WARNING;
1376 }
1377 assert (circuit);
1378
1379
1380 circuit->hello_interval[0] = HELLO_INTERVAL; /* Default is 1 sec. */
1381 circuit->hello_interval[1] = HELLO_INTERVAL;
1382
1383 return CMD_SUCCESS;
1384 }
1385
1386 ALIAS (no_isis_hello_interval,
1387 no_isis_hello_interval_arg_cmd,
1388 "no isis hello-interval (<1-65535>|minimal)",
1389 NO_STR
1390 "IS-IS commands\n"
1391 "Set Hello interval\n"
1392 "Hello interval value\n"
1393 "Holdtime 1 second, interval depends on multiplier\n")
1394
1395 DEFUN (isis_hello_interval_l1,
1396 isis_hello_interval_l1_cmd,
1397 "isis hello-interval (<1-65535>|minimal) level-1",
1398 "IS-IS commands\n"
1399 "Set Hello interval\n"
1400 "Hello interval value\n"
1401 "Holdtime 1 second, interval depends on multiplier\n"
1402 "Specify hello-interval for level-1 IIHs\n")
1403 {
1404 struct isis_circuit *circuit;
1405 struct interface *ifp;
1406 long interval;
1407 char c;
1408
1409 ifp = vty->index;
1410 circuit = ifp->info;
1411 if (circuit == NULL)
1412 {
1413 return CMD_WARNING;
1414 }
1415 assert (circuit);
1416
1417 c = *argv[0];
1418 if (isdigit ((int) c))
1419 {
1420 interval = atoi (argv[0]);
1421 }
1422 else
1423 interval = HELLO_MINIMAL;
1424
1425 circuit->hello_interval[0] = (u_int16_t) interval;
1426
1427 return CMD_SUCCESS;
1428 }
1429
1430 DEFUN (no_isis_hello_interval_l1,
1431 no_isis_hello_interval_l1_cmd,
1432 "no isis hello-interval level-1",
1433 NO_STR
1434 "IS-IS commands\n"
1435 "Set Hello interval\n"
1436 "Specify hello-interval for level-1 IIHs\n")
1437 {
1438 struct isis_circuit *circuit;
1439 struct interface *ifp;
1440
1441 ifp = vty->index;
1442 circuit = ifp->info;
1443 if (circuit == NULL)
1444 {
1445 return CMD_WARNING;
1446 }
1447 assert (circuit);
1448
1449
1450 circuit->hello_interval[0] = HELLO_INTERVAL; /* Default is 1 sec. */
1451
1452 return CMD_SUCCESS;
1453 }
1454
1455 ALIAS (no_isis_hello_interval_l1,
1456 no_isis_hello_interval_l1_arg_cmd,
1457 "no isis hello-interval (<1-65535>|minimal) level-1",
1458 NO_STR
1459 "IS-IS commands\n"
1460 "Set Hello interval\n"
1461 "Hello interval value\n"
1462 "Holdtime 1 second, interval depends on multiplier\n"
1463 "Specify hello-interval for level-1 IIHs\n")
1464
1465 DEFUN (isis_hello_interval_l2,
1466 isis_hello_interval_l2_cmd,
1467 "isis hello-interval (<1-65535>|minimal) level-2",
1468 "IS-IS commands\n"
1469 "Set Hello interval\n"
1470 "Hello interval value\n"
1471 "Holdtime 1 second, interval depends on multiplier\n"
1472 "Specify hello-interval for level-2 IIHs\n")
1473 {
1474 struct isis_circuit *circuit;
1475 struct interface *ifp;
1476 long interval;
1477 char c;
1478
1479 ifp = vty->index;
1480 circuit = ifp->info;
1481 if (circuit == NULL)
1482 {
1483 return CMD_WARNING;
1484 }
1485 assert (circuit);
1486
1487 c = *argv[0];
1488 if (isdigit ((int) c))
1489 {
1490 interval = atoi (argv[0]);
1491 }
1492 else
1493 interval = HELLO_MINIMAL;
1494
1495 circuit->hello_interval[1] = (u_int16_t) interval;
1496
1497 return CMD_SUCCESS;
1498 }
1499
1500 DEFUN (no_isis_hello_interval_l2,
1501 no_isis_hello_interval_l2_cmd,
1502 "no isis hello-interval level-2",
1503 NO_STR
1504 "IS-IS commands\n"
1505 "Set Hello interval\n"
1506 "Specify hello-interval for level-2 IIHs\n")
1507 {
1508 struct isis_circuit *circuit;
1509 struct interface *ifp;
1510
1511 ifp = vty->index;
1512 circuit = ifp->info;
1513 if (circuit == NULL)
1514 {
1515 return CMD_WARNING;
1516 }
1517 assert (circuit);
1518
1519
1520 circuit->hello_interval[1] = HELLO_INTERVAL; /* Default is 1 sec. */
1521
1522 return CMD_SUCCESS;
1523 }
1524
1525 ALIAS (no_isis_hello_interval_l2,
1526 no_isis_hello_interval_l2_arg_cmd,
1527 "no isis hello-interval (<1-65535>|minimal) level-2",
1528 NO_STR
1529 "IS-IS commands\n"
1530 "Set Hello interval\n"
1531 "Hello interval value\n"
1532 "Holdtime 1 second, interval depends on multiplier\n"
1533 "Specify hello-interval for level-2 IIHs\n")
1534
1535 DEFUN (isis_hello_multiplier,
1536 isis_hello_multiplier_cmd,
1537 "isis hello-multiplier <3-1000>",
1538 "IS-IS commands\n"
1539 "Set multiplier for Hello holding time\n"
1540 "Hello multiplier value\n")
1541 {
1542 struct isis_circuit *circuit;
1543 struct interface *ifp;
1544 int mult;
1545
1546 ifp = vty->index;
1547 circuit = ifp->info;
1548 if (circuit == NULL)
1549 {
1550 return CMD_WARNING;
1551 }
1552 assert (circuit);
1553
1554 mult = atoi (argv[0]);
1555
1556 circuit->hello_multiplier[0] = (u_int16_t) mult;
1557 circuit->hello_multiplier[1] = (u_int16_t) mult;
1558
1559 return CMD_SUCCESS;
1560 }
1561
1562 DEFUN (no_isis_hello_multiplier,
1563 no_isis_hello_multiplier_cmd,
1564 "no isis hello-multiplier",
1565 NO_STR
1566 "IS-IS commands\n"
1567 "Set multiplier for Hello holding time\n")
1568 {
1569 struct isis_circuit *circuit;
1570 struct interface *ifp;
1571
1572 ifp = vty->index;
1573 circuit = ifp->info;
1574 if (circuit == NULL)
1575 {
1576 return CMD_WARNING;
1577 }
1578 assert (circuit);
1579
1580 circuit->hello_multiplier[0] = HELLO_MULTIPLIER;
1581 circuit->hello_multiplier[1] = HELLO_MULTIPLIER;
1582
1583 return CMD_SUCCESS;
1584 }
1585
1586 ALIAS (no_isis_hello_multiplier,
1587 no_isis_hello_multiplier_arg_cmd,
1588 "no isis hello-multiplier <3-1000>",
1589 NO_STR
1590 "IS-IS commands\n"
1591 "Set multiplier for Hello holding time\n"
1592 "Hello multiplier value\n")
1593
1594 DEFUN (isis_hello_multiplier_l1,
1595 isis_hello_multiplier_l1_cmd,
1596 "isis hello-multiplier <3-1000> level-1",
1597 "IS-IS commands\n"
1598 "Set multiplier for Hello holding time\n"
1599 "Hello multiplier value\n"
1600 "Specify hello multiplier for level-1 IIHs\n")
1601 {
1602 struct isis_circuit *circuit;
1603 struct interface *ifp;
1604 int mult;
1605
1606 ifp = vty->index;
1607 circuit = ifp->info;
1608 if (circuit == NULL)
1609 {
1610 return CMD_WARNING;
1611 }
1612 assert (circuit);
1613
1614 mult = atoi (argv[0]);
1615
1616 circuit->hello_multiplier[0] = (u_int16_t) mult;
1617
1618 return CMD_SUCCESS;
1619 }
1620
1621 DEFUN (no_isis_hello_multiplier_l1,
1622 no_isis_hello_multiplier_l1_cmd,
1623 "no isis hello-multiplier level-1",
1624 NO_STR
1625 "IS-IS commands\n"
1626 "Set multiplier for Hello holding time\n"
1627 "Specify hello multiplier for level-1 IIHs\n")
1628 {
1629 struct isis_circuit *circuit;
1630 struct interface *ifp;
1631
1632 ifp = vty->index;
1633 circuit = ifp->info;
1634 if (circuit == NULL)
1635 {
1636 return CMD_WARNING;
1637 }
1638 assert (circuit);
1639
1640 circuit->hello_multiplier[0] = HELLO_MULTIPLIER;
1641
1642 return CMD_SUCCESS;
1643 }
1644
1645 ALIAS (no_isis_hello_multiplier_l1,
1646 no_isis_hello_multiplier_l1_arg_cmd,
1647 "no isis hello-multiplier <3-1000> level-1",
1648 NO_STR
1649 "IS-IS commands\n"
1650 "Set multiplier for Hello holding time\n"
1651 "Hello multiplier value\n"
1652 "Specify hello multiplier for level-1 IIHs\n")
1653
1654 DEFUN (isis_hello_multiplier_l2,
1655 isis_hello_multiplier_l2_cmd,
1656 "isis hello-multiplier <3-1000> level-2",
1657 "IS-IS commands\n"
1658 "Set multiplier for Hello holding time\n"
1659 "Hello multiplier value\n"
1660 "Specify hello multiplier for level-2 IIHs\n")
1661 {
1662 struct isis_circuit *circuit;
1663 struct interface *ifp;
1664 int mult;
1665
1666 ifp = vty->index;
1667 circuit = ifp->info;
1668 if (circuit == NULL)
1669 {
1670 return CMD_WARNING;
1671 }
1672 assert (circuit);
1673
1674 mult = atoi (argv[0]);
1675
1676 circuit->hello_multiplier[1] = (u_int16_t) mult;
1677
1678 return CMD_SUCCESS;
1679 }
1680
1681 DEFUN (no_isis_hello_multiplier_l2,
1682 no_isis_hello_multiplier_l2_cmd,
1683 "no isis hello-multiplier level-2",
1684 NO_STR
1685 "IS-IS commands\n"
1686 "Set multiplier for Hello holding time\n"
1687 "Specify hello multiplier for level-2 IIHs\n")
1688 {
1689 struct isis_circuit *circuit;
1690 struct interface *ifp;
1691
1692 ifp = vty->index;
1693 circuit = ifp->info;
1694 if (circuit == NULL)
1695 {
1696 return CMD_WARNING;
1697 }
1698 assert (circuit);
1699
1700 circuit->hello_multiplier[1] = HELLO_MULTIPLIER;
1701
1702 return CMD_SUCCESS;
1703 }
1704
1705 ALIAS (no_isis_hello_multiplier_l2,
1706 no_isis_hello_multiplier_l2_arg_cmd,
1707 "no isis hello-multiplier <3-1000> level-2",
1708 NO_STR
1709 "IS-IS commands\n"
1710 "Set multiplier for Hello holding time\n"
1711 "Hello multiplier value\n"
1712 "Specify hello multiplier for level-2 IIHs\n")
1713
1714 DEFUN (isis_hello,
1715 isis_hello_cmd,
1716 "isis hello padding",
1717 "IS-IS commands\n"
1718 "Add padding to IS-IS hello packets\n"
1719 "Pad hello packets\n"
1720 "<cr>\n")
1721 {
1722 struct interface *ifp;
1723 struct isis_circuit *circuit;
1724
1725 ifp = vty->index;
1726 circuit = ifp->info;
1727 if (circuit == NULL)
1728 {
1729 return CMD_WARNING;
1730 }
1731 assert (circuit);
1732
1733 circuit->u.bc.pad_hellos = 1;
1734
1735 return CMD_SUCCESS;
1736 }
1737
1738 DEFUN (no_isis_hello,
1739 no_isis_hello_cmd,
1740 "no isis hello padding",
1741 NO_STR
1742 "IS-IS commands\n"
1743 "Add padding to IS-IS hello packets\n"
1744 "Pad hello packets\n"
1745 "<cr>\n")
1746 {
1747 struct isis_circuit *circuit;
1748 struct interface *ifp;
1749
1750 ifp = vty->index;
1751 circuit = ifp->info;
1752 if (circuit == NULL)
1753 {
1754 return CMD_WARNING;
1755 }
1756 assert (circuit);
1757
1758 circuit->u.bc.pad_hellos = 0;
1759
1760 return CMD_SUCCESS;
1761 }
1762
1763 DEFUN (csnp_interval,
1764 csnp_interval_cmd,
1765 "isis csnp-interval <0-65535>",
1766 "IS-IS commands\n"
1767 "Set CSNP interval in seconds\n"
1768 "CSNP interval value\n")
1769 {
1770 struct isis_circuit *circuit;
1771 struct interface *ifp;
1772 unsigned long interval;
1773
1774 ifp = vty->index;
1775 circuit = ifp->info;
1776 if (circuit == NULL)
1777 {
1778 return CMD_WARNING;
1779 }
1780 assert (circuit);
1781
1782 interval = atol (argv[0]);
1783
1784 circuit->csnp_interval[0] = (u_int16_t) interval;
1785 circuit->csnp_interval[1] = (u_int16_t) interval;
1786
1787 return CMD_SUCCESS;
1788 }
1789
1790 DEFUN (no_csnp_interval,
1791 no_csnp_interval_cmd,
1792 "no isis csnp-interval",
1793 NO_STR
1794 "IS-IS commands\n"
1795 "Set CSNP interval in seconds\n")
1796 {
1797 struct isis_circuit *circuit;
1798 struct interface *ifp;
1799
1800 ifp = vty->index;
1801 circuit = ifp->info;
1802 if (circuit == NULL)
1803 {
1804 return CMD_WARNING;
1805 }
1806 assert (circuit);
1807
1808 circuit->csnp_interval[0] = CSNP_INTERVAL;
1809 circuit->csnp_interval[1] = CSNP_INTERVAL;
1810
1811 return CMD_SUCCESS;
1812 }
1813
1814 ALIAS (no_csnp_interval,
1815 no_csnp_interval_arg_cmd,
1816 "no isis csnp-interval <0-65535>",
1817 NO_STR
1818 "IS-IS commands\n"
1819 "Set CSNP interval in seconds\n"
1820 "CSNP interval value\n")
1821
1822 DEFUN (csnp_interval_l1,
1823 csnp_interval_l1_cmd,
1824 "isis csnp-interval <0-65535> level-1",
1825 "IS-IS commands\n"
1826 "Set CSNP interval in seconds\n"
1827 "CSNP interval value\n"
1828 "Specify interval for level-1 CSNPs\n")
1829 {
1830 struct isis_circuit *circuit;
1831 struct interface *ifp;
1832 unsigned long interval;
1833
1834 ifp = vty->index;
1835 circuit = ifp->info;
1836 if (circuit == NULL)
1837 {
1838 return CMD_WARNING;
1839 }
1840 assert (circuit);
1841
1842 interval = atol (argv[0]);
1843
1844 circuit->csnp_interval[0] = (u_int16_t) interval;
1845
1846 return CMD_SUCCESS;
1847 }
1848
1849 DEFUN (no_csnp_interval_l1,
1850 no_csnp_interval_l1_cmd,
1851 "no isis csnp-interval level-1",
1852 NO_STR
1853 "IS-IS commands\n"
1854 "Set CSNP interval in seconds\n"
1855 "Specify interval for level-1 CSNPs\n")
1856 {
1857 struct isis_circuit *circuit;
1858 struct interface *ifp;
1859
1860 ifp = vty->index;
1861 circuit = ifp->info;
1862 if (circuit == NULL)
1863 {
1864 return CMD_WARNING;
1865 }
1866 assert (circuit);
1867
1868 circuit->csnp_interval[0] = CSNP_INTERVAL;
1869
1870 return CMD_SUCCESS;
1871 }
1872
1873 ALIAS (no_csnp_interval_l1,
1874 no_csnp_interval_l1_arg_cmd,
1875 "no isis csnp-interval <0-65535> level-1",
1876 NO_STR
1877 "IS-IS commands\n"
1878 "Set CSNP interval in seconds\n"
1879 "CSNP interval value\n"
1880 "Specify interval for level-1 CSNPs\n")
1881
1882 DEFUN (csnp_interval_l2,
1883 csnp_interval_l2_cmd,
1884 "isis csnp-interval <0-65535> level-2",
1885 "IS-IS commands\n"
1886 "Set CSNP interval in seconds\n"
1887 "CSNP interval value\n"
1888 "Specify interval for level-2 CSNPs\n")
1889 {
1890 struct isis_circuit *circuit;
1891 struct interface *ifp;
1892 unsigned long interval;
1893
1894 ifp = vty->index;
1895 circuit = ifp->info;
1896 if (circuit == NULL)
1897 {
1898 return CMD_WARNING;
1899 }
1900 assert (circuit);
1901
1902 interval = atol (argv[0]);
1903
1904 circuit->csnp_interval[1] = (u_int16_t) interval;
1905
1906 return CMD_SUCCESS;
1907 }
1908
1909 DEFUN (no_csnp_interval_l2,
1910 no_csnp_interval_l2_cmd,
1911 "no isis csnp-interval level-2",
1912 NO_STR
1913 "IS-IS commands\n"
1914 "Set CSNP interval in seconds\n"
1915 "Specify interval for level-2 CSNPs\n")
1916 {
1917 struct isis_circuit *circuit;
1918 struct interface *ifp;
1919
1920 ifp = vty->index;
1921 circuit = ifp->info;
1922 if (circuit == NULL)
1923 {
1924 return CMD_WARNING;
1925 }
1926 assert (circuit);
1927
1928 circuit->csnp_interval[1] = CSNP_INTERVAL;
1929
1930 return CMD_SUCCESS;
1931 }
1932
1933 ALIAS (no_csnp_interval_l2,
1934 no_csnp_interval_l2_arg_cmd,
1935 "no isis csnp-interval <0-65535> level-2",
1936 NO_STR
1937 "IS-IS commands\n"
1938 "Set CSNP interval in seconds\n"
1939 "CSNP interval value\n"
1940 "Specify interval for level-2 CSNPs\n")
1941
1942 #ifdef HAVE_IPV6
1943 DEFUN (ipv6_router_isis,
1944 ipv6_router_isis_cmd,
1945 "ipv6 router isis WORD",
1946 "IPv6 interface subcommands\n"
1947 "IPv6 Router interface commands\n"
1948 "IS-IS Routing for IPv6\n"
1949 "Routing process tag\n")
1950 {
1951 struct isis_circuit *c;
1952 struct interface *ifp;
1953 struct isis_area *area;
1954
1955 ifp = (struct interface *) vty->index;
1956 assert (ifp);
1957
1958 area = isis_area_lookup (argv[0]);
1959
1960 /* Prevent more than one circuit per interface */
1961 if (area)
1962 c = circuit_lookup_by_ifp (ifp, area->circuit_list);
1963 else
1964 c = NULL;
1965
1966 if (c && (ifp->info != NULL))
1967 {
1968 if (c->ipv6_router == 1)
1969 {
1970 vty_out (vty, "ISIS circuit is already defined for IPv6%s",
1971 VTY_NEWLINE);
1972 return CMD_WARNING;
1973 }
1974 }
1975
1976 /* this is here for ciscopability */
1977 if (!area)
1978 {
1979 vty_out (vty, "Can't find ISIS instance %s", VTY_NEWLINE);
1980 return CMD_WARNING;
1981 }
1982
1983 if (!c)
1984 {
1985 c = circuit_lookup_by_ifp (ifp, isis->init_circ_list);
1986 c = isis_csm_state_change (ISIS_ENABLE, c, area);
1987 c->interface = ifp;
1988 ifp->info = c;
1989 }
1990
1991 if (!c)
1992 return CMD_WARNING;
1993
1994 c->ipv6_router = 1;
1995 area->ipv6_circuits++;
1996 circuit_update_nlpids (c);
1997
1998 vty->node = INTERFACE_NODE;
1999
2000 return CMD_SUCCESS;
2001 }
2002
2003 DEFUN (no_ipv6_router_isis,
2004 no_ipv6_router_isis_cmd,
2005 "no ipv6 router isis WORD",
2006 NO_STR
2007 "IPv6 interface subcommands\n"
2008 "IPv6 Router interface commands\n"
2009 "IS-IS Routing for IPv6\n"
2010 "Routing process tag\n")
2011 {
2012 struct isis_circuit *c;
2013 struct interface *ifp;
2014 struct isis_area *area;
2015
2016 ifp = (struct interface *) vty->index;
2017 /* UGLY - will remove l8r
2018 if (circuit == NULL) {
2019 return CMD_WARNING;
2020 } */
2021 assert (ifp);
2022
2023 area = isis_area_lookup (argv[0]);
2024 if (!area)
2025 {
2026 vty_out (vty, "Can't find ISIS instance %s", VTY_NEWLINE);
2027 return CMD_WARNING;
2028 }
2029
2030 c = circuit_lookup_by_ifp (ifp, area->circuit_list);
2031 if (!c)
2032 return CMD_WARNING;
2033
2034 c->ipv6_router = 0;
2035 area->ipv6_circuits--;
2036 if (c->ip_router == 0)
2037 isis_csm_state_change (ISIS_DISABLE, c, area);
2038
2039 return CMD_SUCCESS;
2040 }
2041 #endif /* HAVE_IPV6 */
2042
2043 static struct cmd_node interface_node = {
2044 INTERFACE_NODE,
2045 "%s(config-if)# ",
2046 1,
2047 };
2048
2049 int
2050 isis_if_new_hook (struct interface *ifp)
2051 {
2052 /* FIXME: Discuss if the circuit should be created here
2053 ifp->info = XMALLOC (MTYPE_ISIS_IF_INFO, sizeof (struct isis_if_info)); */
2054 ifp->info = NULL;
2055 return 0;
2056 }
2057
2058 int
2059 isis_if_delete_hook (struct interface *ifp)
2060 {
2061 /* FIXME: Discuss if the circuit should be created here
2062 XFREE (MTYPE_ISIS_IF_INFO, ifp->info);*/
2063 ifp->info = NULL;
2064 return 0;
2065 }
2066
2067 void
2068 isis_circuit_init ()
2069 {
2070 /* Initialize Zebra interface data structure */
2071 if_init ();
2072 if_add_hook (IF_NEW_HOOK, isis_if_new_hook);
2073 if_add_hook (IF_DELETE_HOOK, isis_if_delete_hook);
2074
2075 /* Install interface node */
2076 install_node (&interface_node, isis_interface_config_write);
2077 install_element (CONFIG_NODE, &interface_cmd);
2078
2079 install_default (INTERFACE_NODE);
2080 install_element (INTERFACE_NODE, &interface_desc_cmd);
2081 install_element (INTERFACE_NODE, &no_interface_desc_cmd);
2082
2083 install_element (INTERFACE_NODE, &ip_router_isis_cmd);
2084 install_element (INTERFACE_NODE, &no_ip_router_isis_cmd);
2085
2086 install_element (INTERFACE_NODE, &isis_circuit_type_cmd);
2087 install_element (INTERFACE_NODE, &no_isis_circuit_type_cmd);
2088
2089 install_element (INTERFACE_NODE, &isis_passwd_cmd);
2090 install_element (INTERFACE_NODE, &no_isis_passwd_cmd);
2091
2092 install_element (INTERFACE_NODE, &isis_priority_cmd);
2093 install_element (INTERFACE_NODE, &no_isis_priority_cmd);
2094 install_element (INTERFACE_NODE, &no_isis_priority_arg_cmd);
2095 install_element (INTERFACE_NODE, &isis_priority_l1_cmd);
2096 install_element (INTERFACE_NODE, &no_isis_priority_l1_cmd);
2097 install_element (INTERFACE_NODE, &no_isis_priority_l1_arg_cmd);
2098 install_element (INTERFACE_NODE, &isis_priority_l2_cmd);
2099 install_element (INTERFACE_NODE, &no_isis_priority_l2_cmd);
2100 install_element (INTERFACE_NODE, &no_isis_priority_l2_arg_cmd);
2101
2102 install_element (INTERFACE_NODE, &isis_metric_cmd);
2103 install_element (INTERFACE_NODE, &no_isis_metric_cmd);
2104 install_element (INTERFACE_NODE, &no_isis_metric_arg_cmd);
2105
2106 install_element (INTERFACE_NODE, &isis_hello_interval_cmd);
2107 install_element (INTERFACE_NODE, &no_isis_hello_interval_cmd);
2108 install_element (INTERFACE_NODE, &no_isis_hello_interval_arg_cmd);
2109 install_element (INTERFACE_NODE, &isis_hello_interval_l1_cmd);
2110 install_element (INTERFACE_NODE, &no_isis_hello_interval_l1_cmd);
2111 install_element (INTERFACE_NODE, &no_isis_hello_interval_l1_arg_cmd);
2112 install_element (INTERFACE_NODE, &isis_hello_interval_l2_cmd);
2113 install_element (INTERFACE_NODE, &no_isis_hello_interval_l2_cmd);
2114 install_element (INTERFACE_NODE, &no_isis_hello_interval_l2_arg_cmd);
2115
2116 install_element (INTERFACE_NODE, &isis_hello_multiplier_cmd);
2117 install_element (INTERFACE_NODE, &no_isis_hello_multiplier_cmd);
2118 install_element (INTERFACE_NODE, &no_isis_hello_multiplier_arg_cmd);
2119 install_element (INTERFACE_NODE, &isis_hello_multiplier_l1_cmd);
2120 install_element (INTERFACE_NODE, &no_isis_hello_multiplier_l1_cmd);
2121 install_element (INTERFACE_NODE, &no_isis_hello_multiplier_l1_arg_cmd);
2122 install_element (INTERFACE_NODE, &isis_hello_multiplier_l2_cmd);
2123 install_element (INTERFACE_NODE, &no_isis_hello_multiplier_l2_cmd);
2124 install_element (INTERFACE_NODE, &no_isis_hello_multiplier_l2_arg_cmd);
2125
2126 install_element (INTERFACE_NODE, &isis_hello_cmd);
2127 install_element (INTERFACE_NODE, &no_isis_hello_cmd);
2128 install_element (INTERFACE_NODE, &csnp_interval_cmd);
2129 install_element (INTERFACE_NODE, &no_csnp_interval_cmd);
2130 install_element (INTERFACE_NODE, &no_csnp_interval_arg_cmd);
2131 install_element (INTERFACE_NODE, &csnp_interval_l1_cmd);
2132 install_element (INTERFACE_NODE, &no_csnp_interval_l1_cmd);
2133 install_element (INTERFACE_NODE, &no_csnp_interval_l1_arg_cmd);
2134 install_element (INTERFACE_NODE, &csnp_interval_l2_cmd);
2135 install_element (INTERFACE_NODE, &no_csnp_interval_l2_cmd);
2136 install_element (INTERFACE_NODE, &no_csnp_interval_l2_arg_cmd);
2137
2138 #ifdef HAVE_IPV6
2139 install_element (INTERFACE_NODE, &ipv6_router_isis_cmd);
2140 install_element (INTERFACE_NODE, &no_ipv6_router_isis_cmd);
2141 #endif
2142 }