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