summaryrefslogtreecommitdiffstats
path: root/zebra/zebra_mpls_netlink.c
diff options
context:
space:
mode:
Diffstat (limited to 'zebra/zebra_mpls_netlink.c')
-rw-r--r--zebra/zebra_mpls_netlink.c88
1 files changed, 88 insertions, 0 deletions
diff --git a/zebra/zebra_mpls_netlink.c b/zebra/zebra_mpls_netlink.c
new file mode 100644
index 0000000..ce7702b
--- /dev/null
+++ b/zebra/zebra_mpls_netlink.c
@@ -0,0 +1,88 @@
+/* MPLS forwarding table updates using netlink over GNU/Linux system.
+ * Copyright (C) 2016 Cumulus Networks, Inc.
+ *
+ * This file is part of Quagga.
+ *
+ * Quagga 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, or (at your option) any
+ * later version.
+ *
+ * Quagga 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; 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>
+
+#ifdef HAVE_NETLINK
+
+#include "zebra/debug.h"
+#include "zebra/rt.h"
+#include "zebra/rt_netlink.h"
+#include "zebra/zebra_mpls.h"
+#include "zebra/kernel_netlink.h"
+
+ssize_t netlink_lsp_msg_encoder(struct zebra_dplane_ctx *ctx, void *buf,
+ size_t buflen)
+{
+ int cmd;
+
+ /* Call to netlink layer based on type of update */
+ if (dplane_ctx_get_op(ctx) == DPLANE_OP_LSP_DELETE) {
+ cmd = RTM_DELROUTE;
+ } else if (dplane_ctx_get_op(ctx) == DPLANE_OP_LSP_INSTALL ||
+ dplane_ctx_get_op(ctx) == DPLANE_OP_LSP_UPDATE) {
+
+ /* Validate */
+ if (dplane_ctx_get_best_nhlfe(ctx) == NULL) {
+ if (IS_ZEBRA_DEBUG_KERNEL || IS_ZEBRA_DEBUG_MPLS)
+ zlog_debug("LSP in-label %u: update fails, no best NHLFE",
+ dplane_ctx_get_in_label(ctx));
+ return -1;
+ }
+
+ cmd = RTM_NEWROUTE;
+ } else
+ /* Invalid op? */
+ return -1;
+
+ return netlink_mpls_multipath_msg_encode(cmd, ctx, buf, buflen);
+}
+
+enum netlink_msg_status netlink_put_lsp_update_msg(struct nl_batch *bth,
+ struct zebra_dplane_ctx *ctx)
+{
+ return netlink_batch_add_msg(bth, ctx, netlink_lsp_msg_encoder, false);
+}
+
+/*
+ * Pseudowire update api - not supported by netlink as of 12/18,
+ * but note that the default has been to report 'success' for pw updates
+ * on unsupported platforms.
+ */
+enum netlink_msg_status netlink_put_pw_update_msg(struct nl_batch *bth,
+ struct zebra_dplane_ctx *ctx)
+{
+ return FRR_NETLINK_SUCCESS;
+}
+
+int mpls_kernel_init(void)
+{
+ struct stat st;
+
+ /*
+ * Check if the MPLS module is loaded in the kernel.
+ */
+ if (stat("/proc/sys/net/mpls", &st) != 0)
+ return -1;
+
+ return 0;
+};
+
+#endif /* HAVE_NETLINK */