]> git.proxmox.com Git - mirror_frr.git/blob - lib/filter.c
Merge pull request #803 from opensourcerouting/redhat-doc-fixes-master
[mirror_frr.git] / lib / filter.c
1 /* Route filtering function.
2 * Copyright (C) 1998, 1999 Kunihiro Ishiguro
3 *
4 * This file is part of GNU Zebra.
5 *
6 * GNU Zebra is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published
8 * by the Free Software Foundation; either version 2, or (at your
9 * option) any later version.
10 *
11 * GNU Zebra is distributed in the hope that it will be useful, but
12 * WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 * General Public License for more details.
15 *
16 * You should have received a copy of the GNU General Public License along
17 * with this program; see the file COPYING; if not, write to the Free Software
18 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
19 */
20
21 #include <zebra.h>
22
23 #include "prefix.h"
24 #include "filter.h"
25 #include "memory.h"
26 #include "command.h"
27 #include "sockunion.h"
28 #include "buffer.h"
29 #include "log.h"
30 #include "routemap.h"
31 #include "libfrr.h"
32
33 DEFINE_MTYPE_STATIC(LIB, ACCESS_LIST, "Access List")
34 DEFINE_MTYPE_STATIC(LIB, ACCESS_LIST_STR, "Access List Str")
35 DEFINE_MTYPE_STATIC(LIB, ACCESS_FILTER, "Access Filter")
36
37 struct filter_cisco
38 {
39 /* Cisco access-list */
40 int extended;
41 struct in_addr addr;
42 struct in_addr addr_mask;
43 struct in_addr mask;
44 struct in_addr mask_mask;
45 };
46
47 struct filter_zebra
48 {
49 /* If this filter is "exact" match then this flag is set. */
50 int exact;
51
52 /* Prefix information. */
53 struct prefix prefix;
54 };
55
56 /* Filter element of access list */
57 struct filter
58 {
59 /* For doubly linked list. */
60 struct filter *next;
61 struct filter *prev;
62
63 /* Filter type information. */
64 enum filter_type type;
65
66 /* Cisco access-list */
67 int cisco;
68
69 union
70 {
71 struct filter_cisco cfilter;
72 struct filter_zebra zfilter;
73 } u;
74 };
75
76 /* List of access_list. */
77 struct access_list_list
78 {
79 struct access_list *head;
80 struct access_list *tail;
81 };
82
83 /* Master structure of access_list. */
84 struct access_master
85 {
86 /* List of access_list which name is number. */
87 struct access_list_list num;
88
89 /* List of access_list which name is string. */
90 struct access_list_list str;
91
92 /* Hook function which is executed when new access_list is added. */
93 void (*add_hook) (struct access_list *);
94
95 /* Hook function which is executed when access_list is deleted. */
96 void (*delete_hook) (struct access_list *);
97 };
98
99 /* Static structure for IPv4 access_list's master. */
100 static struct access_master access_master_ipv4 =
101 {
102 {NULL, NULL},
103 {NULL, NULL},
104 NULL,
105 NULL,
106 };
107
108 /* Static structure for IPv6 access_list's master. */
109 static struct access_master access_master_ipv6 =
110 {
111 {NULL, NULL},
112 {NULL, NULL},
113 NULL,
114 NULL,
115 };
116
117 static struct access_master *
118 access_master_get (afi_t afi)
119 {
120 if (afi == AFI_IP)
121 return &access_master_ipv4;
122 else if (afi == AFI_IP6)
123 return &access_master_ipv6;
124 return NULL;
125 }
126
127 /* Allocate new filter structure. */
128 static struct filter *
129 filter_new (void)
130 {
131 return (struct filter *) XCALLOC (MTYPE_ACCESS_FILTER,
132 sizeof (struct filter));
133 }
134
135 static void
136 filter_free (struct filter *filter)
137 {
138 XFREE (MTYPE_ACCESS_FILTER, filter);
139 }
140
141 /* Return string of filter_type. */
142 static const char *
143 filter_type_str (struct filter *filter)
144 {
145 switch (filter->type)
146 {
147 case FILTER_PERMIT:
148 return "permit";
149 break;
150 case FILTER_DENY:
151 return "deny";
152 break;
153 case FILTER_DYNAMIC:
154 return "dynamic";
155 break;
156 default:
157 return "";
158 break;
159 }
160 }
161
162 /* If filter match to the prefix then return 1. */
163 static int
164 filter_match_cisco (struct filter *mfilter, struct prefix *p)
165 {
166 struct filter_cisco *filter;
167 struct in_addr mask;
168 u_int32_t check_addr;
169 u_int32_t check_mask;
170
171 filter = &mfilter->u.cfilter;
172 check_addr = p->u.prefix4.s_addr & ~filter->addr_mask.s_addr;
173
174 if (filter->extended)
175 {
176 masklen2ip (p->prefixlen, &mask);
177 check_mask = mask.s_addr & ~filter->mask_mask.s_addr;
178
179 if (memcmp (&check_addr, &filter->addr.s_addr, 4) == 0
180 && memcmp (&check_mask, &filter->mask.s_addr, 4) == 0)
181 return 1;
182 }
183 else if (memcmp (&check_addr, &filter->addr.s_addr, 4) == 0)
184 return 1;
185
186 return 0;
187 }
188
189 /* If filter match to the prefix then return 1. */
190 static int
191 filter_match_zebra (struct filter *mfilter, struct prefix *p)
192 {
193 struct filter_zebra *filter;
194
195 filter = &mfilter->u.zfilter;
196
197 if (filter->prefix.family == p->family)
198 {
199 if (filter->exact)
200 {
201 if (filter->prefix.prefixlen == p->prefixlen)
202 return prefix_match (&filter->prefix, p);
203 else
204 return 0;
205 }
206 else
207 return prefix_match (&filter->prefix, p);
208 }
209 else
210 return 0;
211 }
212
213 /* Allocate new access list structure. */
214 static struct access_list *
215 access_list_new (void)
216 {
217 return (struct access_list *) XCALLOC (MTYPE_ACCESS_LIST,
218 sizeof (struct access_list));
219 }
220
221 /* Free allocated access_list. */
222 static void
223 access_list_free (struct access_list *access)
224 {
225 XFREE (MTYPE_ACCESS_LIST, access);
226 }
227
228 /* Delete access_list from access_master and free it. */
229 static void
230 access_list_delete (struct access_list *access)
231 {
232 struct filter *filter;
233 struct filter *next;
234 struct access_list_list *list;
235 struct access_master *master;
236
237 for (filter = access->head; filter; filter = next)
238 {
239 next = filter->next;
240 filter_free (filter);
241 }
242
243 master = access->master;
244
245 if (access->type == ACCESS_TYPE_NUMBER)
246 list = &master->num;
247 else
248 list = &master->str;
249
250 if (access->next)
251 access->next->prev = access->prev;
252 else
253 list->tail = access->prev;
254
255 if (access->prev)
256 access->prev->next = access->next;
257 else
258 list->head = access->next;
259
260 if (access->name)
261 XFREE (MTYPE_ACCESS_LIST_STR, access->name);
262
263 if (access->remark)
264 XFREE (MTYPE_TMP, access->remark);
265
266 access_list_free (access);
267 }
268
269 /* Insert new access list to list of access_list. Each acceess_list
270 is sorted by the name. */
271 static struct access_list *
272 access_list_insert (afi_t afi, const char *name)
273 {
274 unsigned int i;
275 long number;
276 struct access_list *access;
277 struct access_list *point;
278 struct access_list_list *alist;
279 struct access_master *master;
280
281 master = access_master_get (afi);
282 if (master == NULL)
283 return NULL;
284
285 /* Allocate new access_list and copy given name. */
286 access = access_list_new ();
287 access->name = XSTRDUP (MTYPE_ACCESS_LIST_STR, name);
288 access->master = master;
289
290 /* If name is made by all digit character. We treat it as
291 number. */
292 for (number = 0, i = 0; i < strlen (name); i++)
293 {
294 if (isdigit ((int) name[i]))
295 number = (number * 10) + (name[i] - '0');
296 else
297 break;
298 }
299
300 /* In case of name is all digit character */
301 if (i == strlen (name))
302 {
303 access->type = ACCESS_TYPE_NUMBER;
304
305 /* Set access_list to number list. */
306 alist = &master->num;
307
308 for (point = alist->head; point; point = point->next)
309 if (atol (point->name) >= number)
310 break;
311 }
312 else
313 {
314 access->type = ACCESS_TYPE_STRING;
315
316 /* Set access_list to string list. */
317 alist = &master->str;
318
319 /* Set point to insertion point. */
320 for (point = alist->head; point; point = point->next)
321 if (strcmp (point->name, name) >= 0)
322 break;
323 }
324
325 /* In case of this is the first element of master. */
326 if (alist->head == NULL)
327 {
328 alist->head = alist->tail = access;
329 return access;
330 }
331
332 /* In case of insertion is made at the tail of access_list. */
333 if (point == NULL)
334 {
335 access->prev = alist->tail;
336 alist->tail->next = access;
337 alist->tail = access;
338 return access;
339 }
340
341 /* In case of insertion is made at the head of access_list. */
342 if (point == alist->head)
343 {
344 access->next = alist->head;
345 alist->head->prev = access;
346 alist->head = access;
347 return access;
348 }
349
350 /* Insertion is made at middle of the access_list. */
351 access->next = point;
352 access->prev = point->prev;
353
354 if (point->prev)
355 point->prev->next = access;
356 point->prev = access;
357
358 return access;
359 }
360
361 /* Lookup access_list from list of access_list by name. */
362 struct access_list *
363 access_list_lookup (afi_t afi, const char *name)
364 {
365 struct access_list *access;
366 struct access_master *master;
367
368 if (name == NULL)
369 return NULL;
370
371 master = access_master_get (afi);
372 if (master == NULL)
373 return NULL;
374
375 for (access = master->num.head; access; access = access->next)
376 if (strcmp (access->name, name) == 0)
377 return access;
378
379 for (access = master->str.head; access; access = access->next)
380 if (strcmp (access->name, name) == 0)
381 return access;
382
383 return NULL;
384 }
385
386 /* Get access list from list of access_list. If there isn't matched
387 access_list create new one and return it. */
388 static struct access_list *
389 access_list_get (afi_t afi, const char *name)
390 {
391 struct access_list *access;
392
393 access = access_list_lookup (afi, name);
394 if (access == NULL)
395 access = access_list_insert (afi, name);
396 return access;
397 }
398
399 /* Apply access list to object (which should be struct prefix *). */
400 enum filter_type
401 access_list_apply (struct access_list *access, void *object)
402 {
403 struct filter *filter;
404 struct prefix *p;
405
406 p = (struct prefix *) object;
407
408 if (access == NULL)
409 return FILTER_DENY;
410
411 for (filter = access->head; filter; filter = filter->next)
412 {
413 if (filter->cisco)
414 {
415 if (filter_match_cisco (filter, p))
416 return filter->type;
417 }
418 else
419 {
420 if (filter_match_zebra (filter, p))
421 return filter->type;
422 }
423 }
424
425 return FILTER_DENY;
426 }
427
428 /* Add hook function. */
429 void
430 access_list_add_hook (void (*func) (struct access_list *access))
431 {
432 access_master_ipv4.add_hook = func;
433 access_master_ipv6.add_hook = func;
434 }
435
436 /* Delete hook function. */
437 void
438 access_list_delete_hook (void (*func) (struct access_list *access))
439 {
440 access_master_ipv4.delete_hook = func;
441 access_master_ipv6.delete_hook = func;
442 }
443
444 /* Add new filter to the end of specified access_list. */
445 static void
446 access_list_filter_add (struct access_list *access, struct filter *filter)
447 {
448 filter->next = NULL;
449 filter->prev = access->tail;
450
451 if (access->tail)
452 access->tail->next = filter;
453 else
454 access->head = filter;
455 access->tail = filter;
456
457 /* Run hook function. */
458 if (access->master->add_hook)
459 (*access->master->add_hook) (access);
460 route_map_notify_dependencies(access->name, RMAP_EVENT_FILTER_ADDED);
461 }
462
463 /* If access_list has no filter then return 1. */
464 static int
465 access_list_empty (struct access_list *access)
466 {
467 if (access->head == NULL && access->tail == NULL)
468 return 1;
469 else
470 return 0;
471 }
472
473 /* Delete filter from specified access_list. If there is hook
474 function execute it. */
475 static void
476 access_list_filter_delete (struct access_list *access, struct filter *filter)
477 {
478 struct access_master *master;
479
480 master = access->master;
481
482 if (filter->next)
483 filter->next->prev = filter->prev;
484 else
485 access->tail = filter->prev;
486
487 if (filter->prev)
488 filter->prev->next = filter->next;
489 else
490 access->head = filter->next;
491
492 filter_free (filter);
493
494 route_map_notify_dependencies(access->name, RMAP_EVENT_FILTER_DELETED);
495 /* Run hook function. */
496 if (master->delete_hook)
497 (*master->delete_hook) (access);
498
499 /* If access_list becomes empty delete it from access_master. */
500 if (access_list_empty (access))
501 access_list_delete (access);
502 }
503
504 /*
505 deny Specify packets to reject
506 permit Specify packets to forward
507 dynamic ?
508 */
509
510 /*
511 Hostname or A.B.C.D Address to match
512 any Any source host
513 host A single host address
514 */
515
516 static struct filter *
517 filter_lookup_cisco (struct access_list *access, struct filter *mnew)
518 {
519 struct filter *mfilter;
520 struct filter_cisco *filter;
521 struct filter_cisco *new;
522
523 new = &mnew->u.cfilter;
524
525 for (mfilter = access->head; mfilter; mfilter = mfilter->next)
526 {
527 filter = &mfilter->u.cfilter;
528
529 if (filter->extended)
530 {
531 if (mfilter->type == mnew->type
532 && filter->addr.s_addr == new->addr.s_addr
533 && filter->addr_mask.s_addr == new->addr_mask.s_addr
534 && filter->mask.s_addr == new->mask.s_addr
535 && filter->mask_mask.s_addr == new->mask_mask.s_addr)
536 return mfilter;
537 }
538 else
539 {
540 if (mfilter->type == mnew->type
541 && filter->addr.s_addr == new->addr.s_addr
542 && filter->addr_mask.s_addr == new->addr_mask.s_addr)
543 return mfilter;
544 }
545 }
546
547 return NULL;
548 }
549
550 static struct filter *
551 filter_lookup_zebra (struct access_list *access, struct filter *mnew)
552 {
553 struct filter *mfilter;
554 struct filter_zebra *filter;
555 struct filter_zebra *new;
556
557 new = &mnew->u.zfilter;
558
559 for (mfilter = access->head; mfilter; mfilter = mfilter->next)
560 {
561 filter = &mfilter->u.zfilter;
562
563 if (filter->exact == new->exact
564 && mfilter->type == mnew->type
565 && prefix_same (&filter->prefix, &new->prefix))
566 return mfilter;
567 }
568 return NULL;
569 }
570
571 static int
572 vty_access_list_remark_unset (struct vty *vty, afi_t afi, const char *name)
573 {
574 struct access_list *access;
575
576 access = access_list_lookup (afi, name);
577 if (! access)
578 {
579 vty_out (vty, "%% access-list %s doesn't exist\n",name);
580 return CMD_WARNING_CONFIG_FAILED;
581 }
582
583 if (access->remark)
584 {
585 XFREE (MTYPE_TMP, access->remark);
586 access->remark = NULL;
587 }
588
589 if (access->head == NULL && access->tail == NULL && access->remark == NULL)
590 access_list_delete (access);
591
592 return CMD_SUCCESS;
593 }
594
595 static int
596 filter_set_cisco (struct vty *vty, const char *name_str, const char *type_str,
597 const char *addr_str, const char *addr_mask_str,
598 const char *mask_str, const char *mask_mask_str,
599 int extended, int set)
600 {
601 int ret;
602 enum filter_type type;
603 struct filter *mfilter;
604 struct filter_cisco *filter;
605 struct access_list *access;
606 struct in_addr addr;
607 struct in_addr addr_mask;
608 struct in_addr mask;
609 struct in_addr mask_mask;
610
611 /* Check of filter type. */
612 if (strncmp (type_str, "p", 1) == 0)
613 type = FILTER_PERMIT;
614 else if (strncmp (type_str, "d", 1) == 0)
615 type = FILTER_DENY;
616 else
617 {
618 vty_out (vty, "%% filter type must be permit or deny\n");
619 return CMD_WARNING_CONFIG_FAILED;
620 }
621
622 ret = inet_aton (addr_str, &addr);
623 if (ret <= 0)
624 {
625 vty_out (vty,"%%Inconsistent address and mask\n");
626 return CMD_WARNING_CONFIG_FAILED;
627 }
628
629 ret = inet_aton (addr_mask_str, &addr_mask);
630 if (ret <= 0)
631 {
632 vty_out (vty,"%%Inconsistent address and mask\n");
633 return CMD_WARNING_CONFIG_FAILED;
634 }
635
636 if (extended)
637 {
638 ret = inet_aton (mask_str, &mask);
639 if (ret <= 0)
640 {
641 vty_out (vty,"%%Inconsistent address and mask\n");
642 return CMD_WARNING_CONFIG_FAILED;
643 }
644
645 ret = inet_aton (mask_mask_str, &mask_mask);
646 if (ret <= 0)
647 {
648 vty_out (vty,"%%Inconsistent address and mask\n");
649 return CMD_WARNING_CONFIG_FAILED;
650 }
651 }
652
653 mfilter = filter_new();
654 mfilter->type = type;
655 mfilter->cisco = 1;
656 filter = &mfilter->u.cfilter;
657 filter->extended = extended;
658 filter->addr.s_addr = addr.s_addr & ~addr_mask.s_addr;
659 filter->addr_mask.s_addr = addr_mask.s_addr;
660
661 if (extended)
662 {
663 filter->mask.s_addr = mask.s_addr & ~mask_mask.s_addr;
664 filter->mask_mask.s_addr = mask_mask.s_addr;
665 }
666
667 /* Install new filter to the access_list. */
668 access = access_list_get (AFI_IP, name_str);
669
670 if (set)
671 {
672 if (filter_lookup_cisco (access, mfilter))
673 filter_free (mfilter);
674 else
675 access_list_filter_add (access, mfilter);
676 }
677 else
678 {
679 struct filter *delete_filter;
680
681 delete_filter = filter_lookup_cisco (access, mfilter);
682 if (delete_filter)
683 access_list_filter_delete (access, delete_filter);
684
685 filter_free (mfilter);
686 }
687
688 return CMD_SUCCESS;
689 }
690
691 /* Standard access-list */
692 DEFUN (access_list_standard,
693 access_list_standard_cmd,
694 "access-list <(1-99)|(1300-1999)> <deny|permit> A.B.C.D A.B.C.D",
695 "Add an access list entry\n"
696 "IP standard access list\n"
697 "IP standard access list (expanded range)\n"
698 "Specify packets to reject\n"
699 "Specify packets to forward\n"
700 "Address to match\n"
701 "Wildcard bits\n")
702 {
703 int idx_acl = 1;
704 int idx_permit_deny = 2;
705 int idx_ipv4 = 3;
706 int idx_ipv4_2 = 4;
707 return filter_set_cisco (vty, argv[idx_acl]->arg, argv[idx_permit_deny]->arg, argv[idx_ipv4]->arg, argv[idx_ipv4_2]->arg,
708 NULL, NULL, 0, 1);
709 }
710
711 DEFUN (access_list_standard_nomask,
712 access_list_standard_nomask_cmd,
713 "access-list <(1-99)|(1300-1999)> <deny|permit> A.B.C.D",
714 "Add an access list entry\n"
715 "IP standard access list\n"
716 "IP standard access list (expanded range)\n"
717 "Specify packets to reject\n"
718 "Specify packets to forward\n"
719 "Address to match\n")
720 {
721 int idx_acl = 1;
722 int idx_permit_deny = 2;
723 int idx_ipv4 = 3;
724 return filter_set_cisco (vty, argv[idx_acl]->arg, argv[idx_permit_deny]->arg, argv[idx_ipv4]->arg, "0.0.0.0",
725 NULL, NULL, 0, 1);
726 }
727
728 DEFUN (access_list_standard_host,
729 access_list_standard_host_cmd,
730 "access-list <(1-99)|(1300-1999)> <deny|permit> host A.B.C.D",
731 "Add an access list entry\n"
732 "IP standard access list\n"
733 "IP standard access list (expanded range)\n"
734 "Specify packets to reject\n"
735 "Specify packets to forward\n"
736 "A single host address\n"
737 "Address to match\n")
738 {
739 int idx_acl = 1;
740 int idx_permit_deny = 2;
741 int idx_ipv4 = 4;
742 return filter_set_cisco (vty, argv[idx_acl]->arg, argv[idx_permit_deny]->arg, argv[idx_ipv4]->arg, "0.0.0.0",
743 NULL, NULL, 0, 1);
744 }
745
746 DEFUN (access_list_standard_any,
747 access_list_standard_any_cmd,
748 "access-list <(1-99)|(1300-1999)> <deny|permit> any",
749 "Add an access list entry\n"
750 "IP standard access list\n"
751 "IP standard access list (expanded range)\n"
752 "Specify packets to reject\n"
753 "Specify packets to forward\n"
754 "Any source host\n")
755 {
756 int idx_acl = 1;
757 int idx_permit_deny = 2;
758 return filter_set_cisco (vty, argv[idx_acl]->arg, argv[idx_permit_deny]->arg, "0.0.0.0",
759 "255.255.255.255", NULL, NULL, 0, 1);
760 }
761
762 DEFUN (no_access_list_standard,
763 no_access_list_standard_cmd,
764 "no access-list <(1-99)|(1300-1999)> <deny|permit> A.B.C.D A.B.C.D",
765 NO_STR
766 "Add an access list entry\n"
767 "IP standard access list\n"
768 "IP standard access list (expanded range)\n"
769 "Specify packets to reject\n"
770 "Specify packets to forward\n"
771 "Address to match\n"
772 "Wildcard bits\n")
773 {
774 int idx_acl = 2;
775 int idx_permit_deny = 3;
776 int idx_ipv4 = 4;
777 int idx_ipv4_2 = 5;
778 return filter_set_cisco (vty, argv[idx_acl]->arg, argv[idx_permit_deny]->arg, argv[idx_ipv4]->arg, argv[idx_ipv4_2]->arg,
779 NULL, NULL, 0, 0);
780 }
781
782 DEFUN (no_access_list_standard_nomask,
783 no_access_list_standard_nomask_cmd,
784 "no access-list <(1-99)|(1300-1999)> <deny|permit> A.B.C.D",
785 NO_STR
786 "Add an access list entry\n"
787 "IP standard access list\n"
788 "IP standard access list (expanded range)\n"
789 "Specify packets to reject\n"
790 "Specify packets to forward\n"
791 "Address to match\n")
792 {
793 int idx_acl = 2;
794 int idx_permit_deny = 3;
795 int idx_ipv4 = 4;
796 return filter_set_cisco (vty, argv[idx_acl]->arg, argv[idx_permit_deny]->arg, argv[idx_ipv4]->arg, "0.0.0.0",
797 NULL, NULL, 0, 0);
798 }
799
800 DEFUN (no_access_list_standard_host,
801 no_access_list_standard_host_cmd,
802 "no access-list <(1-99)|(1300-1999)> <deny|permit> host A.B.C.D",
803 NO_STR
804 "Add an access list entry\n"
805 "IP standard access list\n"
806 "IP standard access list (expanded range)\n"
807 "Specify packets to reject\n"
808 "Specify packets to forward\n"
809 "A single host address\n"
810 "Address to match\n")
811 {
812 int idx_acl = 2;
813 int idx_permit_deny = 3;
814 int idx_ipv4 = 5;
815 return filter_set_cisco (vty, argv[idx_acl]->arg, argv[idx_permit_deny]->arg, argv[idx_ipv4]->arg, "0.0.0.0",
816 NULL, NULL, 0, 0);
817 }
818
819 DEFUN (no_access_list_standard_any,
820 no_access_list_standard_any_cmd,
821 "no access-list <(1-99)|(1300-1999)> <deny|permit> any",
822 NO_STR
823 "Add an access list entry\n"
824 "IP standard access list\n"
825 "IP standard access list (expanded range)\n"
826 "Specify packets to reject\n"
827 "Specify packets to forward\n"
828 "Any source host\n")
829 {
830 int idx_acl = 2;
831 int idx_permit_deny = 3;
832 return filter_set_cisco (vty, argv[idx_acl]->arg, argv[idx_permit_deny]->arg, "0.0.0.0",
833 "255.255.255.255", NULL, NULL, 0, 0);
834 }
835
836 /* Extended access-list */
837 DEFUN (access_list_extended,
838 access_list_extended_cmd,
839 "access-list <(100-199)|(2000-2699)> <deny|permit> ip A.B.C.D A.B.C.D A.B.C.D A.B.C.D",
840 "Add an access list entry\n"
841 "IP extended access list\n"
842 "IP extended access list (expanded range)\n"
843 "Specify packets to reject\n"
844 "Specify packets to forward\n"
845 "Any Internet Protocol\n"
846 "Source address\n"
847 "Source wildcard bits\n"
848 "Destination address\n"
849 "Destination Wildcard bits\n")
850 {
851 int idx_acl = 1;
852 int idx_permit_deny = 2;
853 int idx_ipv4 = 4;
854 int idx_ipv4_2 = 5;
855 int idx_ipv4_3 = 6;
856 int idx_ipv4_4 = 7;
857 return filter_set_cisco (vty, argv[idx_acl]->arg, argv[idx_permit_deny]->arg, argv[idx_ipv4]->arg,
858 argv[idx_ipv4_2]->arg, argv[idx_ipv4_3]->arg, argv[idx_ipv4_4]->arg, 1 ,1);
859 }
860
861 DEFUN (access_list_extended_mask_any,
862 access_list_extended_mask_any_cmd,
863 "access-list <(100-199)|(2000-2699)> <deny|permit> ip A.B.C.D A.B.C.D any",
864 "Add an access list entry\n"
865 "IP extended access list\n"
866 "IP extended access list (expanded range)\n"
867 "Specify packets to reject\n"
868 "Specify packets to forward\n"
869 "Any Internet Protocol\n"
870 "Source address\n"
871 "Source wildcard bits\n"
872 "Any destination host\n")
873 {
874 int idx_acl = 1;
875 int idx_permit_deny = 2;
876 int idx_ipv4 = 4;
877 int idx_ipv4_2 = 5;
878 return filter_set_cisco (vty, argv[idx_acl]->arg, argv[idx_permit_deny]->arg, argv[idx_ipv4]->arg,
879 argv[idx_ipv4_2]->arg, "0.0.0.0",
880 "255.255.255.255", 1, 1);
881 }
882
883 DEFUN (access_list_extended_any_mask,
884 access_list_extended_any_mask_cmd,
885 "access-list <(100-199)|(2000-2699)> <deny|permit> ip any A.B.C.D A.B.C.D",
886 "Add an access list entry\n"
887 "IP extended access list\n"
888 "IP extended access list (expanded range)\n"
889 "Specify packets to reject\n"
890 "Specify packets to forward\n"
891 "Any Internet Protocol\n"
892 "Any source host\n"
893 "Destination address\n"
894 "Destination Wildcard bits\n")
895 {
896 int idx_acl = 1;
897 int idx_permit_deny = 2;
898 int idx_ipv4 = 5;
899 int idx_ipv4_2 = 6;
900 return filter_set_cisco (vty, argv[idx_acl]->arg, argv[idx_permit_deny]->arg, "0.0.0.0",
901 "255.255.255.255", argv[idx_ipv4]->arg,
902 argv[idx_ipv4_2]->arg, 1, 1);
903 }
904
905 DEFUN (access_list_extended_any_any,
906 access_list_extended_any_any_cmd,
907 "access-list <(100-199)|(2000-2699)> <deny|permit> ip any any",
908 "Add an access list entry\n"
909 "IP extended access list\n"
910 "IP extended access list (expanded range)\n"
911 "Specify packets to reject\n"
912 "Specify packets to forward\n"
913 "Any Internet Protocol\n"
914 "Any source host\n"
915 "Any destination host\n")
916 {
917 int idx_acl = 1;
918 int idx_permit_deny = 2;
919 return filter_set_cisco (vty, argv[idx_acl]->arg, argv[idx_permit_deny]->arg, "0.0.0.0",
920 "255.255.255.255", "0.0.0.0",
921 "255.255.255.255", 1, 1);
922 }
923
924 DEFUN (access_list_extended_mask_host,
925 access_list_extended_mask_host_cmd,
926 "access-list <(100-199)|(2000-2699)> <deny|permit> ip A.B.C.D A.B.C.D host A.B.C.D",
927 "Add an access list entry\n"
928 "IP extended access list\n"
929 "IP extended access list (expanded range)\n"
930 "Specify packets to reject\n"
931 "Specify packets to forward\n"
932 "Any Internet Protocol\n"
933 "Source address\n"
934 "Source wildcard bits\n"
935 "A single destination host\n"
936 "Destination address\n")
937 {
938 int idx_acl = 1;
939 int idx_permit_deny = 2;
940 int idx_ipv4 = 4;
941 int idx_ipv4_2 = 5;
942 int idx_ipv4_3 = 7;
943 return filter_set_cisco (vty, argv[idx_acl]->arg, argv[idx_permit_deny]->arg, argv[idx_ipv4]->arg,
944 argv[idx_ipv4_2]->arg, argv[idx_ipv4_3]->arg,
945 "0.0.0.0", 1, 1);
946 }
947
948 DEFUN (access_list_extended_host_mask,
949 access_list_extended_host_mask_cmd,
950 "access-list <(100-199)|(2000-2699)> <deny|permit> ip host A.B.C.D A.B.C.D A.B.C.D",
951 "Add an access list entry\n"
952 "IP extended access list\n"
953 "IP extended access list (expanded range)\n"
954 "Specify packets to reject\n"
955 "Specify packets to forward\n"
956 "Any Internet Protocol\n"
957 "A single source host\n"
958 "Source address\n"
959 "Destination address\n"
960 "Destination Wildcard bits\n")
961 {
962 int idx_acl = 1;
963 int idx_permit_deny = 2;
964 int idx_ipv4 = 5;
965 int idx_ipv4_2 = 6;
966 int idx_ipv4_3 = 7;
967 return filter_set_cisco (vty, argv[idx_acl]->arg, argv[idx_permit_deny]->arg, argv[idx_ipv4]->arg,
968 "0.0.0.0", argv[idx_ipv4_2]->arg,
969 argv[idx_ipv4_3]->arg, 1, 1);
970 }
971
972 DEFUN (access_list_extended_host_host,
973 access_list_extended_host_host_cmd,
974 "access-list <(100-199)|(2000-2699)> <deny|permit> ip host A.B.C.D host A.B.C.D",
975 "Add an access list entry\n"
976 "IP extended access list\n"
977 "IP extended access list (expanded range)\n"
978 "Specify packets to reject\n"
979 "Specify packets to forward\n"
980 "Any Internet Protocol\n"
981 "A single source host\n"
982 "Source address\n"
983 "A single destination host\n"
984 "Destination address\n")
985 {
986 int idx_acl = 1;
987 int idx_permit_deny = 2;
988 int idx_ipv4 = 5;
989 int idx_ipv4_2 = 7;
990 return filter_set_cisco (vty, argv[idx_acl]->arg, argv[idx_permit_deny]->arg, argv[idx_ipv4]->arg,
991 "0.0.0.0", argv[idx_ipv4_2]->arg,
992 "0.0.0.0", 1, 1);
993 }
994
995 DEFUN (access_list_extended_any_host,
996 access_list_extended_any_host_cmd,
997 "access-list <(100-199)|(2000-2699)> <deny|permit> ip any host A.B.C.D",
998 "Add an access list entry\n"
999 "IP extended access list\n"
1000 "IP extended access list (expanded range)\n"
1001 "Specify packets to reject\n"
1002 "Specify packets to forward\n"
1003 "Any Internet Protocol\n"
1004 "Any source host\n"
1005 "A single destination host\n"
1006 "Destination address\n")
1007 {
1008 int idx_acl = 1;
1009 int idx_permit_deny = 2;
1010 int idx_ipv4 = 6;
1011 return filter_set_cisco (vty, argv[idx_acl]->arg, argv[idx_permit_deny]->arg, "0.0.0.0",
1012 "255.255.255.255", argv[idx_ipv4]->arg,
1013 "0.0.0.0", 1, 1);
1014 }
1015
1016 DEFUN (access_list_extended_host_any,
1017 access_list_extended_host_any_cmd,
1018 "access-list <(100-199)|(2000-2699)> <deny|permit> ip host A.B.C.D any",
1019 "Add an access list entry\n"
1020 "IP extended access list\n"
1021 "IP extended access list (expanded range)\n"
1022 "Specify packets to reject\n"
1023 "Specify packets to forward\n"
1024 "Any Internet Protocol\n"
1025 "A single source host\n"
1026 "Source address\n"
1027 "Any destination host\n")
1028 {
1029 int idx_acl = 1;
1030 int idx_permit_deny = 2;
1031 int idx_ipv4 = 5;
1032 return filter_set_cisco (vty, argv[idx_acl]->arg, argv[idx_permit_deny]->arg, argv[idx_ipv4]->arg,
1033 "0.0.0.0", "0.0.0.0",
1034 "255.255.255.255", 1, 1);
1035 }
1036
1037 DEFUN (no_access_list_extended,
1038 no_access_list_extended_cmd,
1039 "no access-list <(100-199)|(2000-2699)> <deny|permit> ip A.B.C.D A.B.C.D A.B.C.D A.B.C.D",
1040 NO_STR
1041 "Add an access list entry\n"
1042 "IP extended access list\n"
1043 "IP extended access list (expanded range)\n"
1044 "Specify packets to reject\n"
1045 "Specify packets to forward\n"
1046 "Any Internet Protocol\n"
1047 "Source address\n"
1048 "Source wildcard bits\n"
1049 "Destination address\n"
1050 "Destination Wildcard bits\n")
1051 {
1052 int idx_acl = 2;
1053 int idx_permit_deny = 3;
1054 int idx_ipv4 = 5;
1055 int idx_ipv4_2 = 6;
1056 int idx_ipv4_3 = 7;
1057 int idx_ipv4_4 = 8;
1058 return filter_set_cisco (vty, argv[idx_acl]->arg, argv[idx_permit_deny]->arg, argv[idx_ipv4]->arg,
1059 argv[idx_ipv4_2]->arg, argv[idx_ipv4_3]->arg, argv[idx_ipv4_4]->arg, 1, 0);
1060 }
1061
1062 DEFUN (no_access_list_extended_mask_any,
1063 no_access_list_extended_mask_any_cmd,
1064 "no access-list <(100-199)|(2000-2699)> <deny|permit> ip A.B.C.D A.B.C.D any",
1065 NO_STR
1066 "Add an access list entry\n"
1067 "IP extended access list\n"
1068 "IP extended access list (expanded range)\n"
1069 "Specify packets to reject\n"
1070 "Specify packets to forward\n"
1071 "Any Internet Protocol\n"
1072 "Source address\n"
1073 "Source wildcard bits\n"
1074 "Any destination host\n")
1075 {
1076 int idx_acl = 2;
1077 int idx_permit_deny = 3;
1078 int idx_ipv4 = 5;
1079 int idx_ipv4_2 = 6;
1080 return filter_set_cisco (vty, argv[idx_acl]->arg, argv[idx_permit_deny]->arg, argv[idx_ipv4]->arg,
1081 argv[idx_ipv4_2]->arg, "0.0.0.0",
1082 "255.255.255.255", 1, 0);
1083 }
1084
1085 DEFUN (no_access_list_extended_any_mask,
1086 no_access_list_extended_any_mask_cmd,
1087 "no access-list <(100-199)|(2000-2699)> <deny|permit> ip any A.B.C.D A.B.C.D",
1088 NO_STR
1089 "Add an access list entry\n"
1090 "IP extended access list\n"
1091 "IP extended access list (expanded range)\n"
1092 "Specify packets to reject\n"
1093 "Specify packets to forward\n"
1094 "Any Internet Protocol\n"
1095 "Any source host\n"
1096 "Destination address\n"
1097 "Destination Wildcard bits\n")
1098 {
1099 int idx_acl = 2;
1100 int idx_permit_deny = 3;
1101 int idx_ipv4 = 6;
1102 int idx_ipv4_2 = 7;
1103 return filter_set_cisco (vty, argv[idx_acl]->arg, argv[idx_permit_deny]->arg, "0.0.0.0",
1104 "255.255.255.255", argv[idx_ipv4]->arg,
1105 argv[idx_ipv4_2]->arg, 1, 0);
1106 }
1107
1108 DEFUN (no_access_list_extended_any_any,
1109 no_access_list_extended_any_any_cmd,
1110 "no access-list <(100-199)|(2000-2699)> <deny|permit> ip any any",
1111 NO_STR
1112 "Add an access list entry\n"
1113 "IP extended access list\n"
1114 "IP extended access list (expanded range)\n"
1115 "Specify packets to reject\n"
1116 "Specify packets to forward\n"
1117 "Any Internet Protocol\n"
1118 "Any source host\n"
1119 "Any destination host\n")
1120 {
1121 int idx_acl = 2;
1122 int idx_permit_deny = 3;
1123 return filter_set_cisco (vty, argv[idx_acl]->arg, argv[idx_permit_deny]->arg, "0.0.0.0",
1124 "255.255.255.255", "0.0.0.0",
1125 "255.255.255.255", 1, 0);
1126 }
1127
1128 DEFUN (no_access_list_extended_mask_host,
1129 no_access_list_extended_mask_host_cmd,
1130 "no access-list <(100-199)|(2000-2699)> <deny|permit> ip A.B.C.D A.B.C.D host A.B.C.D",
1131 NO_STR
1132 "Add an access list entry\n"
1133 "IP extended access list\n"
1134 "IP extended access list (expanded range)\n"
1135 "Specify packets to reject\n"
1136 "Specify packets to forward\n"
1137 "Any Internet Protocol\n"
1138 "Source address\n"
1139 "Source wildcard bits\n"
1140 "A single destination host\n"
1141 "Destination address\n")
1142 {
1143 int idx_acl = 2;
1144 int idx_permit_deny = 3;
1145 int idx_ipv4 = 5;
1146 int idx_ipv4_2 = 6;
1147 int idx_ipv4_3 = 8;
1148 return filter_set_cisco (vty, argv[idx_acl]->arg, argv[idx_permit_deny]->arg, argv[idx_ipv4]->arg,
1149 argv[idx_ipv4_2]->arg, argv[idx_ipv4_3]->arg,
1150 "0.0.0.0", 1, 0);
1151 }
1152
1153 DEFUN (no_access_list_extended_host_mask,
1154 no_access_list_extended_host_mask_cmd,
1155 "no access-list <(100-199)|(2000-2699)> <deny|permit> ip host A.B.C.D A.B.C.D A.B.C.D",
1156 NO_STR
1157 "Add an access list entry\n"
1158 "IP extended access list\n"
1159 "IP extended access list (expanded range)\n"
1160 "Specify packets to reject\n"
1161 "Specify packets to forward\n"
1162 "Any Internet Protocol\n"
1163 "A single source host\n"
1164 "Source address\n"
1165 "Destination address\n"
1166 "Destination Wildcard bits\n")
1167 {
1168 int idx_acl = 2;
1169 int idx_permit_deny = 3;
1170 int idx_ipv4 = 6;
1171 int idx_ipv4_2 = 7;
1172 int idx_ipv4_3 = 8;
1173 return filter_set_cisco (vty, argv[idx_acl]->arg, argv[idx_permit_deny]->arg, argv[idx_ipv4]->arg,
1174 "0.0.0.0", argv[idx_ipv4_2]->arg,
1175 argv[idx_ipv4_3]->arg, 1, 0);
1176 }
1177
1178 DEFUN (no_access_list_extended_host_host,
1179 no_access_list_extended_host_host_cmd,
1180 "no access-list <(100-199)|(2000-2699)> <deny|permit> ip host A.B.C.D host A.B.C.D",
1181 NO_STR
1182 "Add an access list entry\n"
1183 "IP extended access list\n"
1184 "IP extended access list (expanded range)\n"
1185 "Specify packets to reject\n"
1186 "Specify packets to forward\n"
1187 "Any Internet Protocol\n"
1188 "A single source host\n"
1189 "Source address\n"
1190 "A single destination host\n"
1191 "Destination address\n")
1192 {
1193 int idx_acl = 2;
1194 int idx_permit_deny = 3;
1195 int idx_ipv4 = 6;
1196 int idx_ipv4_2 = 8;
1197 return filter_set_cisco (vty, argv[idx_acl]->arg, argv[idx_permit_deny]->arg, argv[idx_ipv4]->arg,
1198 "0.0.0.0", argv[idx_ipv4_2]->arg,
1199 "0.0.0.0", 1, 0);
1200 }
1201
1202 DEFUN (no_access_list_extended_any_host,
1203 no_access_list_extended_any_host_cmd,
1204 "no access-list <(100-199)|(2000-2699)> <deny|permit> ip any host A.B.C.D",
1205 NO_STR
1206 "Add an access list entry\n"
1207 "IP extended access list\n"
1208 "IP extended access list (expanded range)\n"
1209 "Specify packets to reject\n"
1210 "Specify packets to forward\n"
1211 "Any Internet Protocol\n"
1212 "Any source host\n"
1213 "A single destination host\n"
1214 "Destination address\n")
1215 {
1216 int idx_acl = 2;
1217 int idx_permit_deny = 3;
1218 int idx_ipv4 = 7;
1219 return filter_set_cisco (vty, argv[idx_acl]->arg, argv[idx_permit_deny]->arg, "0.0.0.0",
1220 "255.255.255.255", argv[idx_ipv4]->arg,
1221 "0.0.0.0", 1, 0);
1222 }
1223
1224 DEFUN (no_access_list_extended_host_any,
1225 no_access_list_extended_host_any_cmd,
1226 "no access-list <(100-199)|(2000-2699)> <deny|permit> ip host A.B.C.D any",
1227 NO_STR
1228 "Add an access list entry\n"
1229 "IP extended access list\n"
1230 "IP extended access list (expanded range)\n"
1231 "Specify packets to reject\n"
1232 "Specify packets to forward\n"
1233 "Any Internet Protocol\n"
1234 "A single source host\n"
1235 "Source address\n"
1236 "Any destination host\n")
1237 {
1238 int idx_acl = 2;
1239 int idx_permit_deny = 3;
1240 int idx_ipv4 = 6;
1241 return filter_set_cisco (vty, argv[idx_acl]->arg, argv[idx_permit_deny]->arg, argv[idx_ipv4]->arg,
1242 "0.0.0.0", "0.0.0.0",
1243 "255.255.255.255", 1, 0);
1244 }
1245
1246 static int
1247 filter_set_zebra (struct vty *vty, const char *name_str, const char *type_str,
1248 afi_t afi, const char *prefix_str, int exact, int set)
1249 {
1250 int ret;
1251 enum filter_type type;
1252 struct filter *mfilter;
1253 struct filter_zebra *filter;
1254 struct access_list *access;
1255 struct prefix p;
1256
1257 if (strlen(name_str) > ACL_NAMSIZ)
1258 {
1259 vty_out (vty, "%% ACL name %s is invalid: length exceeds "
1260 "%d characters\n",
1261 name_str, ACL_NAMSIZ);
1262 return CMD_WARNING_CONFIG_FAILED;
1263 }
1264
1265 /* Check of filter type. */
1266 if (strncmp (type_str, "p", 1) == 0)
1267 type = FILTER_PERMIT;
1268 else if (strncmp (type_str, "d", 1) == 0)
1269 type = FILTER_DENY;
1270 else
1271 {
1272 vty_out (vty, "filter type must be [permit|deny]\n");
1273 return CMD_WARNING_CONFIG_FAILED;
1274 }
1275
1276 /* Check string format of prefix and prefixlen. */
1277 if (afi == AFI_IP)
1278 {
1279 ret = str2prefix_ipv4 (prefix_str, (struct prefix_ipv4 *)&p);
1280 if (ret <= 0)
1281 {
1282 vty_out (vty,"IP address prefix/prefixlen is malformed\n");
1283 return CMD_WARNING_CONFIG_FAILED;
1284 }
1285 }
1286 else if (afi == AFI_IP6)
1287 {
1288 ret = str2prefix_ipv6 (prefix_str, (struct prefix_ipv6 *) &p);
1289 if (ret <= 0)
1290 {
1291 vty_out (vty,"IPv6 address prefix/prefixlen is malformed\n");
1292 return CMD_WARNING_CONFIG_FAILED;
1293 }
1294 }
1295 else
1296 return CMD_WARNING_CONFIG_FAILED;
1297
1298 mfilter = filter_new ();
1299 mfilter->type = type;
1300 filter = &mfilter->u.zfilter;
1301 prefix_copy (&filter->prefix, &p);
1302
1303 /* "exact-match" */
1304 if (exact)
1305 filter->exact = 1;
1306
1307 /* Install new filter to the access_list. */
1308 access = access_list_get (afi, name_str);
1309
1310 if (set)
1311 {
1312 if (filter_lookup_zebra (access, mfilter))
1313 filter_free (mfilter);
1314 else
1315 access_list_filter_add (access, mfilter);
1316 }
1317 else
1318 {
1319 struct filter *delete_filter;
1320
1321 delete_filter = filter_lookup_zebra (access, mfilter);
1322 if (delete_filter)
1323 access_list_filter_delete (access, delete_filter);
1324
1325 filter_free (mfilter);
1326 }
1327
1328 return CMD_SUCCESS;
1329 }
1330
1331 DEFUN (access_list_exact,
1332 access_list_exact_cmd,
1333 "access-list WORD <deny|permit> A.B.C.D/M [exact-match]",
1334 "Add an access list entry\n"
1335 "IP zebra access-list name\n"
1336 "Specify packets to reject\n"
1337 "Specify packets to forward\n"
1338 "Prefix to match. e.g. 10.0.0.0/8\n"
1339 "Exact match of the prefixes\n")
1340 {
1341 int idx;
1342 int exact = 0;
1343 int idx_word = 1;
1344 int idx_permit_deny = 2;
1345 int idx_ipv4_prefixlen = 3;
1346 idx = idx_ipv4_prefixlen;
1347
1348 if (argv_find (argv, argc, "exact-match", &idx))
1349 exact = 1;
1350
1351 return filter_set_zebra (vty, argv[idx_word]->arg, argv[idx_permit_deny]->arg,
1352 AFI_IP, argv[idx_ipv4_prefixlen]->arg, exact, 1);
1353 }
1354
1355 DEFUN (access_list_any,
1356 access_list_any_cmd,
1357 "access-list WORD <deny|permit> any",
1358 "Add an access list entry\n"
1359 "IP zebra access-list name\n"
1360 "Specify packets to reject\n"
1361 "Specify packets to forward\n"
1362 "Prefix to match. e.g. 10.0.0.0/8\n")
1363 {
1364 int idx_word = 1;
1365 int idx_permit_deny = 2;
1366 return filter_set_zebra (vty, argv[idx_word]->arg, argv[idx_permit_deny]->arg, AFI_IP, "0.0.0.0/0", 0, 1);
1367 }
1368
1369 DEFUN (no_access_list_exact,
1370 no_access_list_exact_cmd,
1371 "no access-list WORD <deny|permit> A.B.C.D/M [exact-match]",
1372 NO_STR
1373 "Add an access list entry\n"
1374 "IP zebra access-list name\n"
1375 "Specify packets to reject\n"
1376 "Specify packets to forward\n"
1377 "Prefix to match. e.g. 10.0.0.0/8\n"
1378 "Exact match of the prefixes\n")
1379 {
1380 int idx;
1381 int exact = 0;
1382 int idx_word = 2;
1383 int idx_permit_deny = 3;
1384 int idx_ipv4_prefixlen = 4;
1385 idx = idx_ipv4_prefixlen;
1386
1387 if (argv_find (argv, argc, "exact-match", &idx))
1388 exact = 1;
1389
1390 return filter_set_zebra (vty, argv[idx_word]->arg, argv[idx_permit_deny]->arg, AFI_IP, argv[idx_ipv4_prefixlen]->arg, exact, 0);
1391 }
1392
1393 DEFUN (no_access_list_any,
1394 no_access_list_any_cmd,
1395 "no access-list WORD <deny|permit> any",
1396 NO_STR
1397 "Add an access list entry\n"
1398 "IP zebra access-list name\n"
1399 "Specify packets to reject\n"
1400 "Specify packets to forward\n"
1401 "Prefix to match. e.g. 10.0.0.0/8\n")
1402 {
1403 int idx_word = 2;
1404 int idx_permit_deny = 3;
1405 return filter_set_zebra (vty, argv[idx_word]->arg, argv[idx_permit_deny]->arg, AFI_IP, "0.0.0.0/0", 0, 0);
1406 }
1407
1408 DEFUN (no_access_list_all,
1409 no_access_list_all_cmd,
1410 "no access-list <(1-99)|(100-199)|(1300-1999)|(2000-2699)|WORD>",
1411 NO_STR
1412 "Add an access list entry\n"
1413 "IP standard access list\n"
1414 "IP extended access list\n"
1415 "IP standard access list (expanded range)\n"
1416 "IP extended access list (expanded range)\n"
1417 "IP zebra access-list name\n")
1418 {
1419 int idx_acl = 2;
1420 struct access_list *access;
1421 struct access_master *master;
1422
1423 /* Looking up access_list. */
1424 access = access_list_lookup (AFI_IP, argv[idx_acl]->arg);
1425 if (access == NULL)
1426 {
1427 vty_out (vty, "%% access-list %s doesn't exist\n",argv[idx_acl]->arg);
1428 return CMD_WARNING_CONFIG_FAILED;
1429 }
1430
1431 master = access->master;
1432
1433 route_map_notify_dependencies(access->name, RMAP_EVENT_FILTER_DELETED);
1434 /* Run hook function. */
1435 if (master->delete_hook)
1436 (*master->delete_hook) (access);
1437
1438 /* Delete all filter from access-list. */
1439 access_list_delete (access);
1440
1441 return CMD_SUCCESS;
1442 }
1443
1444 DEFUN (access_list_remark,
1445 access_list_remark_cmd,
1446 "access-list <(1-99)|(100-199)|(1300-1999)|(2000-2699)|WORD> remark LINE...",
1447 "Add an access list entry\n"
1448 "IP standard access list\n"
1449 "IP extended access list\n"
1450 "IP standard access list (expanded range)\n"
1451 "IP extended access list (expanded range)\n"
1452 "IP zebra access-list\n"
1453 "Access list entry comment\n"
1454 "Comment up to 100 characters\n")
1455 {
1456 int idx_acl = 1;
1457 int idx_remark = 3;
1458 struct access_list *access;
1459
1460 access = access_list_get (AFI_IP, argv[idx_acl]->arg);
1461
1462 if (access->remark)
1463 {
1464 XFREE (MTYPE_TMP, access->remark);
1465 access->remark = NULL;
1466 }
1467 access->remark = argv_concat(argv, argc, idx_remark);
1468
1469 return CMD_SUCCESS;
1470 }
1471
1472 DEFUN (no_access_list_remark,
1473 no_access_list_remark_cmd,
1474 "no access-list <(1-99)|(100-199)|(1300-1999)|(2000-2699)|WORD> remark",
1475 NO_STR
1476 "Add an access list entry\n"
1477 "IP standard access list\n"
1478 "IP extended access list\n"
1479 "IP standard access list (expanded range)\n"
1480 "IP extended access list (expanded range)\n"
1481 "IP zebra access-list\n"
1482 "Access list entry comment\n")
1483 {
1484 int idx_acl = 2;
1485 return vty_access_list_remark_unset (vty, AFI_IP, argv[idx_acl]->arg);
1486 }
1487
1488 /* ALIAS_FIXME */
1489 DEFUN (no_access_list_remark_comment,
1490 no_access_list_remark_comment_cmd,
1491 "no access-list <(1-99)|(100-199)|(1300-1999)|(2000-2699)|WORD> remark LINE...",
1492 NO_STR
1493 "Add an access list entry\n"
1494 "IP standard access list\n"
1495 "IP extended access list\n"
1496 "IP standard access list (expanded range)\n"
1497 "IP extended access list (expanded range)\n"
1498 "IP zebra access-list\n"
1499 "Access list entry comment\n"
1500 "Comment up to 100 characters\n")
1501 {
1502 return no_access_list_remark (self, vty, argc, argv);
1503 }
1504
1505 DEFUN (ipv6_access_list_exact,
1506 ipv6_access_list_exact_cmd,
1507 "ipv6 access-list WORD <deny|permit> X:X::X:X/M [exact-match]",
1508 IPV6_STR
1509 "Add an access list entry\n"
1510 "IPv6 zebra access-list\n"
1511 "Specify packets to reject\n"
1512 "Specify packets to forward\n"
1513 "IPv6 prefix\n"
1514 "Exact match of the prefixes\n")
1515 {
1516 int idx;
1517 int exact = 0;
1518 int idx_word = 2;
1519 int idx_allow = 3;
1520 int idx_addr = 4;
1521 idx = idx_addr;
1522
1523 if (argv_find (argv, argc, "exact-match", &idx))
1524 exact = 1;
1525
1526 return filter_set_zebra (vty, argv[idx_word]->arg, argv[idx_allow]->text,
1527 AFI_IP6, argv[idx_addr]->arg, exact, 1);
1528 }
1529
1530 DEFUN (ipv6_access_list_any,
1531 ipv6_access_list_any_cmd,
1532 "ipv6 access-list WORD <deny|permit> any",
1533 IPV6_STR
1534 "Add an access list entry\n"
1535 "IPv6 zebra access-list\n"
1536 "Specify packets to reject\n"
1537 "Specify packets to forward\n"
1538 "Any prefixi to match\n")
1539 {
1540 int idx_word = 2;
1541 int idx_permit_deny = 3;
1542 return filter_set_zebra (vty, argv[idx_word]->arg, argv[idx_permit_deny]->arg, AFI_IP6, "::/0", 0, 1);
1543 }
1544
1545 DEFUN (no_ipv6_access_list_exact,
1546 no_ipv6_access_list_exact_cmd,
1547 "no ipv6 access-list WORD <deny|permit> X:X::X:X/M [exact-match]",
1548 NO_STR
1549 IPV6_STR
1550 "Add an access list entry\n"
1551 "IPv6 zebra access-list\n"
1552 "Specify packets to reject\n"
1553 "Specify packets to forward\n"
1554 "Prefix to match. e.g. 3ffe:506::/32\n"
1555 "Exact match of the prefixes\n")
1556 {
1557 int idx;
1558 int exact = 0;
1559 int idx_word = 3;
1560 int idx_permit_deny = 4;
1561 int idx_ipv6_prefixlen = 5;
1562 idx = idx_ipv6_prefixlen;
1563
1564 if (argv_find (argv, argc, "exact-match", &idx))
1565 exact = 1;
1566
1567 return filter_set_zebra (vty, argv[idx_word]->arg, argv[idx_permit_deny]->arg,
1568 AFI_IP6, argv[idx_ipv6_prefixlen]->arg, exact, 0);
1569 }
1570
1571 DEFUN (no_ipv6_access_list_any,
1572 no_ipv6_access_list_any_cmd,
1573 "no ipv6 access-list WORD <deny|permit> any",
1574 NO_STR
1575 IPV6_STR
1576 "Add an access list entry\n"
1577 "IPv6 zebra access-list\n"
1578 "Specify packets to reject\n"
1579 "Specify packets to forward\n"
1580 "Any prefixi to match\n")
1581 {
1582 int idx_word = 3;
1583 int idx_permit_deny = 4;
1584 return filter_set_zebra (vty, argv[idx_word]->arg, argv[idx_permit_deny]->arg, AFI_IP6, "::/0", 0, 0);
1585 }
1586
1587
1588 DEFUN (no_ipv6_access_list_all,
1589 no_ipv6_access_list_all_cmd,
1590 "no ipv6 access-list WORD",
1591 NO_STR
1592 IPV6_STR
1593 "Add an access list entry\n"
1594 "IPv6 zebra access-list\n")
1595 {
1596 int idx_word = 3;
1597 struct access_list *access;
1598 struct access_master *master;
1599
1600 /* Looking up access_list. */
1601 access = access_list_lookup (AFI_IP6, argv[idx_word]->arg);
1602 if (access == NULL)
1603 {
1604 vty_out (vty, "%% access-list %s doesn't exist\n",argv[idx_word]->arg);
1605 return CMD_WARNING_CONFIG_FAILED;
1606 }
1607
1608 master = access->master;
1609
1610 route_map_notify_dependencies(access->name, RMAP_EVENT_FILTER_DELETED);
1611 /* Run hook function. */
1612 if (master->delete_hook)
1613 (*master->delete_hook) (access);
1614
1615 /* Delete all filter from access-list. */
1616 access_list_delete (access);
1617
1618 return CMD_SUCCESS;
1619 }
1620
1621 DEFUN (ipv6_access_list_remark,
1622 ipv6_access_list_remark_cmd,
1623 "ipv6 access-list WORD remark LINE...",
1624 IPV6_STR
1625 "Add an access list entry\n"
1626 "IPv6 zebra access-list\n"
1627 "Access list entry comment\n"
1628 "Comment up to 100 characters\n")
1629 {
1630 int idx_word = 2;
1631 int idx_line = 4;
1632 struct access_list *access;
1633
1634 access = access_list_get (AFI_IP6, argv[idx_word]->arg);
1635
1636 if (access->remark)
1637 {
1638 XFREE (MTYPE_TMP, access->remark);
1639 access->remark = NULL;
1640 }
1641 access->remark = argv_concat(argv, argc, idx_line);
1642
1643 return CMD_SUCCESS;
1644 }
1645
1646 DEFUN (no_ipv6_access_list_remark,
1647 no_ipv6_access_list_remark_cmd,
1648 "no ipv6 access-list WORD remark",
1649 NO_STR
1650 IPV6_STR
1651 "Add an access list entry\n"
1652 "IPv6 zebra access-list\n"
1653 "Access list entry comment\n")
1654 {
1655 int idx_word = 3;
1656 return vty_access_list_remark_unset (vty, AFI_IP6, argv[idx_word]->arg);
1657 }
1658
1659 /* ALIAS_FIXME */
1660 DEFUN (no_ipv6_access_list_remark_comment,
1661 no_ipv6_access_list_remark_comment_cmd,
1662 "no ipv6 access-list WORD remark LINE...",
1663 NO_STR
1664 IPV6_STR
1665 "Add an access list entry\n"
1666 "IPv6 zebra access-list\n"
1667 "Access list entry comment\n"
1668 "Comment up to 100 characters\n")
1669 {
1670 return no_ipv6_access_list_remark (self, vty, argc, argv);
1671 }
1672
1673 void config_write_access_zebra (struct vty *, struct filter *);
1674 void config_write_access_cisco (struct vty *, struct filter *);
1675
1676 /* show access-list command. */
1677 static int
1678 filter_show (struct vty *vty, const char *name, afi_t afi)
1679 {
1680 struct access_list *access;
1681 struct access_master *master;
1682 struct filter *mfilter;
1683 struct filter_cisco *filter;
1684 int write = 0;
1685
1686 master = access_master_get (afi);
1687 if (master == NULL)
1688 return 0;
1689
1690 /* Print the name of the protocol */
1691 vty_out (vty, "%s:\n", frr_protoname);
1692
1693 for (access = master->num.head; access; access = access->next)
1694 {
1695 if (name && strcmp (access->name, name) != 0)
1696 continue;
1697
1698 write = 1;
1699
1700 for (mfilter = access->head; mfilter; mfilter = mfilter->next)
1701 {
1702 filter = &mfilter->u.cfilter;
1703
1704 if (write)
1705 {
1706 vty_out (vty, "%s IP%s access list %s\n",
1707 mfilter->cisco ?
1708 (filter->extended ? "Extended" : "Standard") : "Zebra",
1709 afi == AFI_IP6 ? "v6" : "",
1710 access->name);
1711 write = 0;
1712 }
1713
1714 vty_out (vty, " %s%s", filter_type_str (mfilter),
1715 mfilter->type == FILTER_DENY ? " " : "");
1716
1717 if (! mfilter->cisco)
1718 config_write_access_zebra (vty, mfilter);
1719 else if (filter->extended)
1720 config_write_access_cisco (vty, mfilter);
1721 else
1722 {
1723 if (filter->addr_mask.s_addr == 0xffffffff)
1724 vty_out (vty, " any\n");
1725 else
1726 {
1727 vty_out (vty, " %s", inet_ntoa (filter->addr));
1728 if (filter->addr_mask.s_addr != 0)
1729 vty_out (vty, ", wildcard bits %s", inet_ntoa (filter->addr_mask));
1730 vty_out (vty, "\n");
1731 }
1732 }
1733 }
1734 }
1735
1736 for (access = master->str.head; access; access = access->next)
1737 {
1738 if (name && strcmp (access->name, name) != 0)
1739 continue;
1740
1741 write = 1;
1742
1743 for (mfilter = access->head; mfilter; mfilter = mfilter->next)
1744 {
1745 filter = &mfilter->u.cfilter;
1746
1747 if (write)
1748 {
1749 vty_out (vty, "%s IP%s access list %s\n",
1750 mfilter->cisco ?
1751 (filter->extended ? "Extended" : "Standard") : "Zebra",
1752 afi == AFI_IP6 ? "v6" : "",
1753 access->name);
1754 write = 0;
1755 }
1756
1757 vty_out (vty, " %s%s", filter_type_str (mfilter),
1758 mfilter->type == FILTER_DENY ? " " : "");
1759
1760 if (! mfilter->cisco)
1761 config_write_access_zebra (vty, mfilter);
1762 else if (filter->extended)
1763 config_write_access_cisco (vty, mfilter);
1764 else
1765 {
1766 if (filter->addr_mask.s_addr == 0xffffffff)
1767 vty_out (vty, " any\n");
1768 else
1769 {
1770 vty_out (vty, " %s", inet_ntoa (filter->addr));
1771 if (filter->addr_mask.s_addr != 0)
1772 vty_out (vty, ", wildcard bits %s", inet_ntoa (filter->addr_mask));
1773 vty_out (vty, "\n");
1774 }
1775 }
1776 }
1777 }
1778 return CMD_SUCCESS;
1779 }
1780
1781 DEFUN (show_ip_access_list,
1782 show_ip_access_list_cmd,
1783 "show ip access-list",
1784 SHOW_STR
1785 IP_STR
1786 "List IP access lists\n")
1787 {
1788 return filter_show (vty, NULL, AFI_IP);
1789 }
1790
1791 DEFUN (show_ip_access_list_name,
1792 show_ip_access_list_name_cmd,
1793 "show ip access-list <(1-99)|(100-199)|(1300-1999)|(2000-2699)|WORD>",
1794 SHOW_STR
1795 IP_STR
1796 "List IP access lists\n"
1797 "IP standard access list\n"
1798 "IP extended access list\n"
1799 "IP standard access list (expanded range)\n"
1800 "IP extended access list (expanded range)\n"
1801 "IP zebra access-list\n")
1802 {
1803 int idx_acl = 3;
1804 return filter_show (vty, argv[idx_acl]->arg, AFI_IP);
1805 }
1806
1807 DEFUN (show_ipv6_access_list,
1808 show_ipv6_access_list_cmd,
1809 "show ipv6 access-list",
1810 SHOW_STR
1811 IPV6_STR
1812 "List IPv6 access lists\n")
1813 {
1814 return filter_show (vty, NULL, AFI_IP6);
1815 }
1816
1817 DEFUN (show_ipv6_access_list_name,
1818 show_ipv6_access_list_name_cmd,
1819 "show ipv6 access-list WORD",
1820 SHOW_STR
1821 IPV6_STR
1822 "List IPv6 access lists\n"
1823 "IPv6 zebra access-list\n")
1824 {
1825 int idx_word = 3;
1826 return filter_show (vty, argv[idx_word]->arg, AFI_IP6);
1827 }
1828
1829 void
1830 config_write_access_cisco (struct vty *vty, struct filter *mfilter)
1831 {
1832 struct filter_cisco *filter;
1833
1834 filter = &mfilter->u.cfilter;
1835
1836 if (filter->extended)
1837 {
1838 vty_out (vty, " ip");
1839 if (filter->addr_mask.s_addr == 0xffffffff)
1840 vty_out (vty, " any");
1841 else if (filter->addr_mask.s_addr == 0)
1842 vty_out (vty, " host %s", inet_ntoa (filter->addr));
1843 else
1844 {
1845 vty_out (vty, " %s", inet_ntoa (filter->addr));
1846 vty_out (vty, " %s", inet_ntoa (filter->addr_mask));
1847 }
1848
1849 if (filter->mask_mask.s_addr == 0xffffffff)
1850 vty_out (vty, " any");
1851 else if (filter->mask_mask.s_addr == 0)
1852 vty_out (vty, " host %s", inet_ntoa (filter->mask));
1853 else
1854 {
1855 vty_out (vty, " %s", inet_ntoa (filter->mask));
1856 vty_out (vty, " %s", inet_ntoa (filter->mask_mask));
1857 }
1858 vty_out (vty, "\n");
1859 }
1860 else
1861 {
1862 if (filter->addr_mask.s_addr == 0xffffffff)
1863 vty_out (vty, " any\n");
1864 else
1865 {
1866 vty_out (vty, " %s", inet_ntoa (filter->addr));
1867 if (filter->addr_mask.s_addr != 0)
1868 vty_out (vty, " %s", inet_ntoa (filter->addr_mask));
1869 vty_out (vty, "\n");
1870 }
1871 }
1872 }
1873
1874 void
1875 config_write_access_zebra (struct vty *vty, struct filter *mfilter)
1876 {
1877 struct filter_zebra *filter;
1878 struct prefix *p;
1879 char buf[BUFSIZ];
1880
1881 filter = &mfilter->u.zfilter;
1882 p = &filter->prefix;
1883
1884 if (p->prefixlen == 0 && ! filter->exact)
1885 vty_out (vty, " any");
1886 else
1887 vty_out (vty, " %s/%d%s",
1888 inet_ntop (p->family, &p->u.prefix, buf, BUFSIZ),
1889 p->prefixlen,
1890 filter->exact ? " exact-match" : "");
1891
1892 vty_out (vty, "\n");
1893 }
1894
1895 static int
1896 config_write_access (struct vty *vty, afi_t afi)
1897 {
1898 struct access_list *access;
1899 struct access_master *master;
1900 struct filter *mfilter;
1901 int write = 0;
1902
1903 master = access_master_get (afi);
1904 if (master == NULL)
1905 return 0;
1906
1907 for (access = master->num.head; access; access = access->next)
1908 {
1909 if (access->remark)
1910 {
1911 vty_out (vty, "%saccess-list %s remark %s\n",
1912 afi == AFI_IP ? "" : "ipv6 ",
1913 access->name,access->remark);
1914 write++;
1915 }
1916
1917 for (mfilter = access->head; mfilter; mfilter = mfilter->next)
1918 {
1919 vty_out (vty, "%saccess-list %s %s",
1920 afi == AFI_IP ? "" : "ipv6 ",
1921 access->name,
1922 filter_type_str (mfilter));
1923
1924 if (mfilter->cisco)
1925 config_write_access_cisco (vty, mfilter);
1926 else
1927 config_write_access_zebra (vty, mfilter);
1928
1929 write++;
1930 }
1931 }
1932
1933 for (access = master->str.head; access; access = access->next)
1934 {
1935 if (access->remark)
1936 {
1937 vty_out (vty, "%saccess-list %s remark %s\n",
1938 afi == AFI_IP ? "" : "ipv6 ",
1939 access->name,access->remark);
1940 write++;
1941 }
1942
1943 for (mfilter = access->head; mfilter; mfilter = mfilter->next)
1944 {
1945 vty_out (vty, "%saccess-list %s %s",
1946 afi == AFI_IP ? "" : "ipv6 ",
1947 access->name,
1948 filter_type_str (mfilter));
1949
1950 if (mfilter->cisco)
1951 config_write_access_cisco (vty, mfilter);
1952 else
1953 config_write_access_zebra (vty, mfilter);
1954
1955 write++;
1956 }
1957 }
1958 return write;
1959 }
1960
1961 /* Access-list node. */
1962 static struct cmd_node access_node =
1963 {
1964 ACCESS_NODE,
1965 "", /* Access list has no interface. */
1966 1
1967 };
1968
1969 static int
1970 config_write_access_ipv4 (struct vty *vty)
1971 {
1972 return config_write_access (vty, AFI_IP);
1973 }
1974
1975 static void
1976 access_list_reset_ipv4 (void)
1977 {
1978 struct access_list *access;
1979 struct access_list *next;
1980 struct access_master *master;
1981
1982 master = access_master_get (AFI_IP);
1983 if (master == NULL)
1984 return;
1985
1986 for (access = master->num.head; access; access = next)
1987 {
1988 next = access->next;
1989 access_list_delete (access);
1990 }
1991 for (access = master->str.head; access; access = next)
1992 {
1993 next = access->next;
1994 access_list_delete (access);
1995 }
1996
1997 assert (master->num.head == NULL);
1998 assert (master->num.tail == NULL);
1999
2000 assert (master->str.head == NULL);
2001 assert (master->str.tail == NULL);
2002 }
2003
2004 /* Install vty related command. */
2005 static void
2006 access_list_init_ipv4 (void)
2007 {
2008 install_node (&access_node, config_write_access_ipv4);
2009
2010 install_element (ENABLE_NODE, &show_ip_access_list_cmd);
2011 install_element (ENABLE_NODE, &show_ip_access_list_name_cmd);
2012
2013 /* Zebra access-list */
2014 install_element (CONFIG_NODE, &access_list_exact_cmd);
2015 install_element (CONFIG_NODE, &access_list_any_cmd);
2016 install_element (CONFIG_NODE, &no_access_list_exact_cmd);
2017 install_element (CONFIG_NODE, &no_access_list_any_cmd);
2018
2019 /* Standard access-list */
2020 install_element (CONFIG_NODE, &access_list_standard_cmd);
2021 install_element (CONFIG_NODE, &access_list_standard_nomask_cmd);
2022 install_element (CONFIG_NODE, &access_list_standard_host_cmd);
2023 install_element (CONFIG_NODE, &access_list_standard_any_cmd);
2024 install_element (CONFIG_NODE, &no_access_list_standard_cmd);
2025 install_element (CONFIG_NODE, &no_access_list_standard_nomask_cmd);
2026 install_element (CONFIG_NODE, &no_access_list_standard_host_cmd);
2027 install_element (CONFIG_NODE, &no_access_list_standard_any_cmd);
2028
2029 /* Extended access-list */
2030 install_element (CONFIG_NODE, &access_list_extended_cmd);
2031 install_element (CONFIG_NODE, &access_list_extended_any_mask_cmd);
2032 install_element (CONFIG_NODE, &access_list_extended_mask_any_cmd);
2033 install_element (CONFIG_NODE, &access_list_extended_any_any_cmd);
2034 install_element (CONFIG_NODE, &access_list_extended_host_mask_cmd);
2035 install_element (CONFIG_NODE, &access_list_extended_mask_host_cmd);
2036 install_element (CONFIG_NODE, &access_list_extended_host_host_cmd);
2037 install_element (CONFIG_NODE, &access_list_extended_any_host_cmd);
2038 install_element (CONFIG_NODE, &access_list_extended_host_any_cmd);
2039 install_element (CONFIG_NODE, &no_access_list_extended_cmd);
2040 install_element (CONFIG_NODE, &no_access_list_extended_any_mask_cmd);
2041 install_element (CONFIG_NODE, &no_access_list_extended_mask_any_cmd);
2042 install_element (CONFIG_NODE, &no_access_list_extended_any_any_cmd);
2043 install_element (CONFIG_NODE, &no_access_list_extended_host_mask_cmd);
2044 install_element (CONFIG_NODE, &no_access_list_extended_mask_host_cmd);
2045 install_element (CONFIG_NODE, &no_access_list_extended_host_host_cmd);
2046 install_element (CONFIG_NODE, &no_access_list_extended_any_host_cmd);
2047 install_element (CONFIG_NODE, &no_access_list_extended_host_any_cmd);
2048
2049 install_element (CONFIG_NODE, &access_list_remark_cmd);
2050 install_element (CONFIG_NODE, &no_access_list_all_cmd);
2051 install_element (CONFIG_NODE, &no_access_list_remark_cmd);
2052 install_element (CONFIG_NODE, &no_access_list_remark_comment_cmd);
2053 }
2054
2055 static struct cmd_node access_ipv6_node =
2056 {
2057 ACCESS_IPV6_NODE,
2058 "",
2059 1
2060 };
2061
2062 static int
2063 config_write_access_ipv6 (struct vty *vty)
2064 {
2065 return config_write_access (vty, AFI_IP6);
2066 }
2067
2068 static void
2069 access_list_reset_ipv6 (void)
2070 {
2071 struct access_list *access;
2072 struct access_list *next;
2073 struct access_master *master;
2074
2075 master = access_master_get (AFI_IP6);
2076 if (master == NULL)
2077 return;
2078
2079 for (access = master->num.head; access; access = next)
2080 {
2081 next = access->next;
2082 access_list_delete (access);
2083 }
2084 for (access = master->str.head; access; access = next)
2085 {
2086 next = access->next;
2087 access_list_delete (access);
2088 }
2089
2090 assert (master->num.head == NULL);
2091 assert (master->num.tail == NULL);
2092
2093 assert (master->str.head == NULL);
2094 assert (master->str.tail == NULL);
2095 }
2096
2097 static void
2098 access_list_init_ipv6 (void)
2099 {
2100 install_node (&access_ipv6_node, config_write_access_ipv6);
2101
2102 install_element (ENABLE_NODE, &show_ipv6_access_list_cmd);
2103 install_element (ENABLE_NODE, &show_ipv6_access_list_name_cmd);
2104
2105 install_element (CONFIG_NODE, &ipv6_access_list_exact_cmd);
2106 install_element (CONFIG_NODE, &ipv6_access_list_any_cmd);
2107 install_element (CONFIG_NODE, &no_ipv6_access_list_exact_cmd);
2108 install_element (CONFIG_NODE, &no_ipv6_access_list_any_cmd);
2109
2110 install_element (CONFIG_NODE, &no_ipv6_access_list_all_cmd);
2111 install_element (CONFIG_NODE, &ipv6_access_list_remark_cmd);
2112 install_element (CONFIG_NODE, &no_ipv6_access_list_remark_cmd);
2113 install_element (CONFIG_NODE, &no_ipv6_access_list_remark_comment_cmd);
2114 }
2115
2116 void
2117 access_list_init ()
2118 {
2119 access_list_init_ipv4 ();
2120 access_list_init_ipv6();
2121 }
2122
2123 void
2124 access_list_reset ()
2125 {
2126 access_list_reset_ipv4 ();
2127 access_list_reset_ipv6();
2128 }