summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--Makefile.am3
-rw-r--r--configure.ac3
-rw-r--r--src/check_prefix_boundary.c135
-rw-r--r--templates/protocols/bgp/node.tag/aggregate-address/node.def2
-rw-r--r--templates/protocols/bgp/node.tag/network/node.def3
-rw-r--r--templates/protocols/ospf/area/node.tag/network/node.def2
-rw-r--r--templates/protocols/ospf/area/node.tag/range/node.def2
-rw-r--r--templates/protocols/ospf/area/node.tag/range/node.tag/substitute/node.def2
-rw-r--r--templates/protocols/rip/network-distance/node.def2
-rw-r--r--templates/protocols/rip/network/node.def2
-rw-r--r--templates/protocols/rip/route/node.def2
-rw-r--r--templates/protocols/static/interface-route/node.def2
-rw-r--r--templates/protocols/static/interface-route6/node.def2
-rw-r--r--templates/protocols/static/route/node.def2
-rw-r--r--templates/protocols/static/route/node.tag/next-hop/node.def28
-rw-r--r--templates/protocols/static/route6/node.def2
16 files changed, 169 insertions, 25 deletions
diff --git a/Makefile.am b/Makefile.am
index 223cf196..6772ef77 100644
--- a/Makefile.am
+++ b/Makefile.am
@@ -8,6 +8,9 @@ sbin_SCRIPTS += scripts/policy/vyatta-check-as-prepend.pl
sbin_SCRIPTS += scripts/vyatta-vtysh.pl
sbin_SCRIPTS += scripts/vyatta-policy-action-verify.pl
sbin_SCRIPTS += scripts/vyatta-gateway-static_route-check.pl
+sbin_PROGRAMS = src/check_prefix_boundary
+
+src_check_prefix_boundary = src/check_prefix_boundary.c
curver_DATA = cfg-version/quagga@1
diff --git a/configure.ac b/configure.ac
index 6489ec9a..9485cf62 100644
--- a/configure.ac
+++ b/configure.ac
@@ -15,6 +15,9 @@ AC_CONFIG_AUX_DIR([config])
AM_INIT_AUTOMAKE([gnu no-dist-gzip dist-bzip2 subdir-objects])
AC_PREFIX_DEFAULT([/opt/vyatta])
+AC_PROG_CC
+AM_PROG_CC_C_O
+
AC_ARG_ENABLE([nostrip],
AC_HELP_STRING([--enable-nostrip],
[include -nostrip option during packaging]),
diff --git a/src/check_prefix_boundary.c b/src/check_prefix_boundary.c
new file mode 100644
index 00000000..1c9ee30a
--- /dev/null
+++ b/src/check_prefix_boundary.c
@@ -0,0 +1,135 @@
+/*
+ * Check format of network prefix
+ */
+#include <stdio.h>
+#include <stdarg.h>
+#include <stdint.h>
+#include <stdlib.h>
+#include <string.h>
+#include <sys/types.h>
+#include <sys/socket.h>
+#include <arpa/inet.h>
+
+typedef struct
+{
+ uint8_t family;
+ uint8_t bytelen;
+ unsigned int plen;
+ uint32_t data[4];
+} inet_prefix;
+
+static void err(const char *fmt, ...)
+{
+ va_list ap;
+
+ va_start(ap, fmt);
+ vfprintf(stderr, fmt, ap);
+ va_end(ap);
+
+ exit(1);
+}
+
+static void usage(void)
+{
+ fprintf(stderr, "Usage: check-prefix-boundary [-4|-6] address/prefix\n");
+ exit(1);
+}
+
+static void get_addr_1(inet_prefix *addr, const char *name, int family)
+{
+ memset(addr, 0, sizeof(*addr));
+
+ if (strchr(name, ':')) {
+ addr->family = AF_INET6;
+ addr->bytelen = 16;
+ if (family != AF_UNSPEC && family != AF_INET6)
+ err("IPV6 address not allowed\n");
+
+ if (inet_pton(AF_INET6, name, addr->data) <= 0)
+ err("Invalid IPV6 address: %s\n", name);
+
+ return;
+ }
+
+ addr->family = AF_INET;
+ addr->bytelen = 4;
+ if (family != AF_UNSPEC && family != AF_INET)
+ err("IPV4 address not allowed\n");
+
+ if (inet_pton(AF_INET, name, addr->data) <= 0)
+ err("Invalid IPV4 address: %s\n", name);
+ return;
+}
+
+static void get_prefix_1(inet_prefix *dst, char *arg, int family)
+{
+ char *slash, *endp;
+
+ memset(dst, 0, sizeof(*dst));
+
+ slash = strchr(arg, '/');
+ if (!slash || slash[1] == '\0')
+ err("Missing prefix length\n");
+ *slash = 0;
+
+ get_addr_1(dst, arg, family);
+
+ dst->plen = strtoul(slash+1, &endp, 0);
+ if (*endp != '\0')
+ err("Invalid character in prefix length\n");
+
+ if (dst->plen > 8 * dst->bytelen)
+ err("Prefix length is too large\n");
+
+ *slash = '/';
+}
+
+static void get_netmask(inet_prefix *msk, const inet_prefix *dst)
+{
+ int i, plen = dst->plen;
+
+ memset(msk, 0, sizeof(*msk));
+ msk->family = dst->family;
+ msk->bytelen = dst->bytelen;
+
+ for (i = 0; plen > 0 && i < dst->bytelen / sizeof(uint32_t); i++) {
+ uint32_t m = (plen > 32) ? ~0 : htonl(~0 << (32 - plen));
+
+ msk->data[i] = dst->data[i] & m;
+ plen -= 32;
+ }
+}
+
+int main(int argc, char **argv)
+{
+ int family = AF_UNSPEC;
+
+ while (--argc) {
+ char *arg = *++argv;
+ inet_prefix dst, msk;
+
+ if (arg[0] == '-')
+ switch(arg[1]) {
+ case '4':
+ family = AF_INET;
+ break;
+ case '6':
+ family = AF_INET6;
+ break;
+ default:
+ usage();
+ }
+
+ get_prefix_1(&dst, arg, family);
+ get_netmask(&msk, &dst);
+
+ if (memcmp(msk.data, dst.data, dst.bytelen) != 0) {
+ char buf[INET_ADDRSTRLEN];
+ err("Prefix not on a natural network boundary."
+ "Did you mean %s?\n",
+ inet_ntop(msk.family, msk.data, buf, sizeof buf));
+ }
+ }
+
+ return 0;
+}
diff --git a/templates/protocols/bgp/node.tag/aggregate-address/node.def b/templates/protocols/bgp/node.tag/aggregate-address/node.def
index 6e2ba210..4f2c63bc 100644
--- a/templates/protocols/bgp/node.tag/aggregate-address/node.def
+++ b/templates/protocols/bgp/node.tag/aggregate-address/node.def
@@ -2,7 +2,7 @@ tag:
type: ipv4net
help: Set a BGP aggregate network
comp_help: \1 <x.x.x.x/x>\taggregate network
-syntax:expression: exec "/opt/vyatta/sbin/vyatta_quagga_utils.pl --check-prefix-boundry $VAR(@)"
+syntax:expression: exec "${sbin_dir}/check_prefix_boundary $VAR(@)"
delete: touch /tmp/`echo $VAR(@) | sed 's!/!!'`.$PPID
end: ${vyatta_sbindir}/vyatta-vtysh.pl -noerr \
-c "configure terminal" \
diff --git a/templates/protocols/bgp/node.tag/network/node.def b/templates/protocols/bgp/node.tag/network/node.def
index ad39bbe3..43585bc5 100644
--- a/templates/protocols/bgp/node.tag/network/node.def
+++ b/templates/protocols/bgp/node.tag/network/node.def
@@ -2,8 +2,7 @@ tag:
type: ipv4net
help: Set a BGP network
comp_help: \1 <x.x.x.x/x>\tnetwork
-syntax:expression: exec "/opt/vyatta/sbin/vyatta_quagga_utils.pl --check-prefix-boundry $VAR(@)";
- "Prefix doesn't fall on a natural boundry"
+syntax:expression: exec "${sbin_dir}/check_prefix_boundary $VAR(@)"
commit:expression: !($VAR(./backdoor/) != "" && $VAR(./route-map/) != "");
"protocols bgp $VAR(../@) network $VAR(@): May specify route-map or backdoor but not both"
delete: touch /tmp/`echo $VAR(@) | sed 's!/!!'`.$PPID
diff --git a/templates/protocols/ospf/area/node.tag/network/node.def b/templates/protocols/ospf/area/node.tag/network/node.def
index d50adfc5..8a5173f4 100644
--- a/templates/protocols/ospf/area/node.tag/network/node.def
+++ b/templates/protocols/ospf/area/node.tag/network/node.def
@@ -2,7 +2,7 @@ multi:
type: ipv4net
help: Set OSPF network
priority: 1
-syntax:expression: exec "/opt/vyatta/sbin/vyatta_quagga_utils.pl --check-prefix-boundry $VAR(@)"
+syntax:expression: exec "${sbin_dir}/check_prefix_boundary $VAR(@)"
create:expression: "${vyatta_sbindir}/vyatta-vtysh.pl -c \"configure terminal\" \
-c \"router ospf\" \
-c \"network $VAR(@) area $VAR(../@)\"; "
diff --git a/templates/protocols/ospf/area/node.tag/range/node.def b/templates/protocols/ospf/area/node.tag/range/node.def
index b8f514e2..8293a1e5 100644
--- a/templates/protocols/ospf/area/node.tag/range/node.def
+++ b/templates/protocols/ospf/area/node.tag/range/node.def
@@ -1,7 +1,7 @@
tag:
type: ipv4net
help: Set to summarize routes matching prefix (border routers only)
-syntax:expression: exec "/opt/vyatta/sbin/vyatta_quagga_utils.pl --check-prefix-boundry $VAR(@)"
+syntax:expression: exec "${sbin_dir}/check_prefix_boundary $VAR(@)"
delete: touch /tmp/ospf-range.$PPID
diff --git a/templates/protocols/ospf/area/node.tag/range/node.tag/substitute/node.def b/templates/protocols/ospf/area/node.tag/range/node.tag/substitute/node.def
index 67ef935a..ceb6ff7f 100644
--- a/templates/protocols/ospf/area/node.tag/range/node.tag/substitute/node.def
+++ b/templates/protocols/ospf/area/node.tag/range/node.tag/substitute/node.def
@@ -1,3 +1,3 @@
type: ipv4net
help: Set to announce area range as another prefix
-syntax:expression: exec "/opt/vyatta/sbin/vyatta_quagga_utils.pl --check-prefix-boundry $VAR(@)"
+syntax:expression: exec "${sbin_dir}/check_prefix_boundary $VAR(@)"
diff --git a/templates/protocols/rip/network-distance/node.def b/templates/protocols/rip/network-distance/node.def
index e0e64003..bb8a483e 100644
--- a/templates/protocols/rip/network-distance/node.def
+++ b/templates/protocols/rip/network-distance/node.def
@@ -1,7 +1,7 @@
tag:
type: ipv4net
help: Set source network
-syntax:expression: exec "/opt/vyatta/sbin/vyatta_quagga_utils.pl --check-prefix-boundry $VAR(@)"
+syntax:expression: exec "${sbin_dir}/check_prefix_boundary $VAR(@)"
commit:expression: $VAR(./distance/) != ""; "Must specify distance for network $VAR(@)"
delete:expression: "touch /tmp/rip-dist.$PPID"
end:expression: "if [ -n \"$VAR(./access-list/@)\" ]; then \
diff --git a/templates/protocols/rip/network/node.def b/templates/protocols/rip/network/node.def
index 07c36d73..4fd37c09 100644
--- a/templates/protocols/rip/network/node.def
+++ b/templates/protocols/rip/network/node.def
@@ -1,7 +1,7 @@
multi:
type: ipv4net
help: Set RIP network
-syntax:expression: exec "/opt/vyatta/sbin/vyatta_quagga_utils.pl --check-prefix-boundry $VAR(@)"
+syntax:expression: exec "${sbin_dir}/check_prefix_boundary $VAR(@)"
create:expression: "${vyatta_sbindir}/vyatta-vtysh.pl -c \"configure terminal\" -c \"router rip\" \
-c \"network $VAR(@)\"; "
delete:expression: "${vyatta_sbindir}/vyatta-vtysh.pl -c \"configure terminal\" -c \"router rip\" \
diff --git a/templates/protocols/rip/route/node.def b/templates/protocols/rip/route/node.def
index 58b6c206..067b8fc1 100644
--- a/templates/protocols/rip/route/node.def
+++ b/templates/protocols/rip/route/node.def
@@ -1,7 +1,7 @@
multi:
type: ipv4net
help: Set RIP static route
-syntax:expression: exec "/opt/vyatta/sbin/vyatta_quagga_utils.pl --check-prefix-boundry $VAR(@)"
+syntax:expression: exec "${sbin_dir}/check_prefix_boundary $VAR(@)"
create:expression: "${vyatta_sbindir}/vyatta-vtysh.pl -c \"configure terminal\" -c \"router rip\" \
-c \"route $VAR(@)\" "
delete:expression: "${vyatta_sbindir}/vyatta-vtysh.pl -c \"configure terminal\" -c \"router rip\" \
diff --git a/templates/protocols/static/interface-route/node.def b/templates/protocols/static/interface-route/node.def
index 0e732ea9..5317a93c 100644
--- a/templates/protocols/static/interface-route/node.def
+++ b/templates/protocols/static/interface-route/node.def
@@ -1,4 +1,4 @@
tag:
type: ipv4net
help: Set an interface-based static route
-syntax:expression: exec "/opt/vyatta/sbin/vyatta_quagga_utils.pl --check-prefix-boundry $VAR(@)"
+syntax:expression: exec "${sbin_dir}/check_prefix_boundary $VAR(@)"
diff --git a/templates/protocols/static/interface-route6/node.def b/templates/protocols/static/interface-route6/node.def
index 04624589..1f2f561a 100644
--- a/templates/protocols/static/interface-route6/node.def
+++ b/templates/protocols/static/interface-route6/node.def
@@ -1,4 +1,4 @@
tag:
type: ipv6net
help: Set an interface-based IPv6 static route
-syntax:expression: exec "/opt/vyatta/sbin/vyatta_quagga_utils.pl --check-prefix-boundry $VAR(@)"
+syntax:expression: exec "${sbin_dir}/check_prefix_boundary $VAR(@)"
diff --git a/templates/protocols/static/route/node.def b/templates/protocols/static/route/node.def
index 78ead81d..9f5eb0db 100644
--- a/templates/protocols/static/route/node.def
+++ b/templates/protocols/static/route/node.def
@@ -1,4 +1,4 @@
tag:
type: ipv4net
help: Set a static route
-syntax:expression: exec "/opt/vyatta/sbin/vyatta_quagga_utils.pl --check-prefix-boundry $VAR(@)"
+syntax:expression: exec "${sbin_dir}/check_prefix_boundary $VAR(@)"
diff --git a/templates/protocols/static/route/node.tag/next-hop/node.def b/templates/protocols/static/route/node.tag/next-hop/node.def
index 1bb4b579..f93b1270 100644
--- a/templates/protocols/static/route/node.tag/next-hop/node.def
+++ b/templates/protocols/static/route/node.tag/next-hop/node.def
@@ -1,15 +1,19 @@
tag:
type: ipv4
help: Set the next-hop router
-delete:expression: "touch /tmp/static.$PPID"
-end:expression: "if [ -f \"/tmp/static.$PPID\" ]; then \
- if ${vyatta_sbindir}/vyatta-gateway-static_route-check.pl \"$VAR(../@)\" \"$VAR(@)\"; then \
- ${vyatta_sbindir}/vyatta-vtysh.pl -c \"configure terminal\" -c \"no ip route $VAR(../@) $VAR(@)\" ; \
- fi;
- rm /tmp/static.$PPID; \
- else \
- if [ -n \"$VAR(./distance/@)\" ]; then \
- DIST=\"$VAR(./distance/@)\"; \
- fi; \
- ${vyatta_sbindir}/vyatta-vtysh.pl -c \"configure terminal\" -c \"ip route $VAR(../@) $VAR(@) $DIST \" ; \
- fi; "
+delete: touch /tmp/static.$PPID
+end: if [[ -f /tmp/static.$PPID ]]
+ then
+ if ${vyatta_sbindir}/vyatta-gateway-static_route-check.pl \
+ "$VAR(../@)" "$VAR(@)"
+ then
+ vyatta-vtysh -c "configure terminal" -c "no ip route $VAR(../@) $VAR(@)"
+ fi
+ rm -f /tmp/static.$PPID
+ else
+ if [[ -n "$VAR(./distance/@)" ]]
+ then
+ DIST="$VAR(./distance/@)"
+ fi
+ vyatta-vtysh -c "configure terminal" -c "ip route $VAR(../@) $VAR(@) $DIST" ; \
+ fi
diff --git a/templates/protocols/static/route6/node.def b/templates/protocols/static/route6/node.def
index 7f95d0be..86ca5826 100644
--- a/templates/protocols/static/route6/node.def
+++ b/templates/protocols/static/route6/node.def
@@ -1,4 +1,4 @@
tag:
type: ipv6net
help: Set a static IPv6 route
-syntax:expression: exec "/opt/vyatta/sbin/vyatta_quagga_utils.pl --check-prefix-boundry $VAR(@)"
+syntax:expression: exec "${sbin_dir}/check_prefix_boundary $VAR(@)"