*
* Copyright (C) 2013-2015 Christian Franke <chris@opensourcerouting.org>
*
- * This program is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by the Free
- * Software Foundation; either version 2 of the License, or (at your option)
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the Free
+ * Software Foundation; either version 2 of the License, or (at your option)
* any later version.
*
- * This program is distributed in the hope that it will be useful,but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
+ * This program is distributed in the hope that it will be useful,but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
-
- * You should have received a copy of the GNU General Public License along
- * with this program; if not, write to the Free Software Foundation, Inc.,
- * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with this program; see the file COPYING; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
*/
#include <zebra.h>
#include "isis_misc.h"
#include "isis_adjacency.h"
#include "isis_circuit.h"
-#include "isis_tlv.h"
#include "isis_pdu.h"
#include "isis_lsp.h"
#include "isis_spf.h"
#include "isis_zebra.h"
#include "isis_routemap.h"
-static route_map_result_t
-route_match_ip_address(void *rule, struct prefix *prefix,
- route_map_object_t type, void *object)
+static route_map_result_t route_match_ip_address(void *rule,
+ const struct prefix *prefix,
+ route_map_object_t type,
+ void *object)
{
- struct access_list *alist;
+ struct access_list *alist;
- if (type != RMAP_ISIS)
- return RMAP_NOMATCH;
+ if (type != RMAP_ISIS)
+ return RMAP_NOMATCH;
- alist = access_list_lookup(AFI_IP, (char*)rule);
- if (access_list_apply(alist, prefix) != FILTER_DENY)
- return RMAP_MATCH;
+ alist = access_list_lookup(AFI_IP, (char *)rule);
+ if (access_list_apply(alist, prefix) != FILTER_DENY)
+ return RMAP_MATCH;
- return RMAP_NOMATCH;
+ return RMAP_NOMATCH;
}
-static void *
-route_match_ip_address_compile(const char *arg)
+static void *route_match_ip_address_compile(const char *arg)
{
- return XSTRDUP(MTYPE_ROUTE_MAP_COMPILED, arg);
+ return XSTRDUP(MTYPE_ROUTE_MAP_COMPILED, arg);
}
-static void
-route_match_ip_address_free(void *rule)
+static void route_match_ip_address_free(void *rule)
{
- XFREE(MTYPE_ROUTE_MAP_COMPILED, rule);
+ XFREE(MTYPE_ROUTE_MAP_COMPILED, rule);
}
-static struct route_map_rule_cmd route_match_ip_address_cmd =
-{
- "ip address",
- route_match_ip_address,
- route_match_ip_address_compile,
- route_match_ip_address_free
-};
+static struct route_map_rule_cmd route_match_ip_address_cmd = {
+ "ip address", route_match_ip_address, route_match_ip_address_compile,
+ route_match_ip_address_free};
/* ------------------------------------------------------------*/
static route_map_result_t
-route_match_ip_address_prefix_list(void *rule, struct prefix *prefix,
- route_map_object_t type, void *object)
+route_match_ip_address_prefix_list(void *rule, const struct prefix *prefix,
+ route_map_object_t type, void *object)
{
- struct prefix_list *plist;
+ struct prefix_list *plist;
- if (type != RMAP_ISIS)
- return RMAP_NOMATCH;
+ if (type != RMAP_ISIS)
+ return RMAP_NOMATCH;
- plist = prefix_list_lookup(AFI_IP, (char*)rule);
- if (prefix_list_apply(plist, prefix) != PREFIX_DENY)
- return RMAP_MATCH;
+ plist = prefix_list_lookup(AFI_IP, (char *)rule);
+ if (prefix_list_apply(plist, prefix) != PREFIX_DENY)
+ return RMAP_MATCH;
- return RMAP_NOMATCH;
+ return RMAP_NOMATCH;
}
-static void *
-route_match_ip_address_prefix_list_compile(const char *arg)
+static void *route_match_ip_address_prefix_list_compile(const char *arg)
{
- return XSTRDUP (MTYPE_ROUTE_MAP_COMPILED, arg);
+ return XSTRDUP(MTYPE_ROUTE_MAP_COMPILED, arg);
}
-static void
-route_match_ip_address_prefix_list_free (void *rule)
+static void route_match_ip_address_prefix_list_free(void *rule)
{
- XFREE (MTYPE_ROUTE_MAP_COMPILED, rule);
+ XFREE(MTYPE_ROUTE_MAP_COMPILED, rule);
}
-struct route_map_rule_cmd route_match_ip_address_prefix_list_cmd =
-{
- "ip address prefix-list",
- route_match_ip_address_prefix_list,
- route_match_ip_address_prefix_list_compile,
- route_match_ip_address_prefix_list_free
-};
+struct route_map_rule_cmd route_match_ip_address_prefix_list_cmd = {
+ "ip address prefix-list", route_match_ip_address_prefix_list,
+ route_match_ip_address_prefix_list_compile,
+ route_match_ip_address_prefix_list_free};
/* ------------------------------------------------------------*/
-static route_map_result_t
-route_match_ipv6_address(void *rule, struct prefix *prefix,
- route_map_object_t type, void *object)
+static route_map_result_t route_match_ipv6_address(void *rule,
+ const struct prefix *prefix,
+ route_map_object_t type,
+ void *object)
{
- struct access_list *alist;
+ struct access_list *alist;
- if (type != RMAP_ISIS)
- return RMAP_NOMATCH;
+ if (type != RMAP_ISIS)
+ return RMAP_NOMATCH;
- alist = access_list_lookup(AFI_IP6, (char*)rule);
- if (access_list_apply(alist, prefix) != FILTER_DENY)
- return RMAP_MATCH;
+ alist = access_list_lookup(AFI_IP6, (char *)rule);
+ if (access_list_apply(alist, prefix) != FILTER_DENY)
+ return RMAP_MATCH;
- return RMAP_NOMATCH;
+ return RMAP_NOMATCH;
}
-static void *
-route_match_ipv6_address_compile(const char *arg)
+static void *route_match_ipv6_address_compile(const char *arg)
{
- return XSTRDUP(MTYPE_ROUTE_MAP_COMPILED, arg);
+ return XSTRDUP(MTYPE_ROUTE_MAP_COMPILED, arg);
}
-static void
-route_match_ipv6_address_free(void *rule)
+static void route_match_ipv6_address_free(void *rule)
{
- XFREE(MTYPE_ROUTE_MAP_COMPILED, rule);
+ XFREE(MTYPE_ROUTE_MAP_COMPILED, rule);
}
-static struct route_map_rule_cmd route_match_ipv6_address_cmd =
-{
- "ipv6 address",
- route_match_ipv6_address,
- route_match_ipv6_address_compile,
- route_match_ipv6_address_free
-};
+static struct route_map_rule_cmd route_match_ipv6_address_cmd = {
+ "ipv6 address", route_match_ipv6_address,
+ route_match_ipv6_address_compile, route_match_ipv6_address_free};
/* ------------------------------------------------------------*/
static route_map_result_t
-route_match_ipv6_address_prefix_list(void *rule, struct prefix *prefix,
- route_map_object_t type, void *object)
+route_match_ipv6_address_prefix_list(void *rule, const struct prefix *prefix,
+ route_map_object_t type, void *object)
{
- struct prefix_list *plist;
+ struct prefix_list *plist;
- if (type != RMAP_ISIS)
- return RMAP_NOMATCH;
+ if (type != RMAP_ISIS)
+ return RMAP_NOMATCH;
- plist = prefix_list_lookup(AFI_IP6, (char*)rule);
- if (prefix_list_apply(plist, prefix) != PREFIX_DENY)
- return RMAP_MATCH;
+ plist = prefix_list_lookup(AFI_IP6, (char *)rule);
+ if (prefix_list_apply(plist, prefix) != PREFIX_DENY)
+ return RMAP_MATCH;
- return RMAP_NOMATCH;
+ return RMAP_NOMATCH;
}
-static void *
-route_match_ipv6_address_prefix_list_compile(const char *arg)
+static void *route_match_ipv6_address_prefix_list_compile(const char *arg)
{
- return XSTRDUP (MTYPE_ROUTE_MAP_COMPILED, arg);
+ return XSTRDUP(MTYPE_ROUTE_MAP_COMPILED, arg);
}
-static void
-route_match_ipv6_address_prefix_list_free (void *rule)
+static void route_match_ipv6_address_prefix_list_free(void *rule)
{
- XFREE (MTYPE_ROUTE_MAP_COMPILED, rule);
+ XFREE(MTYPE_ROUTE_MAP_COMPILED, rule);
}
-struct route_map_rule_cmd route_match_ipv6_address_prefix_list_cmd =
-{
- "ipv6 address prefix-list",
- route_match_ipv6_address_prefix_list,
- route_match_ipv6_address_prefix_list_compile,
- route_match_ipv6_address_prefix_list_free
-};
+struct route_map_rule_cmd route_match_ipv6_address_prefix_list_cmd = {
+ "ipv6 address prefix-list", route_match_ipv6_address_prefix_list,
+ route_match_ipv6_address_prefix_list_compile,
+ route_match_ipv6_address_prefix_list_free};
/* ------------------------------------------------------------*/
-static route_map_result_t
-route_set_metric(void *rule, struct prefix *prefix,
- route_map_object_t type, void *object)
-{
- uint32_t *metric;
- struct isis_ext_info *info;
-
- if (type == RMAP_ISIS)
- {
- metric = rule;
- info = object;
-
- info->metric = *metric;
- }
- return RMAP_OKAY;
-}
-
-static void *
-route_set_metric_compile(const char *arg)
+static route_map_result_t route_set_metric(void *rule,
+ const struct prefix *prefix,
+ route_map_object_t type,
+ void *object)
{
- unsigned long metric;
- char *endp;
- uint32_t *ret;
+ uint32_t *metric;
+ struct isis_ext_info *info;
- metric = strtoul(arg, &endp, 10);
- if (arg[0] == '\0' || *endp != '\0' || metric > MAX_WIDE_PATH_METRIC)
- return NULL;
+ if (type == RMAP_ISIS) {
+ metric = rule;
+ info = object;
- ret = XCALLOC(MTYPE_ROUTE_MAP_COMPILED, sizeof(*ret));
- *ret = metric;
-
- return ret;
+ info->metric = *metric;
+ }
+ return RMAP_OKAY;
}
-static void
-route_set_metric_free(void *rule)
+static void *route_set_metric_compile(const char *arg)
{
- XFREE(MTYPE_ROUTE_MAP_COMPILED, rule);
-}
+ unsigned long metric;
+ char *endp;
+ uint32_t *ret;
-static struct route_map_rule_cmd route_set_metric_cmd =
-{
- "metric",
- route_set_metric,
- route_set_metric_compile,
- route_set_metric_free
-};
+ metric = strtoul(arg, &endp, 10);
+ if (arg[0] == '\0' || *endp != '\0' || metric > MAX_WIDE_PATH_METRIC)
+ return NULL;
-/* ------------------------------------------------------------*/
+ ret = XCALLOC(MTYPE_ROUTE_MAP_COMPILED, sizeof(*ret));
+ *ret = metric;
-static int
-isis_route_match_add(struct vty *vty,
- const char *command, const char *arg)
-{
- VTY_DECLVAR_CONTEXT (route_map_index, index);
- int ret;
-
- ret = route_map_add_match (index, command, arg);
- if (ret)
- {
- switch (ret)
- {
- case RMAP_RULE_MISSING:
- vty_out (vty, "%% Can't find rule.%s", VTY_NEWLINE);
- return CMD_WARNING;
- case RMAP_COMPILE_ERROR:
- vty_out (vty, "%% Argument is malformed.%s", VTY_NEWLINE);
- return CMD_WARNING;
- }
- }
- return CMD_SUCCESS;
+ return ret;
}
-static int
-isis_route_match_delete(struct vty *vty,
- const char *command, const char *arg)
+static void route_set_metric_free(void *rule)
{
- VTY_DECLVAR_CONTEXT (route_map_index, index);
- int ret;
-
- ret = route_map_delete_match (index, command, arg);
- if (ret)
- {
- switch (ret)
- {
- case RMAP_RULE_MISSING:
- vty_out (vty, "%% Can't find rule.%s", VTY_NEWLINE);
- return CMD_WARNING;
- case RMAP_COMPILE_ERROR:
- vty_out (vty, "%% Argument is malformed.%s", VTY_NEWLINE);
- return CMD_WARNING;
- }
- }
- return CMD_SUCCESS;
+ XFREE(MTYPE_ROUTE_MAP_COMPILED, rule);
}
-static int
-isis_route_set_add(struct vty *vty,
- const char *command, const char *arg)
-{
- VTY_DECLVAR_CONTEXT (route_map_index, index);
- int ret;
-
- ret = route_map_add_set(index, command, arg);
- if (ret)
- {
- switch (ret)
- {
- case RMAP_RULE_MISSING:
- vty_out (vty, "%% Can't find rule.%s", VTY_NEWLINE);
- return CMD_WARNING;
- case RMAP_COMPILE_ERROR:
- vty_out (vty, "%% Argument is malformed.%s", VTY_NEWLINE);
- return CMD_WARNING;
- }
- }
-
- return CMD_SUCCESS;
-}
+static struct route_map_rule_cmd route_set_metric_cmd = {
+ "metric", route_set_metric, route_set_metric_compile,
+ route_set_metric_free};
-static int
-isis_route_set_delete (struct vty *vty,
- const char *command, const char *arg)
+void isis_route_map_init(void)
{
- VTY_DECLVAR_CONTEXT (route_map_index, index);
- int ret;
-
- ret = route_map_delete_set (index, command, arg);
- if (ret)
- {
- switch (ret)
- {
- case RMAP_RULE_MISSING:
- vty_out (vty, "%% Can't find rule.%s", VTY_NEWLINE);
- return CMD_WARNING;
- case RMAP_COMPILE_ERROR:
- vty_out (vty, "%% Argument is malformed.%s", VTY_NEWLINE);
- return CMD_WARNING;
- }
- }
-
- return CMD_SUCCESS;
-}
-
-/* ------------------------------------------------------------*/
+ route_map_init();
-DEFUN (match_ip_address,
- match_ip_address_cmd,
- "match ip address (<1-199>|<1300-2699>|WORD)",
- MATCH_STR
- IP_STR
- "Match address of route\n"
- "IP access-list number\n"
- "IP access-list number (expanded range)\n"
- "IP Access-list name\n")
-{
- return isis_route_match_add(vty, "ip address", argv[0]);
-}
+ route_map_match_ip_address_hook(generic_match_add);
+ route_map_no_match_ip_address_hook(generic_match_delete);
-DEFUN (no_match_ip_address,
- no_match_ip_address_val_cmd,
- "no match ip address (<1-199>|<1300-2699>|WORD)",
- NO_STR
- MATCH_STR
- IP_STR
- "Match address of route\n"
- "IP access-list number\n"
- "IP access-list number (expanded range)\n"
- "IP Access-list name\n")
-{
- if (argc == 0)
- return isis_route_match_delete(vty, "ip address", NULL);
- return isis_route_match_delete(vty, "ip address", argv[0]);
-}
+ route_map_match_ip_address_prefix_list_hook(generic_match_add);
+ route_map_no_match_ip_address_prefix_list_hook(generic_match_delete);
-ALIAS (no_match_ip_address,
- no_match_ip_address_cmd,
- "no match ip address",
- NO_STR
- MATCH_STR
- IP_STR
- "Match address of route\n")
+ route_map_match_ipv6_address_hook(generic_match_add);
+ route_map_no_match_ipv6_address_hook(generic_match_delete);
-/* ------------------------------------------------------------*/
+ route_map_match_ipv6_address_prefix_list_hook(generic_match_add);
+ route_map_no_match_ipv6_address_prefix_list_hook(generic_match_delete);
-DEFUN (match_ip_address_prefix_list,
- match_ip_address_prefix_list_cmd,
- "match ip address prefix-list WORD",
- MATCH_STR
- IP_STR
- "Match address of route\n"
- "Match entries of prefix-lists\n"
- "IP prefix-list name\n")
-{
- return isis_route_match_add(vty, "ip address prefix-list", argv[0]);
-}
+ route_map_set_metric_hook(generic_set_add);
+ route_map_no_set_metric_hook(generic_set_delete);
-DEFUN (no_match_ip_address_prefix_list,
- no_match_ip_address_prefix_list_cmd,
- "no match ip address prefix-list",
- NO_STR
- MATCH_STR
- IP_STR
- "Match address of route\n"
- "Match entries of prefix-lists\n")
-{
- if (argc == 0)
- return isis_route_match_delete (vty, "ip address prefix-list", NULL);
- return isis_route_match_delete (vty, "ip address prefix-list", argv[0]);
-}
-
-ALIAS (no_match_ip_address_prefix_list,
- no_match_ip_address_prefix_list_val_cmd,
- "no match ip address prefix-list WORD",
- NO_STR
- MATCH_STR
- IP_STR
- "Match address of route\n"
- "Match entries of prefix-lists\n"
- "IP prefix-list name\n")
-
-/* ------------------------------------------------------------*/
-
-DEFUN (match_ipv6_address,
- match_ipv6_address_cmd,
- "match ipv6 address WORD",
- MATCH_STR
- IPV6_STR
- "Match IPv6 address of route\n"
- "IPv6 access-list name\n")
-{
- return isis_route_match_add(vty, "ipv6 address", argv[0]);
-}
-
-DEFUN (no_match_ipv6_address,
- no_match_ipv6_address_val_cmd,
- "no match ipv6 address WORD",
- NO_STR
- MATCH_STR
- IPV6_STR
- "Match IPv6 address of route\n"
- "IPv6 access-list name\n")
-{
- if (argc == 0)
- return isis_route_match_delete(vty, "ipv6 address", NULL);
- return isis_route_match_delete(vty, "ipv6 address", argv[0]);
-}
-
-ALIAS (no_match_ipv6_address,
- no_match_ipv6_address_cmd,
- "no match ipv6 address",
- NO_STR
- MATCH_STR
- IPV6_STR
- "Match IPv6 address of route\n")
-
-/* ------------------------------------------------------------*/
-
-DEFUN (match_ipv6_address_prefix_list,
- match_ipv6_address_prefix_list_cmd,
- "match ipv6 address prefix-list WORD",
- MATCH_STR
- IPV6_STR
- "Match address of route\n"
- "Match entries of prefix-lists\n"
- "IP prefix-list name\n")
-{
- return isis_route_match_add(vty, "ipv6 address prefix-list", argv[0]);
-}
-
-DEFUN (no_match_ipv6_address_prefix_list,
- no_match_ipv6_address_prefix_list_cmd,
- "no match ipv6 address prefix-list",
- NO_STR
- MATCH_STR
- IPV6_STR
- "Match address of route\n"
- "Match entries of prefix-lists\n")
-{
- if (argc == 0)
- return isis_route_match_delete (vty, "ipv6 address prefix-list", NULL);
- return isis_route_match_delete (vty, "ipv6 address prefix-list", argv[0]);
-}
-
-ALIAS (no_match_ipv6_address_prefix_list,
- no_match_ipv6_address_prefix_list_val_cmd,
- "no match ipv6 address prefix-list WORD",
- NO_STR
- MATCH_STR
- IPV6_STR
- "Match address of route\n"
- "Match entries of prefix-lists\n"
- "IP prefix-list name\n")
-
-/* ------------------------------------------------------------*/
-
-/* set metric already exists e.g. in the ospf routemap. vtysh doesn't cope well with different
- * commands at the same node, therefore add set metric with the same 32-bit range as ospf and
- * verify that the input is a valid isis metric */
-DEFUN (set_metric,
- set_metric_cmd,
- "set metric <0-4294967295>",
- SET_STR
- "Metric vale for destination routing protocol\n"
- "Metric value\n")
-{
- return isis_route_set_add(vty, "metric", argv[0]);
-}
-
-DEFUN (no_set_metric,
- no_set_metric_val_cmd,
- "no set metric <0-4294967295>",
- NO_STR
- SET_STR
- "Metric value for destination routing protocol\n"
- "Metric value\n")
-{
- if (argc == 0)
- return isis_route_set_delete(vty, "metric", NULL);
- return isis_route_set_delete(vty, "metric", argv[0]);
-}
-
-ALIAS (no_set_metric,
- no_set_metric_cmd,
- "no set metric",
- NO_STR
- SET_STR
- "Metric vale for destination routing protocol\n");
-
-void
-isis_route_map_init(void)
-{
- route_map_init();
-
- route_map_install_match(&route_match_ip_address_cmd);
- install_element(RMAP_NODE, &match_ip_address_cmd);
- install_element(RMAP_NODE, &no_match_ip_address_val_cmd);
- install_element(RMAP_NODE, &no_match_ip_address_cmd);
-
- route_map_install_match(&route_match_ip_address_prefix_list_cmd);
- install_element(RMAP_NODE, &match_ip_address_prefix_list_cmd);
- install_element(RMAP_NODE, &no_match_ip_address_prefix_list_val_cmd);
- install_element(RMAP_NODE, &no_match_ip_address_prefix_list_cmd);
-
- route_map_install_match(&route_match_ipv6_address_cmd);
- install_element(RMAP_NODE, &match_ipv6_address_cmd);
- install_element(RMAP_NODE, &no_match_ipv6_address_val_cmd);
- install_element(RMAP_NODE, &no_match_ipv6_address_cmd);
-
- route_map_install_match(&route_match_ipv6_address_prefix_list_cmd);
- install_element(RMAP_NODE, &match_ipv6_address_prefix_list_cmd);
- install_element(RMAP_NODE, &no_match_ipv6_address_prefix_list_val_cmd);
- install_element(RMAP_NODE, &no_match_ipv6_address_prefix_list_cmd);
-
- route_map_install_set(&route_set_metric_cmd);
- install_element(RMAP_NODE, &set_metric_cmd);
- install_element(RMAP_NODE, &no_set_metric_val_cmd);
- install_element(RMAP_NODE, &no_set_metric_cmd);
+ route_map_install_match(&route_match_ip_address_cmd);
+ route_map_install_match(&route_match_ip_address_prefix_list_cmd);
+ route_map_install_match(&route_match_ipv6_address_cmd);
+ route_map_install_match(&route_match_ipv6_address_prefix_list_cmd);
+ route_map_install_set(&route_set_metric_cmd);
}