summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--bgpd/bgp_nexthop.c6
-rw-r--r--bgpd/bgp_zebra.c64
-rw-r--r--isisd/isis_zebra.c55
-rw-r--r--lib/memtypes.c1
-rw-r--r--lib/vrf.c93
-rw-r--r--lib/vrf.h13
-rw-r--r--lib/zclient.c151
-rw-r--r--lib/zclient.h63
-rw-r--r--lib/zebra.h3
-rw-r--r--ospf6d/ospf6_zebra.c69
-rw-r--r--ospf6d/ospf6_zebra.h3
-rw-r--r--ospfd/ospf_vty.c3
-rw-r--r--ospfd/ospf_zebra.c65
-rw-r--r--pimd/pim_zebra.c38
-rw-r--r--pimd/pim_zlookup.c2
-rw-r--r--ripd/rip_interface.c27
-rw-r--r--ripd/rip_interface.h18
-rw-r--r--ripd/rip_zebra.c54
-rw-r--r--ripngd/ripng_interface.c26
-rw-r--r--ripngd/ripng_zebra.c53
-rw-r--r--ripngd/ripngd.h18
-rw-r--r--zebra/client_main.c1
-rw-r--r--zebra/redistribute.c49
-rw-r--r--zebra/redistribute.h12
-rw-r--r--zebra/redistribute_null.c12
-rw-r--r--zebra/zserv.c182
-rw-r--r--zebra/zserv.h9
27 files changed, 705 insertions, 385 deletions
diff --git a/bgpd/bgp_nexthop.c b/bgpd/bgp_nexthop.c
index 6218e670..7336793e 100644
--- a/bgpd/bgp_nexthop.c
+++ b/bgpd/bgp_nexthop.c
@@ -873,7 +873,7 @@ zlookup_query (struct in_addr addr)
s = zlookup->obuf;
stream_reset (s);
- zclient_create_header (s, ZEBRA_IPV4_NEXTHOP_LOOKUP);
+ zclient_create_header (s, ZEBRA_IPV4_NEXTHOP_LOOKUP, VRF_DEFAULT);
stream_put_in_addr (s, &addr);
stream_putw_at (s, 0, stream_get_endp (s));
@@ -988,7 +988,7 @@ zlookup_query_ipv6 (struct in6_addr *addr)
s = zlookup->obuf;
stream_reset (s);
- zclient_create_header (s, ZEBRA_IPV6_NEXTHOP_LOOKUP);
+ zclient_create_header (s, ZEBRA_IPV6_NEXTHOP_LOOKUP, VRF_DEFAULT);
stream_put (s, addr, 16);
stream_putw_at (s, 0, stream_get_endp (s));
@@ -1038,7 +1038,7 @@ bgp_import_check (struct prefix *p, u_int32_t *igpmetric,
/* Send query to the lookup connection */
s = zlookup->obuf;
stream_reset (s);
- zclient_create_header (s, ZEBRA_IPV4_IMPORT_LOOKUP);
+ zclient_create_header (s, ZEBRA_IPV4_IMPORT_LOOKUP, VRF_DEFAULT);
stream_putc (s, p->prefixlen);
stream_put_in_addr (s, &p->u.prefix4);
diff --git a/bgpd/bgp_zebra.c b/bgpd/bgp_zebra.c
index 13f71de9..26163516 100644
--- a/bgpd/bgp_zebra.c
+++ b/bgpd/bgp_zebra.c
@@ -48,7 +48,8 @@ struct stream *bgp_nexthop_buf = NULL;
/* Router-id update message from zebra. */
static int
-bgp_router_id_update (int command, struct zclient *zclient, zebra_size_t length)
+bgp_router_id_update (int command, struct zclient *zclient, zebra_size_t length,
+ vrf_id_t vrf_id)
{
struct prefix router_id;
struct listnode *node, *nnode;
@@ -76,11 +77,12 @@ bgp_router_id_update (int command, struct zclient *zclient, zebra_size_t length)
/* Inteface addition message from zebra. */
static int
-bgp_interface_add (int command, struct zclient *zclient, zebra_size_t length)
+bgp_interface_add (int command, struct zclient *zclient, zebra_size_t length,
+ vrf_id_t vrf_id)
{
struct interface *ifp;
- ifp = zebra_interface_add_read (zclient->ibuf);
+ ifp = zebra_interface_add_read (zclient->ibuf, vrf_id);
if (BGP_DEBUG(zebra, ZEBRA) && ifp)
zlog_debug("Zebra rcvd: interface add %s", ifp->name);
@@ -90,13 +92,13 @@ bgp_interface_add (int command, struct zclient *zclient, zebra_size_t length)
static int
bgp_interface_delete (int command, struct zclient *zclient,
- zebra_size_t length)
+ zebra_size_t length, vrf_id_t vrf_id)
{
struct stream *s;
struct interface *ifp;
s = zclient->ibuf;
- ifp = zebra_interface_state_read (s);
+ ifp = zebra_interface_state_read (s, vrf_id);
ifp->ifindex = IFINDEX_INTERNAL;
if (BGP_DEBUG(zebra, ZEBRA))
@@ -106,7 +108,8 @@ bgp_interface_delete (int command, struct zclient *zclient,
}
static int
-bgp_interface_up (int command, struct zclient *zclient, zebra_size_t length)
+bgp_interface_up (int command, struct zclient *zclient, zebra_size_t length,
+ vrf_id_t vrf_id)
{
struct stream *s;
struct interface *ifp;
@@ -114,7 +117,7 @@ bgp_interface_up (int command, struct zclient *zclient, zebra_size_t length)
struct listnode *node, *nnode;
s = zclient->ibuf;
- ifp = zebra_interface_state_read (s);
+ ifp = zebra_interface_state_read (s, vrf_id);
if (! ifp)
return 0;
@@ -129,7 +132,8 @@ bgp_interface_up (int command, struct zclient *zclient, zebra_size_t length)
}
static int
-bgp_interface_down (int command, struct zclient *zclient, zebra_size_t length)
+bgp_interface_down (int command, struct zclient *zclient, zebra_size_t length,
+ vrf_id_t vrf_id)
{
struct stream *s;
struct interface *ifp;
@@ -137,7 +141,7 @@ bgp_interface_down (int command, struct zclient *zclient, zebra_size_t length)
struct listnode *node, *nnode;
s = zclient->ibuf;
- ifp = zebra_interface_state_read (s);
+ ifp = zebra_interface_state_read (s, vrf_id);
if (! ifp)
return 0;
@@ -174,11 +178,11 @@ bgp_interface_down (int command, struct zclient *zclient, zebra_size_t length)
static int
bgp_interface_address_add (int command, struct zclient *zclient,
- zebra_size_t length)
+ zebra_size_t length, vrf_id_t vrf_id)
{
struct connected *ifc;
- ifc = zebra_interface_address_read (command, zclient->ibuf);
+ ifc = zebra_interface_address_read (command, zclient->ibuf, vrf_id);
if (ifc == NULL)
return 0;
@@ -199,11 +203,11 @@ bgp_interface_address_add (int command, struct zclient *zclient,
static int
bgp_interface_address_delete (int command, struct zclient *zclient,
- zebra_size_t length)
+ zebra_size_t length, vrf_id_t vrf_id)
{
struct connected *ifc;
- ifc = zebra_interface_address_read (command, zclient->ibuf);
+ ifc = zebra_interface_address_read (command, zclient->ibuf, vrf_id);
if (ifc == NULL)
return 0;
@@ -226,7 +230,8 @@ bgp_interface_address_delete (int command, struct zclient *zclient,
/* Zebra route add and delete treatment. */
static int
-zebra_read_ipv4 (int command, struct zclient *zclient, zebra_size_t length)
+zebra_read_ipv4 (int command, struct zclient *zclient, zebra_size_t length,
+ vrf_id_t vrf_id)
{
struct stream *s;
struct zapi_ipv4 api;
@@ -302,7 +307,8 @@ zebra_read_ipv4 (int command, struct zclient *zclient, zebra_size_t length)
#ifdef HAVE_IPV6
/* Zebra route add and delete treatment. */
static int
-zebra_read_ipv6 (int command, struct zclient *zclient, zebra_size_t length)
+zebra_read_ipv6 (int command, struct zclient *zclient, zebra_size_t length,
+ vrf_id_t vrf_id)
{
struct stream *s;
struct zapi_ipv6 api;
@@ -672,7 +678,7 @@ bgp_zebra_announce (struct prefix *p, struct bgp_info *info, struct bgp *bgp, sa
if (zclient->sock < 0)
return;
- if (! zclient->redist[ZEBRA_ROUTE_BGP])
+ if (! vrf_bitmap_check (zclient->redist[ZEBRA_ROUTE_BGP], VRF_DEFAULT))
return;
flags = 0;
@@ -708,6 +714,7 @@ bgp_zebra_announce (struct prefix *p, struct bgp_info *info, struct bgp *bgp, sa
struct zapi_ipv4 api;
struct in_addr *nexthop;
+ api.vrf_id = VRF_DEFAULT;
api.flags = flags;
nexthop = &info->attr->nexthop;
stream_put (bgp_nexthop_buf, &nexthop, sizeof (struct in_addr *));
@@ -798,6 +805,7 @@ bgp_zebra_announce (struct prefix *p, struct bgp_info *info, struct bgp *bgp, sa
}
/* Make Zebra API structure. */
+ api.vrf_id = VRF_DEFAULT;
api.flags = flags;
api.type = ZEBRA_ROUTE_BGP;
api.message = 0;
@@ -836,7 +844,7 @@ bgp_zebra_withdraw (struct prefix *p, struct bgp_info *info, safi_t safi)
if (zclient->sock < 0)
return;
- if (! zclient->redist[ZEBRA_ROUTE_BGP])
+ if (! vrf_bitmap_check (zclient->redist[ZEBRA_ROUTE_BGP], VRF_DEFAULT))
return;
peer = info->peer;
@@ -857,6 +865,7 @@ bgp_zebra_withdraw (struct prefix *p, struct bgp_info *info, safi_t safi)
struct zapi_ipv4 api;
struct in_addr *nexthop;
+ api.vrf_id = VRF_DEFAULT;
api.flags = flags;
nexthop = &info->attr->nexthop;
@@ -915,6 +924,7 @@ bgp_zebra_withdraw (struct prefix *p, struct bgp_info *info, safi_t safi)
if (info->peer->ifname)
ifindex = ifname2ifindex (info->peer->ifname);
+ api.vrf_id = VRF_DEFAULT;
api.flags = flags;
api.type = ZEBRA_ROUTE_BGP;
api.message = 0;
@@ -952,10 +962,10 @@ bgp_redistribute_set (struct bgp *bgp, afi_t afi, int type)
bgp->redist[afi][type] = 1;
/* Return if already redistribute flag is set. */
- if (zclient->redist[type])
+ if (vrf_bitmap_check (zclient->redist[type], VRF_DEFAULT))
return CMD_WARNING;
- zclient->redist[type] = 1;
+ vrf_bitmap_set (zclient->redist[type], VRF_DEFAULT);
/* Return if zebra connection is not established. */
if (zclient->sock < 0)
@@ -965,7 +975,7 @@ bgp_redistribute_set (struct bgp *bgp, afi_t afi, int type)
zlog_debug("Zebra send: redistribute add %s", zebra_route_string(type));
/* Send distribute add message to zebra. */
- zebra_redistribute_send (ZEBRA_REDISTRIBUTE_ADD, zclient, type);
+ zebra_redistribute_send (ZEBRA_REDISTRIBUTE_ADD, zclient, type, VRF_DEFAULT);
return CMD_SUCCESS;
}
@@ -1020,9 +1030,9 @@ bgp_redistribute_unset (struct bgp *bgp, afi_t afi, int type)
bgp->redist_metric[afi][type] = 0;
/* Return if zebra connection is disabled. */
- if (! zclient->redist[type])
+ if (! vrf_bitmap_check (zclient->redist[type], VRF_DEFAULT))
return CMD_WARNING;
- zclient->redist[type] = 0;
+ vrf_bitmap_unset (zclient->redist[type], VRF_DEFAULT);
if (bgp->redist[AFI_IP][type] == 0
&& bgp->redist[AFI_IP6][type] == 0
@@ -1032,7 +1042,8 @@ bgp_redistribute_unset (struct bgp *bgp, afi_t afi, int type)
if (BGP_DEBUG(zebra, ZEBRA))
zlog_debug("Zebra send: redistribute delete %s",
zebra_route_string(type));
- zebra_redistribute_send (ZEBRA_REDISTRIBUTE_DELETE, zclient, type);
+ zebra_redistribute_send (ZEBRA_REDISTRIBUTE_DELETE, zclient, type,
+ VRF_DEFAULT);
}
/* Withdraw redistributed routes from current BGP's routing table. */
@@ -1076,12 +1087,19 @@ bgp_zclient_reset (void)
zclient_reset (zclient);
}
+static void
+bgp_zebra_connected (struct zclient *zclient)
+{
+ zclient_send_requests (zclient, VRF_DEFAULT);
+}
+
void
bgp_zebra_init (void)
{
/* Set default values. */
zclient = zclient_new ();
zclient_init (zclient, ZEBRA_ROUTE_BGP);
+ zclient->zebra_connected = bgp_zebra_connected;
zclient->router_id_update = bgp_router_id_update;
zclient->interface_add = bgp_interface_add;
zclient->interface_delete = bgp_interface_delete;
diff --git a/isisd/isis_zebra.c b/isisd/isis_zebra.c
index 1ba0100d..6d0c1571 100644
--- a/isisd/isis_zebra.c
+++ b/isisd/isis_zebra.c
@@ -32,6 +32,7 @@
#include "zclient.h"
#include "stream.h"
#include "linklist.h"
+#include "vrf.h"
#include "isisd/dict.h"
#include "isisd/isis_constants.h"
@@ -52,7 +53,7 @@ struct zclient *zclient = NULL;
/* Router-id update message from zebra. */
static int
isis_router_id_update_zebra (int command, struct zclient *zclient,
- zebra_size_t length)
+ zebra_size_t length, vrf_id_t vrf_id)
{
struct isis_area *area;
struct listnode *node;
@@ -71,11 +72,12 @@ isis_router_id_update_zebra (int command, struct zclient *zclient,
}
static int
-isis_zebra_if_add (int command, struct zclient *zclient, zebra_size_t length)
+isis_zebra_if_add (int command, struct zclient *zclient, zebra_size_t length,
+ vrf_id_t vrf_id)
{
struct interface *ifp;
- ifp = zebra_interface_add_read (zclient->ibuf);
+ ifp = zebra_interface_add_read (zclient->ibuf, vrf_id);
if (isis->debugs & DEBUG_ZEBRA)
zlog_debug ("Zebra I/F add: %s index %d flags %ld metric %d mtu %d",
@@ -88,13 +90,14 @@ isis_zebra_if_add (int command, struct zclient *zclient, zebra_size_t length)
}
static int
-isis_zebra_if_del (int command, struct zclient *zclient, zebra_size_t length)
+isis_zebra_if_del (int command, struct zclient *zclient, zebra_size_t length,
+ vrf_id_t vrf_id)
{
struct interface *ifp;
struct stream *s;
s = zclient->ibuf;
- ifp = zebra_interface_state_read (s);
+ ifp = zebra_interface_state_read (s, vrf_id);
if (!ifp)
return 0;
@@ -120,11 +123,11 @@ isis_zebra_if_del (int command, struct zclient *zclient, zebra_size_t length)
static int
isis_zebra_if_state_up (int command, struct zclient *zclient,
- zebra_size_t length)
+ zebra_size_t length, vrf_id_t vrf_id)
{
struct interface *ifp;
- ifp = zebra_interface_state_read (zclient->ibuf);
+ ifp = zebra_interface_state_read (zclient->ibuf, vrf_id);
if (ifp == NULL)
return 0;
@@ -136,12 +139,12 @@ isis_zebra_if_state_up (int command, struct zclient *zclient,
static int
isis_zebra_if_state_down (int command, struct zclient *zclient,
- zebra_size_t length)
+ zebra_size_t length, vrf_id_t vrf_id)
{
struct interface *ifp;
struct isis_circuit *circuit;
- ifp = zebra_interface_state_read (zclient->ibuf);
+ ifp = zebra_interface_state_read (zclient->ibuf, vrf_id);
if (ifp == NULL)
return 0;
@@ -156,14 +159,14 @@ isis_zebra_if_state_down (int command, struct zclient *zclient,
static int
isis_zebra_if_address_add (int command, struct zclient *zclient,
- zebra_size_t length)
+ zebra_size_t length, vrf_id_t vrf_id)
{
struct connected *c;
struct prefix *p;
char buf[BUFSIZ];
c = zebra_interface_address_read (ZEBRA_INTERFACE_ADDRESS_ADD,
- zclient->ibuf);
+ zclient->ibuf, vrf_id);
if (c == NULL)
return 0;
@@ -187,7 +190,7 @@ isis_zebra_if_address_add (int command, struct zclient *zclient,
static int
isis_zebra_if_address_del (int command, struct zclient *client,
- zebra_size_t length)
+ zebra_size_t length, vrf_id_t vrf_id)
{
struct connected *c;
struct interface *ifp;
@@ -197,7 +200,7 @@ isis_zebra_if_address_del (int command, struct zclient *client,
#endif /* EXTREME_DEBUG */
c = zebra_interface_address_read (ZEBRA_INTERFACE_ADDRESS_DELETE,
- zclient->ibuf);
+ zclient->ibuf, vrf_id);
if (c == NULL)
return 0;
@@ -236,7 +239,7 @@ isis_zebra_route_add_ipv4 (struct prefix *prefix,
if (CHECK_FLAG (route_info->flag, ISIS_ROUTE_FLAG_ZEBRA_SYNCED))
return;
- if (zclient->redist[ZEBRA_ROUTE_ISIS])
+ if (vrf_bitmap_check (zclient->redist[ZEBRA_ROUTE_ISIS], VRF_DEFAULT))
{
message = 0;
flags = 0;
@@ -249,7 +252,7 @@ isis_zebra_route_add_ipv4 (struct prefix *prefix,
stream = zclient->obuf;
stream_reset (stream);
- zclient_create_header (stream, ZEBRA_IPV4_ROUTE_ADD);
+ zclient_create_header (stream, ZEBRA_IPV4_ROUTE_ADD, VRF_DEFAULT);
/* type */
stream_putc (stream, ZEBRA_ROUTE_ISIS);
/* flags */
@@ -301,8 +304,9 @@ isis_zebra_route_del_ipv4 (struct prefix *prefix,
struct zapi_ipv4 api;
struct prefix_ipv4 prefix4;
- if (zclient->redist[ZEBRA_ROUTE_ISIS])
+ if (vrf_bitmap_check (zclient->redist[ZEBRA_ROUTE_ISIS], VRF_DEFAULT))
{
+ api.vrf_id = VRF_DEFAULT;
api.type = ZEBRA_ROUTE_ISIS;
api.flags = 0;
api.message = 0;
@@ -333,6 +337,7 @@ isis_zebra_route_add_ipv6 (struct prefix *prefix,
if (CHECK_FLAG (route_info->flag, ISIS_ROUTE_FLAG_ZEBRA_SYNCED))
return;
+ api.vrf_id = VRF_DEFAULT;
api.type = ZEBRA_ROUTE_ISIS;
api.flags = 0;
api.message = 0;
@@ -418,6 +423,7 @@ isis_zebra_route_del_ipv6 (struct prefix *prefix,
if (CHECK_FLAG (route_info->flag, ISIS_ROUTE_FLAG_ZEBRA_SYNCED))
return;
+ api.vrf_id = VRF_DEFAULT;
api.type = ZEBRA_ROUTE_ISIS;
api.flags = 0;
api.message = 0;
@@ -488,7 +494,7 @@ isis_zebra_route_update (struct prefix *prefix,
if (zclient->sock < 0)
return;
- if (!zclient->redist[ZEBRA_ROUTE_ISIS])
+ if (!vrf_bitmap_check (zclient->redist[ZEBRA_ROUTE_ISIS], VRF_DEFAULT))
return;
if (CHECK_FLAG (route_info->flag, ISIS_ROUTE_FLAG_ACTIVE))
@@ -514,7 +520,7 @@ isis_zebra_route_update (struct prefix *prefix,
static int
isis_zebra_read_ipv4 (int command, struct zclient *zclient,
- zebra_size_t length)
+ zebra_size_t length, vrf_id_t vrf_id)
{
struct stream *stream;
struct zapi_ipv4 api;
@@ -563,14 +569,16 @@ isis_zebra_read_ipv4 (int command, struct zclient *zclient,
#ifdef HAVE_IPV6
static int
isis_zebra_read_ipv6 (int command, struct zclient *zclient,
- zebra_size_t length)
+ zebra_size_t length, vrf_id_t vrf_id)
{
return 0;
}
#endif
#define ISIS_TYPE_IS_REDISTRIBUTED(T) \
-T == ZEBRA_ROUTE_MAX ? zclient->default_information : zclient->redist[type]
+T == ZEBRA_ROUTE_MAX ? \
+ vrf_bitmap_check (zclient->default_information, VRF_DEFAULT) : \
+ vrf_bitmap_check (zclient->redist[type], VRF_DEFAULT)
int
isis_distribute_list_update (int routetype)
@@ -587,11 +595,18 @@ isis_redistribute_default_set (int routetype, int metric_type,
}
#endif /* 0 */
+static void
+isis_zebra_connected (struct zclient *zclient)
+{
+ zclient_send_requests (zclient, VRF_DEFAULT);
+}
+
void
isis_zebra_init ()
{
zclient = zclient_new ();
zclient_init (zclient, ZEBRA_ROUTE_ISIS);
+ zclient->zebra_connected = isis_zebra_connected;
zclient->router_id_update = isis_router_id_update_zebra;
zclient->interface_add = isis_zebra_if_add;
zclient->interface_delete = isis_zebra_if_del;
diff --git a/lib/memtypes.c b/lib/memtypes.c
index 60f24e6a..ab3c1f8e 100644
--- a/lib/memtypes.c
+++ b/lib/memtypes.c
@@ -71,6 +71,7 @@ struct memory_list memory_list_lib[] =
{ MTYPE_HOST, "Host config" },
{ MTYPE_VRF, "VRF" },
{ MTYPE_VRF_NAME, "VRF name" },
+ { MTYPE_VRF_BITMAP, "VRF bit-map" },
{ -1, NULL },
};
diff --git a/lib/vrf.c b/lib/vrf.c
index d11a9826..683026e5 100644
--- a/lib/vrf.c
+++ b/lib/vrf.c
@@ -336,6 +336,99 @@ vrf_iflist_get (vrf_id_t vrf_id)
return vrf->iflist;
}
+/*
+ * VRF bit-map
+ */
+
+#define VRF_BITMAP_NUM_OF_GROUPS 8
+#define VRF_BITMAP_NUM_OF_BITS_IN_GROUP \
+ (UINT16_MAX / VRF_BITMAP_NUM_OF_GROUPS)
+#define VRF_BITMAP_NUM_OF_BYTES_IN_GROUP \
+ (VRF_BITMAP_NUM_OF_BITS_IN_GROUP / CHAR_BIT + 1) /* +1 for ensure */
+
+#define VRF_BITMAP_GROUP(_id) \
+ ((_id) / VRF_BITMAP_NUM_OF_BITS_IN_GROUP)
+#define VRF_BITMAP_BIT_OFFSET(_id) \
+ ((_id) % VRF_BITMAP_NUM_OF_BITS_IN_GROUP)
+
+#define VRF_BITMAP_INDEX_IN_GROUP(_bit_offset) \
+ ((_bit_offset) / CHAR_BIT)
+#define VRF_BITMAP_FLAG(_bit_offset) \
+ (((u_char)1) << ((_bit_offset) % CHAR_BIT))
+
+struct vrf_bitmap
+{
+ u_char *groups[VRF_BITMAP_NUM_OF_GROUPS];
+};
+
+vrf_bitmap_t
+vrf_bitmap_init (void)
+{
+ return (vrf_bitmap_t) XCALLOC (MTYPE_VRF_BITMAP, sizeof (struct vrf_bitmap));
+}
+
+void
+vrf_bitmap_free (vrf_bitmap_t bmap)
+{
+ struct vrf_bitmap *bm = (struct vrf_bitmap *) bmap;
+ int i;
+
+ if (bmap == VRF_BITMAP_NULL)
+ return;
+
+ for (i = 0; i < VRF_BITMAP_NUM_OF_GROUPS; i++)
+ if (bm->groups[i])
+ XFREE (MTYPE_VRF_BITMAP, bm->groups[i]);
+
+ XFREE (MTYPE_VRF_BITMAP, bm);
+}
+
+void
+vrf_bitmap_set (vrf_bitmap_t bmap, vrf_id_t vrf_id)
+{
+ struct vrf_bitmap *bm = (struct vrf_bitmap *) bmap;
+ u_char group = VRF_BITMAP_GROUP (vrf_id);
+ u_char offset = VRF_BITMAP_BIT_OFFSET (vrf_id);
+
+ if (bmap == VRF_BITMAP_NULL)
+ return;
+
+ if (bm->groups[group] == NULL)
+ bm->groups[group] = XCALLOC (MTYPE_VRF_BITMAP,
+ VRF_BITMAP_NUM_OF_BYTES_IN_GROUP);
+
+ SET_FLAG (bm->groups[group][VRF_BITMAP_INDEX_IN_GROUP (offset)],
+ VRF_BITMAP_FLAG (offset));
+}
+
+void
+vrf_bitmap_unset (vrf_bitmap_t bmap, vrf_id_t vrf_id)
+{
+ struct vrf_bitmap *bm = (struct vrf_bitmap *) bmap;
+ u_char group = VRF_BITMAP_GROUP (vrf_id);
+ u_char offset = VRF_BITMAP_BIT_OFFSET (vrf_id);
+
+ if (bmap == VRF_BITMAP_NULL || bm->groups[group] == NULL)
+ return;
+
+ UNSET_FLAG (bm->groups[group][VRF_BITMAP_INDEX_IN_GROUP (offset)],
+ VRF_BITMAP_FLAG (offset));
+}
+
+int
+vrf_bitmap_check (vrf_bitmap_t bmap, vrf_id_t vrf_id)
+{
+ struct vrf_bitmap *bm = (struct vrf_bitmap *) bmap;
+ u_char group = VRF_BITMAP_GROUP (vrf_id);
+ u_char offset = VRF_BITMAP_BIT_OFFSET (vrf_id);
+
+ if (bmap == VRF_BITMAP_NULL || bm->groups[group] == NULL)
+ return 0;
+
+ return CHECK_FLAG (bm->groups[group][VRF_BITMAP_INDEX_IN_GROUP (offset)],
+ VRF_BITMAP_FLAG (offset)) ? 1 : 0;
+}
+
/* Initialize VRF module. */
void
vrf_init (void)
diff --git a/lib/vrf.h b/lib/vrf.h
index 653fabf9..8b29b809 100644
--- a/lib/vrf.h
+++ b/lib/vrf.h
@@ -110,6 +110,19 @@ extern struct list *vrf_iflist (vrf_id_t);
extern struct list *vrf_iflist_get (vrf_id_t);
/*
+ * VRF bit-map: maintaining flags, one bit per VRF ID
+ */
+
+typedef void * vrf_bitmap_t;
+#define VRF_BITMAP_NULL NULL
+
+extern vrf_bitmap_t vrf_bitmap_init (void);
+extern void vrf_bitmap_free (vrf_bitmap_t);
+extern void vrf_bitmap_set (vrf_bitmap_t, vrf_id_t);
+extern void vrf_bitmap_unset (vrf_bitmap_t, vrf_id_t);
+extern int vrf_bitmap_check (vrf_bitmap_t, vrf_id_t);
+
+/*
* VRF initializer/destructor
*/
/* Please add hooks before calling vrf_init(). */
diff --git a/lib/zclient.c b/lib/zclient.c
index 71da87c6..8e443e28 100644
--- a/lib/zclient.c
+++ b/lib/zclient.c
@@ -93,15 +93,14 @@ zclient_init (struct zclient *zclient, int redist_default)
/* Clear redistribution flags. */
for (i = 0; i < ZEBRA_ROUTE_MAX; i++)
- zclient->redist[i] = 0;
+ zclient->redist[i] = vrf_bitmap_init ();
/* Set unwanted redistribute route. bgpd does not need BGP route
redistribution. */
zclient->redist_default = redist_default;
- zclient->redist[redist_default] = 1;
/* Set default-information redistribute to zero. */
- zclient->default_information = 0;
+ zclient->default_information = vrf_bitmap_init ();
/* Schedule first zclient connection. */
if (zclient_debug)
@@ -293,18 +292,19 @@ zclient_send_message(struct zclient *zclient)
}
void
-zclient_create_header (struct stream *s, uint16_t command)
+zclient_create_header (struct stream *s, uint16_t command, vrf_id_t vrf_id)
{
/* length placeholder, caller can update */
stream_putw (s, ZEBRA_HEADER_SIZE);
stream_putc (s, ZEBRA_HEADER_MARKER);
stream_putc (s, ZSERV_VERSION);
+ stream_putw (s, vrf_id);
stream_putw (s, command);
}
/* Send simple Zebra message. */
static int
-zebra_message_send (struct zclient *zclient, int command)
+zebra_message_send (struct zclient *zclient, int command, vrf_id_t vrf_id)
{
struct stream *s;
@@ -313,7 +313,7 @@ zebra_message_send (struct zclient *zclient, int command)
stream_reset (s);
/* Send very simple command only Zebra message. */
- zclient_create_header (s, command);
+ zclient_create_header (s, command, vrf_id);
return zclient_send_message(zclient);
}
@@ -328,7 +328,8 @@ zebra_hello_send (struct zclient *zclient)
s = zclient->obuf;
stream_reset (s);
- zclient_create_header (s, ZEBRA_HELLO);
+ /* The VRF ID in the HELLO message is always 0. */
+ zclient_create_header (s, ZEBRA_HELLO, VRF_DEFAULT);
stream_putc (s, zclient->redist_default);
stream_putw_at (s, 0, stream_get_endp (s));
return zclient_send_message(zclient);
@@ -337,12 +338,47 @@ zebra_hello_send (struct zclient *zclient)
return 0;
}
+/* Send requests to zebra daemon for the information in a VRF. */
+void
+zclient_send_requests (struct zclient *zclient, vrf_id_t vrf_id)
+{
+ int i;
+
+ /* zclient is disabled. */
+ if (! zclient->enable)
+ return;
+
+ /* If not connected to the zebra yet. */
+ if (zclient->sock < 0)
+ return;
+
+ if (zclient_debug)
+ zlog_debug ("%s: send messages for VRF %u", __func__, vrf_id);
+
+ /* We need router-id information. */
+ zebra_message_send (zclient, ZEBRA_ROUTER_ID_ADD, vrf_id);
+
+ /* We need interface information. */
+ zebra_message_send (zclient, ZEBRA_INTERFACE_ADD, vrf_id);
+
+ /* Set unwanted redistribute route. */
+ vrf_bitmap_set (zclient->redist[zclient->redist_default], vrf_id);
+
+ /* Flush all redistribute request. */
+ for (i = 0; i < ZEBRA_ROUTE_MAX; i++)
+ if (i != zclient->redist_default &&
+ vrf_bitmap_check (zclient->redist[i], vrf_id))
+ zebra_redistribute_send (ZEBRA_REDISTRIBUTE_ADD, zclient, i, vrf_id);
+
+ /* If default information is needed. */
+ if (vrf_bitmap_check (zclient->default_information, VRF_DEFAULT))
+ zebra_message_send (zclient, ZEBRA_REDISTRIBUTE_DEFAULT_ADD, vrf_id);
+}
+
/* Make connection to zebra daemon. */
int
zclient_start (struct zclient *zclient)
{
- int i;
-
if (zclient_debug)
zlog_debug ("zclient_start is called");
@@ -380,20 +416,9 @@ zclient_start (struct zclient *zclient)
zebra_hello_send (zclient);
- /* We need router-id information. */
- zebra_message_send (zclient, ZEBRA_ROUTER_ID_ADD);
-
- /* We need interface information. */
- zebra_message_send (zclient, ZEBRA_INTERFACE_ADD);
-
- /* Flush all redistribute request. */
- for (i = 0; i < ZEBRA_ROUTE_MAX; i++)
- if (i != zclient->redist_default && zclient->redist[i])
- zebra_redistribute_send (ZEBRA_REDISTRIBUTE_ADD, zclient, i);
-
- /* If default information is needed. */
- if (zclient->default_information)
- zebra_message_send (zclient, ZEBRA_REDISTRIBUTE_DEFAULT_ADD);
+ /* Inform the successful connection. */
+ if (zclient->zebra_connected)
+ (*zclient->zebra_connected) (zclient);
return 0;
}
@@ -469,8 +494,8 @@ zapi_ipv4_route (u_char cmd, struct zclient *zclient, struct prefix_ipv4 *p,
/* Reset stream. */
s = zclient->obuf;
stream_reset (s);
-
- zclient_create_header (s, cmd);
+
+ zclient_create_header (s, cmd, api->vrf_id);
/* Put type and nexthop. */
stream_putc (s, api->type);
@@ -532,7 +557,7 @@ zapi_ipv6_route (u_char cmd, struct zclient *zclient, struct prefix_ipv6 *p,
s = zclient->obuf;
stream_reset (s);
- zclient_create_header (s, cmd);
+ zclient_create_header (s, cmd, api->vrf_id);
/* Put type and nexthop. */
stream_putc (s, api->type);
@@ -581,14 +606,15 @@ zapi_ipv6_route (u_char cmd, struct zclient *zclient, struct prefix_ipv6 *p,
* sending client
*/
int
-zebra_redistribute_send (int command, struct zclient *zclient, int type)
+zebra_redistribute_send (int command, struct zclient *zclient, int type,
+ vrf_id_t vrf_id)
{
struct stream *s;
s = zclient->obuf;
stream_reset(s);
- zclient_create_header (s, command);
+ zclient_create_header (s, command, vrf_id);
stream_putc (s, type);
stream_putw_at (s, 0, stream_get_endp (s));
@@ -643,7 +669,7 @@ zebra_router_id_update_read (struct stream *s, struct prefix *rid)
*/
struct interface *
-zebra_interface_add_read (struct stream *s)
+zebra_interface_add_read (struct stream *s, vrf_id_t vrf_id)
{
struct interface *ifp;
char ifname_tmp[INTERFACE_NAMSIZ];
@@ -652,7 +678,9 @@ zebra_interface_add_read (struct stream *s)
stream_get (ifname_tmp, s, INTERFACE_NAMSIZ);
/* Lookup/create interface by name. */
- ifp = if_get_by_name_len (ifname_tmp, strnlen(ifname_tmp, INTERFACE_NAMSIZ));
+ ifp = if_get_by_name_len_vrf (ifname_tmp,
+ strnlen (ifname_tmp, INTERFACE_NAMSIZ),
+ vrf_id);
zebra_interface_if_set_value (s, ifp);
@@ -667,7 +695,7 @@ zebra_interface_add_read (struct stream *s)
* is sent at the tail of the message.
*/
struct interface *
-zebra_interface_state_read (struct stream *s)
+zebra_interface_state_read (struct stream *s, vrf_id_t vrf_id)
{
struct interface *ifp;
char ifname_tmp[INTERFACE_NAMSIZ];
@@ -676,8 +704,9 @@ zebra_interface_state_read (struct stream *s)
stream_get (ifname_tmp, s, INTERFACE_NAMSIZ);
/* Lookup this by interface index. */
- ifp = if_lookup_by_name_len (ifname_tmp,
- strnlen(ifname_tmp, INTERFACE_NAMSIZ));
+ ifp = if_lookup_by_name_len_vrf (ifname_tmp,
+ strnlen (ifname_tmp, INTERFACE_NAMSIZ),
+ vrf_id);
/* If such interface does not exist, indicate an error */
if (! ifp)
@@ -754,7 +783,7 @@ memconstant(const void *s, int c, size_t n)
}
struct connected *
-zebra_interface_address_read (int type, struct stream *s)
+zebra_interface_address_read (int type, struct stream *s, vrf_id_t vrf_id)
{
unsigned int ifindex;
struct interface *ifp;
@@ -771,7 +800,7 @@ zebra_interface_address_read (int type, struct stream *s)
ifindex = stream_getl (s);
/* Lookup index. */
- ifp = if_lookup_by_index (ifindex);
+ ifp = if_lookup_by_index_vrf (ifindex, vrf_id);
if (ifp == NULL)
{
zlog_warn ("zebra_interface_address_read(%s): "
@@ -834,6 +863,7 @@ zclient_read (struct thread *thread)
size_t already;
uint16_t length, command;
uint8_t marker, version;
+ vrf_id_t vrf_id;
struct zclient *zclient;
/* Get socket to zebra. */
@@ -868,6 +898,7 @@ zclient_read (struct thread *thread)
length = stream_getw (zclient->ibuf);
marker = stream_getc (zclient->ibuf);
version = stream_getc (zclient->ibuf);
+ vrf_id = stream_getw (zclient->ibuf);
command = stream_getw (zclient->ibuf);
if (marker != ZEBRA_HEADER_MARKER || version != ZSERV_VERSION)
@@ -919,53 +950,53 @@ zclient_read (struct thread *thread)
length -= ZEBRA_HEADER_SIZE;
if (zclient_debug)
- zlog_debug("zclient 0x%p command 0x%x \n", (void *)zclient, command);
+ zlog_debug("zclient 0x%p command 0x%x VRF %u\n", (void *)zclient, command, vrf_id);
switch (command)
{
case ZEBRA_ROUTER_ID_UPDATE:
if (zclient->router_id_update)
- (*zclient->router_id_update) (command, zclient, length);
+ (*zclient->router_id_update) (command, zclient, length, vrf_id);
break;
case ZEBRA_INTERFACE_ADD:
if (zclient->interface_add)
- (*zclient->interface_add) (command, zclient, length);
+ (*zclient->interface_add) (command, zclient, length, vrf_id);
break;
case ZEBRA_INTERFACE_DELETE:
if (zclient->interface_delete)
- (*zclient->interface_delete) (command, zclient, length);
+ (*zclient->interface_delete) (command, zclient, length, vrf_id);
break;
case ZEBRA_INTERFACE_ADDRESS_ADD:
if (zclient->interface_address_add)
- (*zclient->interface_address_add) (command, zclient, length);
+ (*zclient->interface_address_add) (command, zclient, length, vrf_id);
break;
case ZEBRA_INTERFACE_ADDRESS_DELETE:
if (zclient->interface_address_delete)
- (*zclient->interface_address_delete) (command, zclient, length);
+ (*zclient->interface_address_delete) (command, zclient, length, vrf_id);
break;
case ZEBRA_INTERFACE_UP:
if (zclient->interface_up)
- (*zclient->interface_up) (command, zclient, length);
+ (*zclient->interface_up) (command, zclient, length, vrf_id);
break;
case ZEBRA_INTERFACE_DOWN:
if (zclient->interface_down)
- (*zclient->interface_down) (command, zclient, length);
+ (*zclient->interface_down) (command, zclient, length, vrf_id);
break;
case ZEBRA_IPV4_ROUTE_ADD:
if (zclient->ipv4_route_add)
- (*zclient->ipv4_route_add) (command, zclient, length);
+ (*zclient->ipv4_route_add) (command, zclient, length, vrf_id);
break;
case ZEBRA_IPV4_ROUTE_DELETE:
if (zclient->ipv4_route_delete)
- (*zclient->ipv4_route_delete) (command, zclient, length);
+ (*zclient->ipv4_route_delete) (command, zclient, length, vrf_id);
break;
case ZEBRA_IPV6_ROUTE_ADD:
if (zclient->ipv6_route_add)
- (*zclient->ipv6_route_add) (command, zclient, length);
+ (*zclient->ipv6_route_add) (command, zclient, length, vrf_id);
break;
case ZEBRA_IPV6_ROUTE_DELETE:
if (zclient->ipv6_route_delete)
- (*zclient->ipv6_route_delete) (command, zclient, length);
+ (*zclient->ipv6_route_delete) (command, zclient, length, vrf_id);
break;
default:
break;
@@ -983,46 +1014,48 @@ zclient_read (struct thread *thread)
}
void
-zclient_redistribute (int command, struct zclient *zclient, int type)
+zclient_redistribute (int command, struct zclient *zclient, int type,
+ vrf_id_t vrf_id)
{
if (command == ZEBRA_REDISTRIBUTE_ADD)
{
- if (zclient->redist[type])
+ if (vrf_bitmap_check (zclient->redist[type], vrf_id))
return;
- zclient->redist[type] = 1;
+ vrf_bitmap_set (zclient->redist[type], vrf_id);
}
else
{
- if (!zclient->redist[type])
+ if (!vrf_bitmap_check (zclient->redist[type], vrf_id))
return;
- zclient->redist[type] = 0;
+ vrf_bitmap_unset (zclient->redist[type], vrf_id);
}
if (zclient->sock > 0)
- zebra_redistribute_send (command, zclient, type);
+ zebra_redistribute_send (command, zclient, type, vrf_id);
}
void
-zclient_redistribute_default (int command, struct zclient *zclient)
+zclient_redistribute_default (int command, struct zclient *zclient,
+ vrf_id_t vrf_id)
{
if (command == ZEBRA_REDISTRIBUTE_DEFAULT_ADD)
{
- if (zclient->default_information)
+ if (vrf_bitmap_check (zclient->default_information, vrf_id))
return;
- zclient->default_information = 1;
+ vrf_bitmap_set (zclient->default_information, vrf_id);
}
else
{
- if (!zclient->default_information)
+ if (!vrf_bitmap_check (zclient->default_information, vrf_id))
return;
- zclient->default_information = 0;
+ vrf_bitmap_unset (zclient->default_information, vrf_id);
}
if (zclient->sock > 0)
- zebra_message_send (zclient, command);
+ zebra_message_send (zclient, command, vrf_id);
}
static void
diff --git a/lib/zclient.h b/lib/zclient.h
index a51b3def..19b4f0ea 100644
--- a/lib/zclient.h
+++ b/lib/zclient.h
@@ -28,11 +28,14 @@
/* For struct interface and struct connected. */
#include "if.h"
+/* For vrf_bitmap_t. */
+#include "vrf.h"
+
/* For input/output buffer to zebra. */
#define ZEBRA_MAX_PACKET_SIZ 4096
/* Zebra header size. */
-#define ZEBRA_HEADER_SIZE 6
+#define ZEBRA_HEADER_SIZE 8
/* Structure for the zebra client. */
struct zclient
@@ -65,23 +68,24 @@ struct zclient
/* Redistribute information. */
u_char redist_default;
- u_char redist[ZEBRA_ROUTE_MAX];
+ vrf_bitmap_t redist[ZEBRA_ROUTE_MAX];
/* Redistribute defauilt. */
- u_char default_information;
+ vrf_bitmap_t default_information;
/* Pointer to the callback functions. */
- int (*router_id_update) (int, struct zclient *, uint16_t);
- int (*interface_add) (int, struct zclient *, uint16_t);
- int (*interface_delete) (int, struct zclient *, uint16_t);
- int (*interface_up) (int, struct zclient *, uint16_t);
- int (*interface_down) (int, struct zclient *, uint16_t);
- int (*interface_address_add) (int, struct zclient *, uint16_t);
- int (*interface_address_delete) (int, struct zclient *, uint16_t);
- int (*ipv4_route_add) (int, struct zclient *, uint16_t);
- int (*ipv4_route_delete) (int, struct zclient *, uint16_t);
- int (*ipv6_route_add) (int, struct zclient *, uint16_t);
- int (*ipv6_route_delete) (int, struct zclient *, uint16_t);
+ void (*zebra_connected) (struct zclient *);
+ int (*router_id_update) (int, struct zclient *, uint16_t, vrf_id_t);
+ int (*interface_add) (int, struct zclient *, uint16_t, vrf_id_t);
+ int (*interface_delete) (int, struct zclient *, uint16_t, vrf_id_t);
+ int (*interface_up) (int, struct zclient *, uint16_t, vrf_id_t);
+ int (*interface_down) (int, struct zclient *, uint16_t, vrf_id_t);
+ int (*interface_address_add) (int, struct zclient *, uint16_t, vrf_id_t);
+ int (*interface_address_delete) (int, struct zclient *, uint16_t, vrf_id_t);
+ int (*ipv4_route_add) (int, struct zclient *, uint16_t, vrf_id_t);
+ int (*ipv4_route_delete) (int, struct zclient *, uint16_t, vrf_id_t);
+ int (*ipv6_route_add) (int, struct zclient *, uint16_t, vrf_id_t);
+ int (*ipv6_route_delete) (int, struct zclient *, uint16_t, vrf_id_t);
};
/* Zebra API message flag. */
@@ -98,7 +102,8 @@ struct zserv_header
* always set to 255 in new zserv.
*/
uint8_t version;
-#define ZSERV_VERSION 2
+#define ZSERV_VERSION 3
+ vrf_id_t vrf_id;
uint16_t command;
};
@@ -122,6 +127,8 @@ struct zapi_ipv4
u_char distance;
u_int32_t metric;
+
+ vrf_id_t vrf_id;
};
/* Prototypes of zebra client service functions. */
@@ -136,25 +143,33 @@ extern int zclient_socket_connect (struct zclient *);
extern void zclient_serv_path_set (char *path);
extern const char *zclient_serv_path_get (void);
+extern void zclient_send_requests (struct zclient *, vrf_id_t);
+
/* Send redistribute command to zebra daemon. Do not update zclient state. */
-extern int zebra_redistribute_send (int command, struct zclient *, int type);
+extern int zebra_redistribute_send (int command, struct zclient *, int type,
+ vrf_id_t vrf_id);
/* If state has changed, update state and call zebra_redistribute_send. */
-extern void zclient_redistribute (int command, struct zclient *, int type);
+extern void zclient_redistribute (int command, struct zclient *, int type,
+ vrf_id_t vrf_id);
/* If state has changed, update state and send the command to zebra. */
-extern void zclient_redistribute_default (int command, struct zclient *);
+extern void zclient_redistribute_default (int command, struct zclient *,
+ vrf_id_t vrf_id);
/* Send the message in zclient->obuf to the zebra daemon (or enqueue it).
Returns 0 for success or -1 on an I/O error. */
extern int zclient_send_message(struct zclient *);
/* create header for command, length to be filled in by user later */
-extern void zclient_create_header (struct stream *, uint16_t);
-
-extern struct interface *zebra_interface_add_read (struct stream *);
-extern struct interface *zebra_interface_state_read (struct stream *s);
-extern struct connected *zebra_interface_address_read (int, struct stream *);
+extern void zclient_create_header (struct stream *, uint16_t, vrf_id_t);
+
+extern struct interface *zebra_interface_add_read (struct stream *,
+ vrf_id_t);
+extern struct interface *zebra_interface_state_read (struct stream *,
+ vrf_id_t);
+extern struct connected *zebra_interface_address_read (int, struct stream *,
+ vrf_id_t);
extern void zebra_interface_if_set_value (struct stream *, struct interface *);
extern void zebra_router_id_update_read (struct stream *s, struct prefix *rid);
extern int zapi_ipv4_route (u_char, struct zclient *, struct prefix_ipv4 *,
@@ -182,6 +197,8 @@ struct zapi_ipv6
u_char distance;
u_int32_t metric;
+
+ vrf_id_t vrf_id;
};
extern int zapi_ipv6_route (u_char cmd, struct zclient *zclient,
diff --git a/lib/zebra.h b/lib/zebra.h
index e88a6293..85864377 100644
--- a/lib/zebra.h
+++ b/lib/zebra.h
@@ -412,7 +412,8 @@ struct in_pktinfo
#define ZEBRA_ROUTER_ID_UPDATE 22
#define ZEBRA_HELLO 23
#define ZEBRA_IPV4_NEXTHOP_LOOKUP_MRIB 24
-#define ZEBRA_MESSAGE_MAX 25
+#define ZEBRA_VRF_UNREGISTER 25
+#define ZEBRA_MESSAGE_MAX 26
/* Marker value used in new Zserv, in the byte location corresponding
* the command value in the old zserv header. To allow old and new
diff --git a/ospf6d/ospf6_zebra.c b/ospf6d/ospf6_zebra.c
index ac3235c4..951e11d2 100644
--- a/ospf6d/ospf6_zebra.c
+++ b/ospf6d/ospf6_zebra.c
@@ -49,7 +49,7 @@ struct in_addr router_id_zebra;
/* Router-id update message from zebra. */
static int
ospf6_router_id_update_zebra (int command, struct zclient *zclient,
- zebra_size_t length)
+ zebra_size_t length, vrf_id_t vrf_id)
{
struct prefix router_id;
struct ospf6 *o = ospf6;
@@ -70,30 +70,33 @@ ospf6_router_id_update_zebra (int command, struct zclient *zclient,
void
ospf6_zebra_redistribute (int type)
{
- if (zclient->redist[type])
+ if (vrf_bitmap_check (zclient->redist[type], VRF_DEFAULT))
return;
- zclient->redist[type] = 1;
+ vrf_bitmap_set (zclient->redist[type], VRF_DEFAULT);
if (zclient->sock > 0)
- zebra_redistribute_send (ZEBRA_REDISTRIBUTE_ADD, zclient, type);
+ zebra_redistribute_send (ZEBRA_REDISTRIBUTE_ADD, zclient, type,
+ VRF_DEFAULT);
}
void
ospf6_zebra_no_redistribute (int type)
{
- if (! zclient->redist[type])
+ if (! vrf_bitmap_check (zclient->redist[type], VRF_DEFAULT))
return;
- zclient->redist[type] = 0;
+ vrf_bitmap_unset (zclient->redist[type], VRF_DEFAULT);
if (zclient->sock > 0)
- zebra_redistribute_send (ZEBRA_REDISTRIBUTE_DELETE, zclient, type);
+ zebra_redistribute_send (ZEBRA_REDISTRIBUTE_DELETE, zclient, type,
+ VRF_DEFAULT);
}
/* Inteface addition message from zebra. */
static int
-ospf6_zebra_if_add (int command, struct zclient *zclient, zebra_size_t length)
+ospf6_zebra_if_add (int command, struct zclient *zclient, zebra_size_t length,
+ vrf_id_t vrf_id)
{
struct interface *ifp;
- ifp = zebra_interface_add_read (zclient->ibuf);
+ ifp = zebra_interface_add_read (zclient->ibuf, vrf_id);
if (IS_OSPF6_DEBUG_ZEBRA (RECV))
zlog_debug ("Zebra Interface add: %s index %d mtu %d",
ifp->name, ifp->ifindex, ifp->mtu6);
@@ -102,11 +105,12 @@ ospf6_zebra_if_add (int command, struct zclient *zclient, zebra_size_t length)
}
static int
-ospf6_zebra_if_del (int command, struct zclient *zclient, zebra_size_t length)
+ospf6_zebra_if_del (int command, struct zclient *zclient, zebra_size_t length,
+ vrf_id_t vrf_id)
{
struct interface *ifp;
- if (!(ifp = zebra_interface_state_read(zclient->ibuf)))
+ if (!(ifp = zebra_interface_state_read (zclient->ibuf, vrf_id)))
return 0;
if (if_is_up (ifp))
@@ -129,11 +133,11 @@ ospf6_zebra_if_del (int command, struct zclient *zclient, zebra_size_t length)
static int
ospf6_zebra_if_state_update (int command, struct zclient *zclient,
- zebra_size_t length)
+ zebra_size_t length, vrf_id_t vrf_id)
{
struct interface *ifp;
- ifp = zebra_interface_state_read (zclient->ibuf);
+ ifp = zebra_interface_state_read (zclient->ibuf, vrf_id);
if (ifp == NULL)
return 0;
@@ -149,12 +153,13 @@ ospf6_zebra_if_state_update (int command, struct zclient *zclient,
static int
ospf6_zebra_if_address_update_add (int command, struct zclient *zclient,
- zebra_size_t length)
+ zebra_size_t length, vrf_id_t vrf_id)
{
struct connected *c;
char buf[128];
- c = zebra_interface_address_read (ZEBRA_INTERFACE_ADDRESS_ADD, zclient->ibuf);
+ c = zebra_interface_address_read (ZEBRA_INTERFACE_ADDRESS_ADD, zclient->ibuf,
+ vrf_id);
if (c == NULL)
return 0;
@@ -174,12 +179,13 @@ ospf6_zebra_if_address_update_add (int command, struct zclient *zclient,
static int
ospf6_zebra_if_address_update_delete (int command, struct zclient *zclient,
- zebra_size_t length)
+ zebra_size_t length, vrf_id_t vrf_id)
{
struct connected *c;
char buf[128];
- c = zebra_interface_address_read (ZEBRA_INTERFACE_ADDRESS_DELETE, zclient->ibuf);
+ c = zebra_interface_address_read (ZEBRA_INTERFACE_ADDRESS_DELETE, zclient->ibuf,
+ vrf_id);
if (c == NULL)
return 0;
@@ -200,7 +206,7 @@ ospf6_zebra_if_address_update_delete (int command, struct zclient *zclient,
static int
ospf6_zebra_read_ipv6 (int command, struct zclient *zclient,
- zebra_size_t length)
+ zebra_size_t length, vrf_id_t vrf_id)
{
struct stream *s;
struct zapi_ipv6 api;
@@ -291,12 +297,13 @@ DEFUN (show_zebra,
vty_out (vty, "Zebra Infomation%s", VNL);
vty_out (vty, " enable: %d fail: %d%s",
zclient->enable, zclient->fail, VNL);
- vty_out (vty, " redistribute default: %d%s", zclient->redist_default,
+ vty_out (vty, " redistribute default: %d%s",
+ vrf_bitmap_check (zclient->default_information, VRF_DEFAULT),
VNL);
vty_out (vty, " redistribute:");
for (i = 0; i < ZEBRA_ROUTE_MAX; i++)
{
- if (zclient->redist[i])
+ if (vrf_bitmap_check (zclient->redist[i], VRF_DEFAULT))
vty_out (vty, " %s", zebra_route_string(i));
}
vty_out (vty, "%s", VNL);
@@ -336,7 +343,7 @@ config_write_ospf6_zebra (struct vty *vty)
vty_out (vty, "no router zebra%s", VNL);
vty_out (vty, "!%s", VNL);
}
- else if (! zclient->redist[ZEBRA_ROUTE_OSPF6])
+ else if (! vrf_bitmap_check (zclient->redist[ZEBRA_ROUTE_OSPF6], VRF_DEFAULT))
{
vty_out (vty, "router zebra%s", VNL);
vty_out (vty, " no redistribute ospf6%s", VNL);
@@ -454,6 +461,7 @@ ospf6_zebra_route_update (int type, struct ospf6_route *request)
ifindexes[i] = request->nexthop[i].ifindex;
}
+ api.vrf_id = VRF_DEFAULT;
api.type = ZEBRA_ROUTE_OSPF6;
api.flags = 0;
api.message = 0;
@@ -487,7 +495,7 @@ ospf6_zebra_route_update (int type, struct ospf6_route *request)
void
ospf6_zebra_route_update_add (struct ospf6_route *request)
{
- if (! zclient->redist[ZEBRA_ROUTE_OSPF6])
+ if (! vrf_bitmap_check (zclient->redist[ZEBRA_ROUTE_OSPF6], VRF_DEFAULT))
{
ospf6->route_table->hook_add = NULL;
ospf6->route_table->hook_remove = NULL;
@@ -499,7 +507,7 @@ ospf6_zebra_route_update_add (struct ospf6_route *request)
void
ospf6_zebra_route_update_remove (struct ospf6_route *request)
{
- if (! zclient->redist[ZEBRA_ROUTE_OSPF6])
+ if (! vrf_bitmap_check (zclient->redist[ZEBRA_ROUTE_OSPF6], VRF_DEFAULT))
{
ospf6->route_table->hook_add = NULL;
ospf6->route_table->hook_remove = NULL;
@@ -516,10 +524,10 @@ DEFUN (redistribute_ospf6,
{
struct ospf6_route *route;
- if (zclient->redist[ZEBRA_ROUTE_OSPF6])
+ if (vrf_bitmap_check (zclient->redist[ZEBRA_ROUTE_OSPF6], VRF_DEFAULT))
return CMD_SUCCESS;
- zclient->redist[ZEBRA_ROUTE_OSPF6] = 1;
+ vrf_bitmap_set (zclient->redist[ZEBRA_ROUTE_OSPF6], VRF_DEFAULT);
if (ospf6 == NULL)
return CMD_SUCCESS;
@@ -544,10 +552,10 @@ DEFUN (no_redistribute_ospf6,
{
struct ospf6_route *route;
- if (! zclient->redist[ZEBRA_ROUTE_OSPF6])
+ if (! vrf_bitmap_check (zclient->redist[ZEBRA_ROUTE_OSPF6], VRF_DEFAULT))
return CMD_SUCCESS;
- zclient->redist[ZEBRA_ROUTE_OSPF6] = 0;
+ vrf_bitmap_unset (zclient->redist[ZEBRA_ROUTE_OSPF6], VRF_DEFAULT);
if (ospf6 == NULL)
return CMD_SUCCESS;
@@ -563,12 +571,19 @@ DEFUN (no_redistribute_ospf6,
return CMD_SUCCESS;
}
+static void
+ospf6_zebra_connected (struct zclient *zclient)
+{
+ zclient_send_requests (zclient, VRF_DEFAULT);
+}
+
void
ospf6_zebra_init (void)
{
/* Allocate zebra structure. */
zclient = zclient_new ();
zclient_init (zclient, ZEBRA_ROUTE_OSPF6);
+ zclient->zebra_connected = ospf6_zebra_connected;
zclient->router_id_update = ospf6_router_id_update_zebra;
zclient->interface_add = ospf6_zebra_if_add;
zclient->interface_delete = ospf6_zebra_if_del;
diff --git a/ospf6d/ospf6_zebra.h b/ospf6d/ospf6_zebra.h
index 24a4ae63..a219450e 100644
--- a/ospf6d/ospf6_zebra.h
+++ b/ospf6d/ospf6_zebra.h
@@ -42,7 +42,8 @@ extern void ospf6_zebra_route_update_remove (struct ospf6_route *request);
extern void ospf6_zebra_redistribute (int);
extern void ospf6_zebra_no_redistribute (int);
-#define ospf6_zebra_is_redistribute(type) (zclient->redist[type])
+#define ospf6_zebra_is_redistribute(type) \
+ vrf_bitmap_check (zclient->redist[type], VRF_DEFAULT)
extern void ospf6_zebra_init (void);
extern int config_write_ospf6_debug_zebra (struct vty *vty);
diff --git a/ospfd/ospf_vty.c b/ospfd/ospf_vty.c
index d57eb41d..9d04892c 100644
--- a/ospfd/ospf_vty.c
+++ b/ospfd/ospf_vty.c
@@ -7133,7 +7133,8 @@ config_write_ospf_redistribute (struct vty *vty, struct ospf *ospf)
/* redistribute print. */
for (type = 0; type < ZEBRA_ROUTE_MAX; type++)
- if (type != zclient->redist_default && zclient->redist[type])
+ if (type != zclient->redist_default &&
+ vrf_bitmap_check (zclient->redist[type], VRF_DEFAULT))
{
vty_out (vty, " redistribute %s", zebra_route_string(type));
if (ospf->dmetric[type].value >= 0)
diff --git a/ospfd/ospf_zebra.c b/ospfd/ospf_zebra.c
index bdb5193a..fe1f45db 100644
--- a/ospfd/ospf_zebra.c
+++ b/ospfd/ospf_zebra.c
@@ -59,7 +59,7 @@ struct in_addr router_id_zebra;
/* Router-id update message from zebra. */
static int
ospf_router_id_update_zebra (int command, struct zclient *zclient,
- zebra_size_t length)
+ zebra_size_t length, vrf_id_t vrf_id)
{
struct ospf *ospf;
struct prefix router_id;
@@ -84,11 +84,12 @@ ospf_router_id_update_zebra (int command, struct zclient *zclient,
/* Inteface addition message from zebra. */
static int
-ospf_interface_add (int command, struct zclient *zclient, zebra_size_t length)
+ospf_interface_add (int command, struct zclient *zclient, zebra_size_t length,
+ vrf_id_t vrf_id)
{
struct interface *ifp;
- ifp = zebra_interface_add_read (zclient->ibuf);
+ ifp = zebra_interface_add_read (zclient->ibuf, vrf_id);
if (IS_DEBUG_OSPF (zebra, ZEBRA_INTERFACE))
zlog_debug ("Zebra: interface add %s index %d flags %llx metric %d mtu %d",
@@ -114,7 +115,7 @@ ospf_interface_add (int command, struct zclient *zclient, zebra_size_t length)
static int
ospf_interface_delete (int command, struct zclient *zclient,
- zebra_size_t length)
+ zebra_size_t length, vrf_id_t vrf_id)
{
struct interface *ifp;
struct stream *s;
@@ -122,7 +123,7 @@ ospf_interface_delete (int command, struct zclient *zclient,
s = zclient->ibuf;
/* zebra_interface_state_read() updates interface structure in iflist */
- ifp = zebra_interface_state_read (s);
+ ifp = zebra_interface_state_read (s, vrf_id);
if (ifp == NULL)
return 0;
@@ -149,7 +150,7 @@ ospf_interface_delete (int command, struct zclient *zclient,
}
static struct interface *
-zebra_interface_if_lookup (struct stream *s)
+zebra_interface_if_lookup (struct stream *s, vrf_id_t vrf_id)
{
char ifname_tmp[INTERFACE_NAMSIZ];
@@ -163,13 +164,13 @@ zebra_interface_if_lookup (struct stream *s)
static int
ospf_interface_state_up (int command, struct zclient *zclient,
- zebra_size_t length)
+ zebra_size_t length, vrf_id_t vrf_id)
{
struct interface *ifp;
struct ospf_interface *oi;
struct route_node *rn;
- ifp = zebra_interface_if_lookup (zclient->ibuf);
+ ifp = zebra_interface_if_lookup (zclient->ibuf, vrf_id);
if (ifp == NULL)
return 0;
@@ -225,13 +226,13 @@ ospf_interface_state_up (int command, struct zclient *zclient,
static int
ospf_interface_state_down (int command, struct zclient *zclient,
- zebra_size_t length)
+ zebra_size_t length, vrf_id_t vrf_id)
{
struct interface *ifp;
struct ospf_interface *oi;
struct route_node *node;
- ifp = zebra_interface_state_read (zclient->ibuf);
+ ifp = zebra_interface_state_read (zclient->ibuf, vrf_id);
if (ifp == NULL)
return 0;
@@ -251,11 +252,11 @@ ospf_interface_state_down (int command, struct zclient *zclient,
static int
ospf_interface_address_add (int command, struct zclient *zclient,
- zebra_size_t length)
+ zebra_size_t length, vrf_id_t vrf_id)
{
struct connected *c;
- c = zebra_interface_address_read (command, zclient->ibuf);
+ c = zebra_interface_address_read (command, zclient->ibuf, vrf_id);
if (c == NULL)
return 0;
@@ -278,7 +279,7 @@ ospf_interface_address_add (int command, struct zclient *zclient,
static int
ospf_interface_address_delete (int command, struct zclient *zclient,
- zebra_size_t length)
+ zebra_size_t length, vrf_id_t vrf_id)
{
struct connected *c;
struct interface *ifp;
@@ -286,7 +287,7 @@ ospf_interface_address_delete (int command, struct zclient *zclient,
struct route_node *rn;
struct prefix p;
- c = zebra_interface_address_read (command, zclient->ibuf);
+ c = zebra_interface_address_read (command, zclient->ibuf, vrf_id);
if (c == NULL)
return 0;
@@ -335,7 +336,7 @@ ospf_zebra_add (struct prefix_ipv4 *p, struct ospf_route *or)
struct ospf_path *path;
struct listnode *node;
- if (zclient->redist[ZEBRA_ROUTE_OSPF])
+ if (vrf_bitmap_check (zclient->redist[ZEBRA_ROUTE_OSPF], VRF_DEFAULT))
{
message = 0;
flags = 0;
@@ -354,7 +355,7 @@ ospf_zebra_add (struct prefix_ipv4 *p, struct ospf_route *or)
stream_reset (s);
/* Put command, type, flags, message. */
- zclient_create_header (s, ZEBRA_IPV4_ROUTE_ADD);
+ zclient_create_header (s, ZEBRA_IPV4_ROUTE_ADD, VRF_DEFAULT);
stream_putc (s, ZEBRA_ROUTE_OSPF);
stream_putc (s, flags);
stream_putc (s, message);
@@ -433,7 +434,7 @@ ospf_zebra_delete (struct prefix_ipv4 *p, struct ospf_route *or)
struct ospf_path *path;
struct listnode *node;
- if (zclient->redist[ZEBRA_ROUTE_OSPF])
+ if (vrf_bitmap_check (zclient->redist[ZEBRA_ROUTE_OSPF], VRF_DEFAULT))
{
message = 0;
flags = 0;
@@ -444,7 +445,7 @@ ospf_zebra_delete (struct prefix_ipv4 *p, struct ospf_route *or)
stream_reset (s);
/* Put command, type, flags, message. */
- zclient_create_header (s, ZEBRA_IPV4_ROUTE_DELETE);
+ zclient_create_header (s, ZEBRA_IPV4_ROUTE_DELETE, VRF_DEFAULT);
stream_putc (s, ZEBRA_ROUTE_OSPF);
stream_putc (s, flags);
stream_putc (s, message);
@@ -514,8 +515,9 @@ ospf_zebra_add_discard (struct prefix_ipv4 *p)
{
struct zapi_ipv4 api;
- if (zclient->redist[ZEBRA_ROUTE_OSPF])
+ if (vrf_bitmap_check (zclient->redist[ZEBRA_ROUTE_OSPF], VRF_DEFAULT))
{
+ api.vrf_id = VRF_DEFAULT;
api.type = ZEBRA_ROUTE_OSPF;
api.flags = ZEBRA_FLAG_BLACKHOLE;
api.message = 0;
@@ -537,8 +539,9 @@ ospf_zebra_delete_discard (struct prefix_ipv4 *p)
{
struct zapi_ipv4 api;
- if (zclient->redist[ZEBRA_ROUTE_OSPF])
+ if (vrf_bitmap_check (zclient->redist[ZEBRA_ROUTE_OSPF], VRF_DEFAULT))
{
+ api.vrf_id = VRF_DEFAULT;
api.type = ZEBRA_ROUTE_OSPF;
api.flags = ZEBRA_FLAG_BLACKHOLE;
api.message = 0;
@@ -560,7 +563,8 @@ int
ospf_is_type_redistributed (int type)
{
return (DEFAULT_ROUTE_TYPE (type)) ?
- zclient->default_information : zclient->redist[type];
+ vrf_bitmap_check (zclient->default_information, VRF_DEFAULT) : \
+ vrf_bitmap_check (zclient->redist[type], VRF_DEFAULT);
}
int
@@ -594,7 +598,7 @@ ospf_redistribute_set (struct ospf *ospf, int type, int mtype, int mvalue)
ospf->dmetric[type].type = mtype;
ospf->dmetric[type].value = mvalue;
- zclient_redistribute (ZEBRA_REDISTRIBUTE_ADD, zclient, type);
+ zclient_redistribute (ZEBRA_REDISTRIBUTE_ADD, zclient, type, VRF_DEFAULT);
if (IS_DEBUG_OSPF (zebra, ZEBRA_REDISTRIBUTE))
zlog_debug ("Redistribute[%s]: Start Type[%d], Metric[%d]",
@@ -615,7 +619,7 @@ ospf_redistribute_unset (struct ospf *ospf, int type)
if (!ospf_is_type_redistributed (type))
return CMD_SUCCESS;
- zclient_redistribute (ZEBRA_REDISTRIBUTE_DELETE, zclient, type);
+ zclient_redistribute (ZEBRA_REDISTRIBUTE_DELETE, zclient, type, VRF_DEFAULT);
if (IS_DEBUG_OSPF (zebra, ZEBRA_REDISTRIBUTE))
zlog_debug ("Redistribute[%s]: Stop",
@@ -655,7 +659,8 @@ ospf_redistribute_default_set (struct ospf *ospf, int originate,
return CMD_SUCCESS;
}
- zclient_redistribute_default (ZEBRA_REDISTRIBUTE_DEFAULT_ADD, zclient);
+ zclient_redistribute_default (ZEBRA_REDISTRIBUTE_DEFAULT_ADD, zclient,
+ VRF_DEFAULT);
if (IS_DEBUG_OSPF (zebra, ZEBRA_REDISTRIBUTE))
zlog_debug ("Redistribute[DEFAULT]: Start Type[%d], Metric[%d]",
@@ -682,7 +687,8 @@ ospf_redistribute_default_unset (struct ospf *ospf)
ospf->dmetric[DEFAULT_ROUTE].type = -1;
ospf->dmetric[DEFAULT_ROUTE].value = -1;
- zclient_redistribute_default (ZEBRA_REDISTRIBUTE_DEFAULT_DELETE, zclient);
+ zclient_redistribute_default (ZEBRA_REDISTRIBUTE_DEFAULT_DELETE, zclient,
+ VRF_DEFAULT);
if (IS_DEBUG_OSPF (zebra, ZEBRA_REDISTRIBUTE))
zlog_debug ("Redistribute[DEFAULT]: Stop");
@@ -816,7 +822,7 @@ ospf_routemap_unset (struct ospf *ospf, int type)
/* Zebra route add and delete treatment. */
static int
ospf_zebra_read_ipv4 (int command, struct zclient *zclient,
- zebra_size_t length)
+ zebra_size_t length, vrf_id_t vrf_id)
{
struct stream *s;
struct zapi_ipv4 api;
@@ -1292,12 +1298,19 @@ ospf_distance_apply (struct prefix_ipv4 *p, struct ospf_route *or)
return 0;
}
+static void
+ospf_zebra_connected (struct zclient *zclient)
+{
+ zclient_send_requests (zclient, VRF_DEFAULT);
+}
+
void
ospf_zebra_init ()
{
/* Allocate zebra structure. */
zclient = zclient_new ();
zclient_init (zclient, ZEBRA_ROUTE_OSPF);
+ zclient->zebra_connected = ospf_zebra_connected;
zclient->router_id_update = ospf_router_id_update_zebra;
zclient->interface_add = ospf_interface_add;
zclient->interface_delete = ospf_interface_delete;
diff --git a/pimd/pim_zebra.c b/pimd/pim_zebra.c
index 129cbe4f..dfc871b3 100644
--- a/pimd/pim_zebra.c
+++ b/pimd/pim_zebra.c
@@ -70,7 +70,7 @@ static void zclient_broken(struct zclient *zclient)
/* Router-id update message from zebra. */
static int pim_router_id_update_zebra(int command, struct zclient *zclient,
- zebra_size_t length)
+ zebra_size_t length, vrf_id_t vrf_id)
{
struct prefix router_id;
@@ -80,7 +80,7 @@ static int pim_router_id_update_zebra(int command, struct zclient *zclient,
}
static int pim_zebra_if_add(int command, struct zclient *zclient,
- zebra_size_t length)
+ zebra_size_t length, vrf_id_t vrf_id)
{
struct interface *ifp;
@@ -88,7 +88,7 @@ static int pim_zebra_if_add(int command, struct zclient *zclient,
zebra api adds/dels interfaces using the same call
interface_add_read below, see comments in lib/zclient.c
*/
- ifp = zebra_interface_add_read(zclient->ibuf);
+ ifp = zebra_interface_add_read(zclient->ibuf, vrf_id);
if (!ifp)
return 0;
@@ -106,7 +106,7 @@ static int pim_zebra_if_add(int command, struct zclient *zclient,
}
static int pim_zebra_if_del(int command, struct zclient *zclient,
- zebra_size_t length)
+ zebra_size_t length, vrf_id_t vrf_id)
{
struct interface *ifp;
@@ -120,7 +120,7 @@ static int pim_zebra_if_del(int command, struct zclient *zclient,
pimd to assert. Other clients use zebra_interface_state_read
and it appears to work just fine.
*/
- ifp = zebra_interface_state_read(zclient->ibuf);
+ ifp = zebra_interface_state_read(zclient->ibuf, vrf_id);
if (!ifp)
return 0;
@@ -138,7 +138,7 @@ static int pim_zebra_if_del(int command, struct zclient *zclient,
}
static int pim_zebra_if_state_up(int command, struct zclient *zclient,
- zebra_size_t length)
+ zebra_size_t length, vrf_id_t vrf_id)
{
struct interface *ifp;
@@ -146,7 +146,7 @@ static int pim_zebra_if_state_up(int command, struct zclient *zclient,
zebra api notifies interface up/down events by using the same call
zebra_interface_state_read below, see comments in lib/zclient.c
*/
- ifp = zebra_interface_state_read(zclient->ibuf);
+ ifp = zebra_interface_state_read(zclient->ibuf, vrf_id);
if (!ifp)
return 0;
@@ -170,7 +170,7 @@ static int pim_zebra_if_state_up(int command, struct zclient *zclient,
}
static int pim_zebra_if_state_down(int command, struct zclient *zclient,
- zebra_size_t length)
+ zebra_size_t length, vrf_id_t vrf_id)
{
struct interface *ifp;
@@ -178,7 +178,7 @@ static int pim_zebra_if_state_down(int command, struct zclient *zclient,
zebra api notifies interface up/down events by using the same call
zebra_interface_state_read below, see comments in lib/zclient.c
*/
- ifp = zebra_interface_state_read(zclient->ibuf);
+ ifp = zebra_interface_state_read(zclient->ibuf, vrf_id);
if (!ifp)
return 0;
@@ -237,7 +237,7 @@ static void dump_if_address(struct interface *ifp)
#endif
static int pim_zebra_if_address_add(int command, struct zclient *zclient,
- zebra_size_t length)
+ zebra_size_t length, vrf_id_t vrf_id)
{
struct connected *c;
struct prefix *p;
@@ -252,7 +252,7 @@ static int pim_zebra_if_address_add(int command, struct zclient *zclient,
will add address to interface list by calling
connected_add_by_prefix()
*/
- c = zebra_interface_address_read(command, zclient->ibuf);
+ c = zebra_interface_address_read(command, zclient->ibuf, vrf_id);
if (!c)
return 0;
@@ -299,7 +299,7 @@ static int pim_zebra_if_address_add(int command, struct zclient *zclient,
}
static int pim_zebra_if_address_del(int command, struct zclient *client,
- zebra_size_t length)
+ zebra_size_t length, vrf_id_t vrf_id)
{
struct connected *c;
struct prefix *p;
@@ -314,7 +314,7 @@ static int pim_zebra_if_address_del(int command, struct zclient *client,
will remove address from interface list by calling
connected_delete_by_prefix()
*/
- c = zebra_interface_address_read(command, client->ibuf);
+ c = zebra_interface_address_read(command, client->ibuf, vrf_id);
if (!c)
return 0;
@@ -526,7 +526,7 @@ static void sched_rpf_cache_refresh()
}
static int redist_read_ipv4_route(int command, struct zclient *zclient,
- zebra_size_t length)
+ zebra_size_t length, vrf_id_t vrf_id)
{
struct stream *s;
struct zapi_ipv4 api;
@@ -650,6 +650,11 @@ static int redist_read_ipv4_route(int command, struct zclient *zclient,
return 0;
}
+static void pim_zebra_connected(struct zclient *zclient)
+{
+ zclient_send_requests(zclient, VRF_DEFAULT);
+}
+
void pim_zebra_init(char *zebra_sock_path)
{
int i;
@@ -666,6 +671,7 @@ void pim_zebra_init(char *zebra_sock_path)
/* Socket for receiving updates from Zebra daemon */
qpim_zclient_update = zclient_new();
+ qpim_zclient_update->zebra_connected = pim_zebra_connected;
qpim_zclient_update->router_id_update = pim_router_id_update_zebra;
qpim_zclient_update->interface_add = pim_zebra_if_add;
qpim_zclient_update->interface_delete = pim_zebra_if_del;
@@ -687,7 +693,7 @@ void pim_zebra_init(char *zebra_sock_path)
for (i = 0; i < ZEBRA_ROUTE_MAX; i++) {
if (i == qpim_zclient_update->redist_default)
continue;
- qpim_zclient_update->redist[i] = 1;
+ vrf_bitmap_set(qpim_zclient_update->redist[i], VRF_DEFAULT);
if (PIM_DEBUG_PIM_TRACE) {
zlog_debug("%s: requesting redistribution for %s (%i)",
__PRETTY_FUNCTION__, zebra_route_string(i), i);
@@ -695,7 +701,7 @@ void pim_zebra_init(char *zebra_sock_path)
}
/* Request default information */
- qpim_zclient_update->default_information = 1;
+ vrf_bitmap_set(qpim_zclient_update->default_information, VRF_DEFAULT);
if (PIM_DEBUG_PIM_TRACE) {
zlog_info("%s: requesting default information redistribution",
__PRETTY_FUNCTION__);
diff --git a/pimd/pim_zlookup.c b/pimd/pim_zlookup.c
index 2e71dc4e..60003670 100644
--- a/pimd/pim_zlookup.c
+++ b/pimd/pim_zlookup.c
@@ -346,7 +346,7 @@ static int zclient_lookup_nexthop_once(struct zclient *zlookup,
s = zlookup->obuf;
stream_reset(s);
- zclient_create_header(s, ZEBRA_IPV4_NEXTHOP_LOOKUP_MRIB);
+ zclient_create_header(s, ZEBRA_IPV4_NEXTHOP_LOOKUP_MRIB, VRF_DEFAULT);
stream_put_in_addr(s, &addr);
stream_putw_at(s, 0, stream_get_endp(s));
diff --git a/ripd/rip_interface.c b/ripd/rip_interface.c
index f26ef48a..00612df4 100644
--- a/ripd/rip_interface.c
+++ b/ripd/rip_interface.c
@@ -380,7 +380,8 @@ if_check_address (struct in_addr addr)
/* Inteface link down message processing. */
int
-rip_interface_down (int command, struct zclient *zclient, zebra_size_t length)
+rip_interface_down (int command, struct zclient *zclient, zebra_size_t length,
+ vrf_id_t vrf_id)
{
struct interface *ifp;
struct stream *s;
@@ -389,7 +390,7 @@ rip_interface_down (int command, struct zclient *zclient, zebra_size_t length)
/* zebra_interface_state_read() updates interface structure in
iflist. */
- ifp = zebra_interface_state_read(s);
+ ifp = zebra_interface_state_read (s, vrf_id);
if (ifp == NULL)
return 0;
@@ -406,13 +407,14 @@ rip_interface_down (int command, struct zclient *zclient, zebra_size_t length)
/* Inteface link up message processing */
int
-rip_interface_up (int command, struct zclient *zclient, zebra_size_t length)
+rip_interface_up (int command, struct zclient *zclient, zebra_size_t length,
+ vrf_id_t vrf_id)
{
struct interface *ifp;
/* zebra_interface_state_read () updates interface structure in
iflist. */
- ifp = zebra_interface_state_read (zclient->ibuf);
+ ifp = zebra_interface_state_read (zclient->ibuf, vrf_id);
if (ifp == NULL)
return 0;
@@ -436,11 +438,12 @@ rip_interface_up (int command, struct zclient *zclient, zebra_size_t length)
/* Inteface addition message from zebra. */
int
-rip_interface_add (int command, struct zclient *zclient, zebra_size_t length)
+rip_interface_add (int command, struct zclient *zclient, zebra_size_t length,
+ vrf_id_t vrf_id)
{
struct interface *ifp;
- ifp = zebra_interface_add_read (zclient->ibuf);
+ ifp = zebra_interface_add_read (zclient->ibuf, vrf_id);
if (IS_RIP_DEBUG_ZEBRA)
zlog_debug ("interface add %s index %d flags %#llx metric %d mtu %d",
@@ -466,7 +469,7 @@ rip_interface_add (int command, struct zclient *zclient, zebra_size_t length)
int
rip_interface_delete (int command, struct zclient *zclient,
- zebra_size_t length)
+ zebra_size_t length, vrf_id_t vrf_id)
{
struct interface *ifp;
struct stream *s;
@@ -474,7 +477,7 @@ rip_interface_delete (int command, struct zclient *zclient,
s = zclient->ibuf;
/* zebra_interface_state_read() updates interface structure in iflist */
- ifp = zebra_interface_state_read(s);
+ ifp = zebra_interface_state_read (s, vrf_id);
if (ifp == NULL)
return 0;
@@ -644,13 +647,13 @@ rip_apply_address_add (struct connected *ifc)
int
rip_interface_address_add (int command, struct zclient *zclient,
- zebra_size_t length)
+ zebra_size_t length, vrf_id_t vrf_id)
{
struct connected *ifc;
struct prefix *p;
ifc = zebra_interface_address_read (ZEBRA_INTERFACE_ADDRESS_ADD,
- zclient->ibuf);
+ zclient->ibuf, vrf_id);
if (ifc == NULL)
return 0;
@@ -700,13 +703,13 @@ rip_apply_address_del (struct connected *ifc) {
int
rip_interface_address_delete (int command, struct zclient *zclient,
- zebra_size_t length)
+ zebra_size_t length, vrf_id_t vrf_id)
{
struct connected *ifc;
struct prefix *p;
ifc = zebra_interface_address_read (ZEBRA_INTERFACE_ADDRESS_DELETE,
- zclient->ibuf);
+ zclient->ibuf, vrf_id);
if (ifc)
{
diff --git a/ripd/rip_interface.h b/ripd/rip_interface.h
index 8926cce7..d9dfbb7c 100644
--- a/ripd/rip_interface.h
+++ b/ripd/rip_interface.h
@@ -21,11 +21,17 @@
#ifndef _QUAGGA_RIP_INTERFACE_H
#define _QUAGGA_RIP_INTERFACE_H
-extern int rip_interface_down (int , struct zclient *, zebra_size_t);
-extern int rip_interface_up (int , struct zclient *, zebra_size_t);
-extern int rip_interface_add (int , struct zclient *, zebra_size_t);
-extern int rip_interface_delete (int , struct zclient *, zebra_size_t);
-extern int rip_interface_address_add (int , struct zclient *, zebra_size_t);
-extern int rip_interface_address_delete (int , struct zclient *, zebra_size_t);
+extern int rip_interface_down (int , struct zclient *, zebra_size_t,
+ vrf_id_t);
+extern int rip_interface_up (int , struct zclient *, zebra_size_t,
+ vrf_id_t);
+extern int rip_interface_add (int , struct zclient *, zebra_size_t,
+ vrf_id_t);
+extern int rip_interface_delete (int , struct zclient *, zebra_size_t,
+ vrf_id_t);
+extern int rip_interface_address_add (int , struct zclient *, zebra_size_t,
+ vrf_id_t);
+extern int rip_interface_address_delete (int , struct zclient *, zebra_size_t,
+ vrf_id_t);
#endif /* _QUAGGA_RIP_INTERFACE_H */
diff --git a/ripd/rip_zebra.c b/ripd/rip_zebra.c
index b005ece9..de981623 100644
--- a/ripd/rip_zebra.c
+++ b/ripd/rip_zebra.c
@@ -29,6 +29,7 @@
#include "routemap.h"
#include "zclient.h"
#include "log.h"
+#include "vrf.h"
#include "ripd/ripd.h"
#include "ripd/rip_debug.h"
#include "ripd/rip_interface.h"
@@ -49,8 +50,9 @@ rip_zebra_ipv4_send (struct route_node *rp, u_char cmd)
struct rip_info *rinfo = NULL;
int count = 0;
- if (zclient->redist[ZEBRA_ROUTE_RIP])
+ if (vrf_bitmap_check (zclient->redist[ZEBRA_ROUTE_RIP], VRF_DEFAULT))
{
+ api.vrf_id = VRF_DEFAULT;
api.type = ZEBRA_ROUTE_RIP;
api.flags = 0;
api.message = 0;
@@ -125,7 +127,8 @@ rip_zebra_ipv4_delete (struct route_node *rp)
/* Zebra route add and delete treatment. */
static int
-rip_zebra_read_ipv4 (int command, struct zclient *zclient, zebra_size_t length)
+rip_zebra_read_ipv4 (int command, struct zclient *zclient, zebra_size_t length,
+ vrf_id_t vrf_id)
{
struct stream *s;
struct zapi_ipv4 api;
@@ -272,10 +275,10 @@ DEFUN (no_router_zebra,
static int
rip_redistribute_set (int type)
{
- if (zclient->redist[type])
+ if (vrf_bitmap_check (zclient->redist[type], VRF_DEFAULT))
return CMD_SUCCESS;
- zclient->redist[type] = 1;
+ vrf_bitmap_set (zclient->redist[type], VRF_DEFAULT);
if (zclient->sock > 0)
zebra_redistribute_send (ZEBRA_REDISTRIBUTE_ADD, zclient, type);
@@ -287,13 +290,14 @@ rip_redistribute_set (int type)
static int
rip_redistribute_unset (int type)
{
- if (! zclient->redist[type])
+ if (! vrf_bitmap_check (zclient->redist[type], VRF_DEFAULT))
return CMD_SUCCESS;
- zclient->redist[type] = 0;
+ vrf_bitmap_unset (zclient->redist[type], VRF_DEFAULT);
if (zclient->sock > 0)
- zebra_redistribute_send (ZEBRA_REDISTRIBUTE_DELETE, zclient, type);
+ zebra_redistribute_send (ZEBRA_REDISTRIBUTE_DELETE, zclient, type,
+ VRF_DEFAULT);
/* Remove the routes from RIP table. */
rip_redistribute_withdraw (type);
@@ -304,7 +308,7 @@ rip_redistribute_unset (int type)
int
rip_redistribute_check (int type)
{
- return (zclient->redist[type]);
+ return vrf_bitmap_check (zclient->redist[type], VRF_DEFAULT);
}
void
@@ -314,13 +318,14 @@ rip_redistribute_clean (void)
for (i = 0; redist_type[i].str; i++)
{
- if (zclient->redist[redist_type[i].type])
+ if (vrf_bitmap_check (zclient->redist[redist_type[i].type], VRF_DEFAULT))
{
if (zclient->sock > 0)
zebra_redistribute_send (ZEBRA_REDISTRIBUTE_DELETE,
- zclient, redist_type[i].type);
+ zclient, redist_type[i].type,
+ VRF_DEFAULT);
- zclient->redist[redist_type[i].type] = 0;
+ vrf_bitmap_unset (zclient->redist[redist_type[i].type], VRF_DEFAULT);
/* Remove the routes from RIP table. */
rip_redistribute_withdraw (redist_type[i].type);
@@ -334,7 +339,7 @@ DEFUN (rip_redistribute_rip,
"Redistribute information from another routing protocol\n"
"Routing Information Protocol (RIP)\n")
{
- zclient->redist[ZEBRA_ROUTE_RIP] = 1;
+ vrf_bitmap_set (zclient->redist[ZEBRA_ROUTE_RIP], VRF_DEFAULT);
return CMD_SUCCESS;
}
@@ -345,7 +350,7 @@ DEFUN (no_rip_redistribute_rip,
"Redistribute information from another routing protocol\n"
"Routing Information Protocol (RIP)\n")
{
- zclient->redist[ZEBRA_ROUTE_RIP] = 0;
+ vrf_bitmap_unset (zclient->redist[ZEBRA_ROUTE_RIP], VRF_DEFAULT);
return CMD_SUCCESS;
}
@@ -363,7 +368,7 @@ DEFUN (rip_redistribute_type,
redist_type[i].str_min_len) == 0)
{
zclient_redistribute (ZEBRA_REDISTRIBUTE_ADD, zclient,
- redist_type[i].type);
+ redist_type[i].type, VRF_DEFAULT);
return CMD_SUCCESS;
}
}
@@ -416,7 +421,8 @@ DEFUN (rip_redistribute_type_routemap,
redist_type[i].str_min_len) == 0)
{
rip_routemap_set (redist_type[i].type, argv[1]);
- zclient_redistribute (ZEBRA_REDISTRIBUTE_ADD, zclient, redist_type[i].type);
+ zclient_redistribute (ZEBRA_REDISTRIBUTE_ADD, zclient, redist_type[i].type,
+ VRF_DEFAULT);
return CMD_SUCCESS;
}
}
@@ -474,7 +480,8 @@ DEFUN (rip_redistribute_type_metric,
redist_type[i].str_min_len) == 0)
{
rip_redistribute_metric_set (redist_type[i].type, metric);
- zclient_redistribute (ZEBRA_REDISTRIBUTE_ADD, zclient, redist_type[i].type);
+ zclient_redistribute (ZEBRA_REDISTRIBUTE_ADD, zclient, redist_type[i].type,
+ VRF_DEFAULT);
return CMD_SUCCESS;
}
}
@@ -535,7 +542,8 @@ DEFUN (rip_redistribute_type_metric_routemap,
{
rip_redistribute_metric_set (redist_type[i].type, metric);
rip_routemap_set (redist_type[i].type, argv[2]);
- zclient_redistribute (ZEBRA_REDISTRIBUTE_ADD, zclient, redist_type[i].type);
+ zclient_redistribute (ZEBRA_REDISTRIBUTE_ADD, zclient, redist_type[i].type,
+ VRF_DEFAULT);
return CMD_SUCCESS;
}
}
@@ -639,7 +647,7 @@ config_write_zebra (struct vty *vty)
vty_out (vty, "no router zebra%s", VTY_NEWLINE);
return 1;
}
- else if (! zclient->redist[ZEBRA_ROUTE_RIP])
+ else if (! vrf_bitmap_check (zclient->redist[ZEBRA_ROUTE_RIP], VRF_DEFAULT))
{
vty_out (vty, "router zebra%s", VTY_NEWLINE);
vty_out (vty, " no redistribute rip%s", VTY_NEWLINE);
@@ -654,7 +662,8 @@ config_write_rip_redistribute (struct vty *vty, int config_mode)
int i;
for (i = 0; i < ZEBRA_ROUTE_MAX; i++)
- if (i != zclient->redist_default && zclient->redist[i])
+ if (i != zclient->redist_default &&
+ vrf_bitmap_check (zclient->redist[i], VRF_DEFAULT))
{
if (config_mode)
{
@@ -694,12 +703,19 @@ static struct cmd_node zebra_node =
"%s(config-router)# ",
};
+static void
+rip_zebra_connected (struct zclient *zclient)
+{
+ zclient_send_requests (zclient, VRF_DEFAULT);
+}
+
void
rip_zclient_init ()
{
/* Set default value to the zebra client structure. */
zclient = zclient_new ();
zclient_init (zclient, ZEBRA_ROUTE_RIP);
+ zclient->zebra_connected = rip_zebra_connected;
zclient->interface_add = rip_interface_add;
zclient->interface_delete = rip_interface_delete;
zclient->interface_address_add = rip_interface_address_add;
diff --git a/ripngd/ripng_interface.c b/ripngd/ripng_interface.c
index c7865d1e..e1f436eb 100644
--- a/ripngd/ripng_interface.c
+++ b/ripngd/ripng_interface.c
@@ -192,14 +192,15 @@ ripng_if_down (struct interface *ifp)
/* Inteface link up message processing. */
int
-ripng_interface_up (int command, struct zclient *zclient, zebra_size_t length)
+ripng_interface_up (int command, struct zclient *zclient, zebra_size_t length,
+ vrf_id_t vrf_id)
{
struct stream *s;
struct interface *ifp;
/* zebra_interface_state_read() updates interface structure in iflist. */
s = zclient->ibuf;
- ifp = zebra_interface_state_read (s);
+ ifp = zebra_interface_state_read (s, vrf_id);
if (ifp == NULL)
return 0;
@@ -224,14 +225,14 @@ ripng_interface_up (int command, struct zclient *zclient, zebra_size_t length)
/* Inteface link down message processing. */
int
ripng_interface_down (int command, struct zclient *zclient,
- zebra_size_t length)
+ zebra_size_t length, vrf_id_t vrf_id)
{
struct stream *s;
struct interface *ifp;
/* zebra_interface_state_read() updates interface structure in iflist. */
s = zclient->ibuf;
- ifp = zebra_interface_state_read (s);
+ ifp = zebra_interface_state_read (s, vrf_id);
if (ifp == NULL)
return 0;
@@ -248,11 +249,12 @@ ripng_interface_down (int command, struct zclient *zclient,
/* Inteface addition message from zebra. */
int
-ripng_interface_add (int command, struct zclient *zclient, zebra_size_t length)
+ripng_interface_add (int command, struct zclient *zclient, zebra_size_t length,
+ vrf_id_t vrf_id)
{
struct interface *ifp;
- ifp = zebra_interface_add_read (zclient->ibuf);
+ ifp = zebra_interface_add_read (zclient->ibuf, vrf_id);
if (IS_RIPNG_DEBUG_ZEBRA)
zlog_debug ("RIPng interface add %s index %d flags %#llx metric %d mtu %d",
@@ -273,14 +275,14 @@ ripng_interface_add (int command, struct zclient *zclient, zebra_size_t length)
int
ripng_interface_delete (int command, struct zclient *zclient,
- zebra_size_t length)
+ zebra_size_t length, vrf_id_t vrf_id)
{
struct interface *ifp;
struct stream *s;
s = zclient->ibuf;
/* zebra_interface_state_read() updates interface structure in iflist */
- ifp = zebra_interface_state_read(s);
+ ifp = zebra_interface_state_read (s, vrf_id);
if (ifp == NULL)
return 0;
@@ -387,13 +389,13 @@ ripng_apply_address_add (struct connected *ifc) {
int
ripng_interface_address_add (int command, struct zclient *zclient,
- zebra_size_t length)
+ zebra_size_t length, vrf_id_t vrf_id)
{
struct connected *c;
struct prefix *p;
c = zebra_interface_address_read (ZEBRA_INTERFACE_ADDRESS_ADD,
- zclient->ibuf);
+ zclient->ibuf, vrf_id);
if (c == NULL)
return 0;
@@ -454,14 +456,14 @@ ripng_apply_address_del (struct connected *ifc) {
int
ripng_interface_address_delete (int command, struct zclient *zclient,
- zebra_size_t length)
+ zebra_size_t length, vrf_id_t vrf_id)
{
struct connected *ifc;
struct prefix *p;
char buf[INET6_ADDRSTRLEN];
ifc = zebra_interface_address_read (ZEBRA_INTERFACE_ADDRESS_DELETE,
- zclient->ibuf);
+ zclient->ibuf, vrf_id);
if (ifc)
{
diff --git a/ripngd/ripng_zebra.c b/ripngd/ripng_zebra.c
index 5d383fa2..58f88606 100644
--- a/ripngd/ripng_zebra.c
+++ b/ripngd/ripng_zebra.c
@@ -37,14 +37,6 @@
/* All information about zebra. */
struct zclient *zclient = NULL;
-/* Callback prototypes for zebra client service. */
-int ripng_interface_up (int, struct zclient *, zebra_size_t);
-int ripng_interface_down (int, struct zclient *, zebra_size_t);
-int ripng_interface_add (int, struct zclient *, zebra_size_t);
-int ripng_interface_delete (int, struct zclient *, zebra_size_t);
-int ripng_interface_address_add (int, struct zclient *, zebra_size_t);
-int ripng_interface_address_delete (int, struct zclient *, zebra_size_t);
-
/* Send ECMP routes to zebra. */
static void
ripng_zebra_ipv6_send (struct route_node *rp, u_char cmd)
@@ -59,8 +51,9 @@ ripng_zebra_ipv6_send (struct route_node *rp, u_char cmd)
struct ripng_info *rinfo = NULL;
int count = 0;
- if (zclient->redist[ZEBRA_ROUTE_RIPNG])
+ if (vrf_bitmap_check (zclient->redist[ZEBRA_ROUTE_RIPNG], VRF_DEFAULT))
{
+ api.vrf_id = VRF_DEFAULT;
api.type = ZEBRA_ROUTE_RIPNG;
api.flags = 0;
api.message = 0;
@@ -134,7 +127,7 @@ ripng_zebra_ipv6_delete (struct route_node *rp)
/* Zebra route add and delete treatment. */
static int
ripng_zebra_read_ipv6 (int command, struct zclient *zclient,
- zebra_size_t length)
+ zebra_size_t length, vrf_id_t vrf_id)
{
struct stream *s;
struct zapi_ipv6 api;
@@ -194,13 +187,14 @@ ripng_zclient_reset (void)
static int
ripng_redistribute_unset (int type)
{
- if (! zclient->redist[type])
+ if (! vrf_bitmap_check (zclient->redist[type], VRF_DEFAULT))
return CMD_SUCCESS;
- zclient->redist[type] = 0;
+ vrf_bitmap_set (zclient->redist[type], VRF_DEFAULT);
if (zclient->sock > 0)
- zebra_redistribute_send (ZEBRA_REDISTRIBUTE_DELETE, zclient, type);
+ zebra_redistribute_send (ZEBRA_REDISTRIBUTE_DELETE, zclient, type,
+ VRF_DEFAULT);
ripng_redistribute_withdraw (type);
@@ -210,7 +204,7 @@ ripng_redistribute_unset (int type)
int
ripng_redistribute_check (int type)
{
- return (zclient->redist[type]);
+ return vrf_bitmap_check (zclient->redist[type], VRF_DEFAULT);
}
static void
@@ -270,13 +264,14 @@ ripng_redistribute_clean ()
for (i = 0; redist_type[i].str; i++)
{
- if (zclient->redist[redist_type[i].type])
+ if (vrf_bitmap_check (zclient->redist[redist_type[i].type], VRF_DEFAULT))
{
if (zclient->sock > 0)
zebra_redistribute_send (ZEBRA_REDISTRIBUTE_DELETE,
- zclient, redist_type[i].type);
+ zclient, redist_type[i].type,
+ VRF_DEFAULT);
- zclient->redist[redist_type[i].type] = 0;
+ vrf_bitmap_unset (zclient->redist[redist_type[i].type], VRF_DEFAULT);
/* Remove the routes from RIPng table. */
ripng_redistribute_withdraw (redist_type[i].type);
@@ -314,7 +309,7 @@ DEFUN (ripng_redistribute_ripng,
"Redistribute information from another routing protocol\n"
"RIPng route\n")
{
- zclient->redist[ZEBRA_ROUTE_RIPNG] = 1;
+ vrf_bitmap_set (zclient->redist[ZEBRA_ROUTE_RIPNG], VRF_DEFAULT);
return CMD_SUCCESS;
}
@@ -325,7 +320,7 @@ DEFUN (no_ripng_redistribute_ripng,
"Redistribute information from another routing protocol\n"
"RIPng route\n")
{
- zclient->redist[ZEBRA_ROUTE_RIPNG] = 0;
+ vrf_bitmap_unset (zclient->redist[ZEBRA_ROUTE_RIPNG], VRF_DEFAULT);
return CMD_SUCCESS;
}
@@ -345,7 +340,7 @@ DEFUN (ripng_redistribute_type,
return CMD_WARNING;
}
- zclient_redistribute (ZEBRA_REDISTRIBUTE_ADD, zclient, type);
+ zclient_redistribute (ZEBRA_REDISTRIBUTE_ADD, zclient, type, VRF_DEFAULT);
return CMD_SUCCESS;
}
@@ -393,7 +388,7 @@ DEFUN (ripng_redistribute_type_metric,
}
ripng_redistribute_metric_set (type, metric);
- zclient_redistribute (ZEBRA_REDISTRIBUTE_ADD, zclient, type);
+ zclient_redistribute (ZEBRA_REDISTRIBUTE_ADD, zclient, type, VRF_DEFAULT);
return CMD_SUCCESS;
}
@@ -425,7 +420,7 @@ DEFUN (ripng_redistribute_type_routemap,
}
ripng_redistribute_routemap_set (type, argv[1]);
- zclient_redistribute (ZEBRA_REDISTRIBUTE_ADD, zclient, type);
+ zclient_redistribute (ZEBRA_REDISTRIBUTE_ADD, zclient, type, VRF_DEFAULT);
return CMD_SUCCESS;
}
@@ -462,7 +457,7 @@ DEFUN (ripng_redistribute_type_metric_routemap,
ripng_redistribute_metric_set (type, metric);
ripng_redistribute_routemap_set (type, argv[2]);
- zclient_redistribute (ZEBRA_REDISTRIBUTE_ADD, zclient, type);
+ zclient_redistribute (ZEBRA_REDISTRIBUTE_ADD, zclient, type, VRF_DEFAULT);
return CMD_SUCCESS;
}
@@ -481,7 +476,8 @@ ripng_redistribute_write (struct vty *vty, int config_mode)
int i;
for (i = 0; i < ZEBRA_ROUTE_MAX; i++)
- if (i != zclient->redist_default && zclient->redist[i])
+ if (i != zclient->redist_default &&
+ vrf_bitmap_check (zclient->redist[i], VRF_DEFAULT))
{
if (config_mode)
{
@@ -521,7 +517,7 @@ zebra_config_write (struct vty *vty)
vty_out (vty, "no router zebra%s", VTY_NEWLINE);
return 1;
}
- else if (! zclient->redist[ZEBRA_ROUTE_RIPNG])
+ else if (! vrf_bitmap_check (zclient->redist[ZEBRA_ROUTE_RIPNG], VRF_DEFAULT))
{
vty_out (vty, "router zebra%s", VTY_NEWLINE);
vty_out (vty, " no redistribute ripng%s", VTY_NEWLINE);
@@ -537,6 +533,12 @@ static struct cmd_node zebra_node =
"%s(config-router)# ",
};
+static void
+ripng_zebra_connected (struct zclient *zclient)
+{
+ zclient_send_requests (zclient, VRF_DEFAULT);
+}
+
/* Initialize zebra structure and it's commands. */
void
zebra_init ()
@@ -545,6 +547,7 @@ zebra_init ()
zclient = zclient_new ();
zclient_init (zclient, ZEBRA_ROUTE_RIPNG);
+ zclient->zebra_connected = ripng_zebra_connected;
zclient->interface_up = ripng_interface_up;
zclient->interface_down = ripng_interface_down;
zclient->interface_add = ripng_interface_add;
diff --git a/ripngd/ripngd.h b/ripngd/ripngd.h
index 706ff542..28ca41bc 100644
--- a/ripngd/ripngd.h
+++ b/ripngd/ripngd.h
@@ -408,12 +408,18 @@ extern int ripng_send_packet (caddr_t buf, int bufsize,
extern void ripng_packet_dump (struct ripng_packet *packet, int size,
const char *sndrcv);
-extern int ripng_interface_up (int command, struct zclient *, zebra_size_t);
-extern int ripng_interface_down (int command, struct zclient *, zebra_size_t);
-extern int ripng_interface_add (int command, struct zclient *, zebra_size_t);
-extern int ripng_interface_delete (int command, struct zclient *, zebra_size_t);
-extern int ripng_interface_address_add (int command, struct zclient *, zebra_size_t);
-extern int ripng_interface_address_delete (int command, struct zclient *, zebra_size_t);
+extern int ripng_interface_up (int command, struct zclient *, zebra_size_t,
+ vrf_id_t);
+extern int ripng_interface_down (int command, struct zclient *, zebra_size_t,
+ vrf_id_t);
+extern int ripng_interface_add (int command, struct zclient *, zebra_size_t,
+ vrf_id_t);
+extern int ripng_interface_delete (int command, struct zclient *, zebra_size_t,
+ vrf_id_t);
+extern int ripng_interface_address_add (int command, struct zclient *, zebra_size_t,
+ vrf_id_t);
+extern int ripng_interface_address_delete (int command, struct zclient *, zebra_size_t,
+ vrf_id_t);
extern int ripng_network_write (struct vty *, int);
diff --git a/zebra/client_main.c b/zebra/client_main.c
index 8b95907b..06afc56d 100644
--- a/zebra/client_main.c
+++ b/zebra/client_main.c
@@ -54,6 +54,7 @@ zebra_test_ipv4 (int command, int type, char *prefix, char *gateway,
inet_aton (gateway, &gate);
gpnt = &gate;
+ api.vrf_id = VRF_DEFAULT;
api.type = type;
api.flags = 0;
diff --git a/zebra/redistribute.c b/zebra/redistribute.c
index 8bf8ea8c..5ec82198 100644
--- a/zebra/redistribute.c
+++ b/zebra/redistribute.c
@@ -68,7 +68,7 @@ zebra_check_addr (struct prefix *p)
return 1;
}
-static int
+int
is_default (struct prefix *p)
{
if (p->family == AF_INET)
@@ -86,7 +86,7 @@ is_default (struct prefix *p)
}
static void
-zebra_redistribute_default (struct zserv *client)
+zebra_redistribute_default (struct zserv *client, vrf_id_t vrf_id)
{
struct prefix_ipv4 p;
struct route_table *table;
@@ -102,7 +102,7 @@ zebra_redistribute_default (struct zserv *client)
p.family = AF_INET;
/* Lookup table. */
- table = zebra_vrf_table (AFI_IP, SAFI_UNICAST, VRF_DEFAULT);
+ table = zebra_vrf_table (AFI_IP, SAFI_UNICAST, vrf_id);
if (table)
{
rn = route_node_lookup (table, (struct prefix *)&p);
@@ -122,7 +122,7 @@ zebra_redistribute_default (struct zserv *client)
p6.family = AF_INET6;
/* Lookup table. */
- table = zebra_vrf_table (AFI_IP6, SAFI_UNICAST, VRF_DEFAULT);
+ table = zebra_vrf_table (AFI_IP6, SAFI_UNICAST, vrf_id);
if (table)
{
rn = route_node_lookup (table, (struct prefix *)&p6);
@@ -140,13 +140,13 @@ zebra_redistribute_default (struct zserv *client)
/* Redistribute routes. */
static void
-zebra_redistribute (struct zserv *client, int type)
+zebra_redistribute (struct zserv *client, int type, vrf_id_t vrf_id)
{
struct rib *newrib;
struct route_table *table;
struct route_node *rn;
- table = zebra_vrf_table (AFI_IP, SAFI_UNICAST, VRF_DEFAULT);
+ table = zebra_vrf_table (AFI_IP, SAFI_UNICAST, vrf_id);
if (table)
for (rn = route_top (table); rn; rn = route_next (rn))
RNODE_FOREACH_RIB (rn, newrib)
@@ -157,7 +157,7 @@ zebra_redistribute (struct zserv *client, int type)
zsend_route_multipath (ZEBRA_IPV4_ROUTE_ADD, client, &rn->p, newrib);
#ifdef HAVE_IPV6
- table = zebra_vrf_table (AFI_IP6, SAFI_UNICAST, VRF_DEFAULT);
+ table = zebra_vrf_table (AFI_IP6, SAFI_UNICAST, vrf_id);
if (table)
for (rn = route_top (table); rn; rn = route_next (rn))
RNODE_FOREACH_RIB (rn, newrib)
@@ -177,8 +177,9 @@ redistribute_add (struct prefix *p, struct rib *rib)
for (ALL_LIST_ELEMENTS (zebrad.client_list, node, nnode, client))
{
- if ((is_default (p) && client->redist_default)
- || client->redist[rib->type])
+ if ((is_default (p) &&
+ vrf_bitmap_check (client->redist_default, rib->vrf_id))
+ || vrf_bitmap_check (client->redist[rib->type], rib->vrf_id))
{
if (p->family == AF_INET)
zsend_route_multipath (ZEBRA_IPV4_ROUTE_ADD, client, p, rib);
@@ -202,8 +203,9 @@ redistribute_delete (struct prefix *p, struct rib *rib)
for (ALL_LIST_ELEMENTS (zebrad.client_list, node, nnode, client))
{
- if ((is_default (p) && client->redist_default)
- || client->redist[rib->type])
+ if ((is_default (p) &&
+ vrf_bitmap_check (client->redist_default, rib->vrf_id))
+ || vrf_bitmap_check (client->redist[rib->type], rib->vrf_id))
{
if (p->family == AF_INET)
zsend_route_multipath (ZEBRA_IPV4_ROUTE_DELETE, client, p, rib);
@@ -216,7 +218,8 @@ redistribute_delete (struct prefix *p, struct rib *rib)
}
void
-zebra_redistribute_add (int command, struct zserv *client, int length)
+zebra_redistribute_add (int command, struct zserv *client, int length,
+ vrf_id_t vrf_id)
{
int type;
@@ -225,15 +228,16 @@ zebra_redistribute_add (int command, struct zserv *client, int length)
if (type == 0 || type >= ZEBRA_ROUTE_MAX)
return;
- if (! client->redist[type])
+ if (! vrf_bitmap_check (client->redist[type], vrf_id))
{
- client->redist[type] = 1;
- zebra_redistribute (client, type);
+ vrf_bitmap_set (client->redist[type], vrf_id);
+ zebra_redistribute (client, type, vrf_id);
}
}
void
-zebra_redistribute_delete (int command, struct zserv *client, int length)
+zebra_redistribute_delete (int command, struct zserv *client, int length,
+ vrf_id_t vrf_id)
{
int type;
@@ -242,21 +246,22 @@ zebra_redistribute_delete (int command, struct zserv *client, int length)
if (type == 0 || type >= ZEBRA_ROUTE_MAX)
return;
- client->redist[type] = 0;
+ vrf_bitmap_unset (client->redist[type], vrf_id);
}
void
-zebra_redistribute_default_add (int command, struct zserv *client, int length)
+zebra_redistribute_default_add (int command, struct zserv *client, int length,
+ vrf_id_t vrf_id)
{
- client->redist_default = 1;
- zebra_redistribute_default (client);
+ vrf_bitmap_set (client->redist_default, vrf_id);
+ zebra_redistribute_default (client, vrf_id);
}
void
zebra_redistribute_default_delete (int command, struct zserv *client,
- int length)
+ int length, vrf_id_t vrf_id)
{
- client->redist_default = 0;;
+ vrf_bitmap_unset (client->redist_default, vrf_id);
}
/* Interface up information. */
diff --git a/zebra/redistribute.h b/zebra/redistribute.h
index 9ed99bc5..6a36f4d8 100644
--- a/zebra/redistribute.h
+++ b/zebra/redistribute.h
@@ -26,11 +26,13 @@
#include "table.h"
#include "zserv.h"
-extern void zebra_redistribute_add (int, struct zserv *, int);
-extern void zebra_redistribute_delete (int, struct zserv *, int);
+extern void zebra_redistribute_add (int, struct zserv *, int, vrf_id_t);
+extern void zebra_redistribute_delete (int, struct zserv *, int, vrf_id_t);
-extern void zebra_redistribute_default_add (int, struct zserv *, int);
-extern void zebra_redistribute_default_delete (int, struct zserv *, int);
+extern void zebra_redistribute_default_add (int, struct zserv *, int,
+ vrf_id_t);
+extern void zebra_redistribute_default_delete (int, struct zserv *, int,
+ vrf_id_t);
extern void redistribute_add (struct prefix *, struct rib *);
extern void redistribute_delete (struct prefix *, struct rib *);
@@ -48,5 +50,7 @@ extern void zebra_interface_address_delete_update (struct interface *,
extern int zebra_check_addr (struct prefix *);
+extern int is_default (struct prefix *);
+
#endif /* _ZEBRA_REDISTRIBUTE_H */
diff --git a/zebra/redistribute_null.c b/zebra/redistribute_null.c
index c45ebe1d..c68cec6a 100644
--- a/zebra/redistribute_null.c
+++ b/zebra/redistribute_null.c
@@ -25,18 +25,22 @@
#include "zebra/redistribute.h"
-void zebra_redistribute_add (int a, struct zserv *b, int c)
+void zebra_redistribute_add (int a, struct zserv *b, int c,
+ vrf_id_t vrf_id)
{ return; }
#ifdef HAVE_SYS_WEAK_ALIAS_PRAGMA
#pragma weak zebra_redistribute_delete = zebra_redistribute_add
#pragma weak zebra_redistribute_default_add = zebra_redistribute_add
#pragma weak zebra_redistribute_default_delete = zebra_redistribute_add
#else
-void zebra_redistribute_delete (int a, struct zserv *b, int c)
+void zebra_redistribute_delete (int a, struct zserv *b, int c,
+ vrf_id_t vrf_id)
{ return; }
-void zebra_redistribute_default_add (int a, struct zserv *b, int c)
+void zebra_redistribute_default_add (int a, struct zserv *b, int c,
+ vrf_id_t vrf_id)
{ return; }
-void zebra_redistribute_default_delete (int a, struct zserv *b, int c)
+void zebra_redistribute_default_delete (int a, struct zserv *b, int c,
+ vrf_id_t vrf_id)
{ return; }
#endif
diff --git a/zebra/zserv.c b/zebra/zserv.c
index e17bb720..8ca56156 100644
--- a/zebra/zserv.c
+++ b/zebra/zserv.c
@@ -132,12 +132,13 @@ zebra_server_send_message(struct zserv *client)
}
static void
-zserv_create_header (struct stream *s, uint16_t cmd)
+zserv_create_header (struct stream *s, uint16_t cmd, vrf_id_t vrf_id)
{
/* length placeholder, caller can update */
stream_putw (s, ZEBRA_HEADER_SIZE);
stream_putc (s, ZEBRA_HEADER_MARKER);
stream_putc (s, ZSERV_VERSION);
+ stream_putw (s, vrf_id);
stream_putw (s, cmd);
}
@@ -182,13 +183,13 @@ zsend_interface_add (struct zserv *client, struct interface *ifp)
struct stream *s;
/* Check this client need interface information. */
- if (! client->ifinfo)
+ if (! vrf_bitmap_check (client->ifinfo, ifp->vrf_id))
return 0;
s = client->obuf;
stream_reset (s);
- zserv_create_header (s, ZEBRA_INTERFACE_ADD);
+ zserv_create_header (s, ZEBRA_INTERFACE_ADD, ifp->vrf_id);
zserv_encode_interface (s, ifp);
return zebra_server_send_message(client);
@@ -201,13 +202,13 @@ zsend_interface_delete (struct zserv *client, struct interface *ifp)
struct stream *s;
/* Check this client need interface information. */
- if (! client->ifinfo)
+ if (! vrf_bitmap_check (client->ifinfo, ifp->vrf_id))
return 0;
s = client->obuf;
stream_reset (s);
- zserv_create_header (s, ZEBRA_INTERFACE_DELETE);
+ zserv_create_header (s, ZEBRA_INTERFACE_DELETE, ifp->vrf_id);
zserv_encode_interface (s, ifp);
return zebra_server_send_message (client);
@@ -260,13 +261,13 @@ zsend_interface_address (int cmd, struct zserv *client,
struct prefix *p;
/* Check this client need interface information. */
- if (! client->ifinfo)
+ if (! vrf_bitmap_check (client->ifinfo, ifp->vrf_id))
return 0;
s = client->obuf;
stream_reset (s);
- zserv_create_header (s, cmd);
+ zserv_create_header (s, cmd, ifp->vrf_id);
stream_putl (s, ifp->ifindex);
/* Interface address flag. */
@@ -314,13 +315,13 @@ zsend_interface_update (int cmd, struct zserv *client, struct interface *ifp)
struct stream *s;
/* Check this client need interface information. */
- if (! client->ifinfo)
+ if (! vrf_bitmap_check (client->ifinfo, ifp->vrf_id))
return 0;
s = client->obuf;
stream_reset (s);
- zserv_create_header (s, cmd);
+ zserv_create_header (s, cmd, ifp->vrf_id);
zserv_encode_interface (s, ifp);
return zebra_server_send_message(client);
@@ -359,11 +360,17 @@ zsend_route_multipath (int cmd, struct zserv *client, struct prefix *p,
unsigned long nhnummark = 0, messmark = 0;
int nhnum = 0;
u_char zapi_flags = 0;
-
+
+ /* Check this client need this route. */
+ if (!vrf_bitmap_check (client->redist[rib->type], rib->vrf_id) &&
+ !(is_default (p) &&
+ vrf_bitmap_check (client->redist_default, rib->vrf_id)))
+ return 0;
+
s = client->obuf;
stream_reset (s);
- zserv_create_header (s, cmd);
+ zserv_create_header (s, cmd, rib->vrf_id);
/* Put type and nexthop. */
stream_putc (s, rib->type);
@@ -465,7 +472,8 @@ zsend_route_multipath (int cmd, struct zserv *client, struct prefix *p,
#ifdef HAVE_IPV6
static int
-zsend_ipv6_nexthop_lookup (struct zserv *client, struct in6_addr *addr)
+zsend_ipv6_nexthop_lookup (struct zserv *client, struct in6_addr *addr,
+ vrf_id_t vrf_id)
{
struct stream *s;
struct rib *rib;
@@ -474,14 +482,14 @@ zsend_ipv6_nexthop_lookup (struct zserv *client, struct in6_addr *addr)
struct nexthop *nexthop;
/* Lookup nexthop. */
- rib = rib_match_ipv6 (addr, VRF_DEFAULT);
+ rib = rib_match_ipv6 (addr, vrf_id);
/* Get output stream. */
s = client->obuf;
stream_reset (s);
/* Fill in result. */
- zserv_create_header (s, ZEBRA_IPV6_NEXTHOP_LOOKUP);
+ zserv_create_header (s, ZEBRA_IPV6_NEXTHOP_LOOKUP, vrf_id);
stream_put (s, &addr, 16);
if (rib)
@@ -532,7 +540,8 @@ zsend_ipv6_nexthop_lookup (struct zserv *client, struct in6_addr *addr)
#endif /* HAVE_IPV6 */
static int
-zsend_ipv4_nexthop_lookup (struct zserv *client, struct in_addr addr)
+zsend_ipv4_nexthop_lookup (struct zserv *client, struct in_addr addr,
+ vrf_id_t vrf_id)
{
struct stream *s;
struct rib *rib;
@@ -541,14 +550,14 @@ zsend_ipv4_nexthop_lookup (struct zserv *client, struct in_addr addr)
struct nexthop *nexthop;
/* Lookup nexthop - eBGP excluded */
- rib = rib_match_ipv4_safi (addr, SAFI_UNICAST, 1, NULL, VRF_DEFAULT);
+ rib = rib_match_ipv4_safi (addr, SAFI_UNICAST, 1, NULL, vrf_id);
/* Get output stream. */
s = client->obuf;
stream_reset (s);
/* Fill in result. */
- zserv_create_header (s, ZEBRA_IPV4_NEXTHOP_LOOKUP);
+ zserv_create_header (s, ZEBRA_IPV4_NEXTHOP_LOOKUP, vrf_id);
stream_put_in_addr (s, &addr);
if (rib)
@@ -619,7 +628,7 @@ zsend_ipv4_nexthop_lookup_mrib (struct zserv *client, struct in_addr addr,
stream_reset (s);
/* Fill in result. */
- zserv_create_header (s, ZEBRA_IPV4_NEXTHOP_LOOKUP_MRIB);
+ zserv_create_header (s, ZEBRA_IPV4_NEXTHOP_LOOKUP_MRIB, rib->vrf_id);
stream_put_in_addr (s, &addr);
if (rib)
@@ -671,7 +680,8 @@ zsend_ipv4_nexthop_lookup_mrib (struct zserv *client, struct in_addr addr,
}
static int
-zsend_ipv4_import_lookup (struct zserv *client, struct prefix_ipv4 *p)
+zsend_ipv4_import_lookup (struct zserv *client, struct prefix_ipv4 *p,
+ vrf_id_t vrf_id)
{
struct stream *s;
struct rib *rib;
@@ -680,14 +690,14 @@ zsend_ipv4_import_lookup (struct zserv *client, struct prefix_ipv4 *p)
struct nexthop *nexthop;
/* Lookup nexthop. */
- rib = rib_lookup_ipv4 (p, VRF_DEFAULT);
+ rib = rib_lookup_ipv4 (p, vrf_id);
/* Get output stream. */
s = client->obuf;
stream_reset (s);
/* Fill in result. */
- zserv_create_header (s, ZEBRA_IPV4_IMPORT_LOOKUP);
+ zserv_create_header (s, ZEBRA_IPV4_IMPORT_LOOKUP, vrf_id);
stream_put_in_addr (s, &p->prefix);
if (rib)
@@ -742,14 +752,14 @@ zsend_router_id_update (struct zserv *client, struct prefix *p,
int blen;
/* Check this client need interface information. */
- if (!client->ridinfo)
+ if (! vrf_bitmap_check (client->ridinfo, vrf_id))
return 0;
s = client->obuf;
stream_reset (s);
/* Message type. */
- zserv_create_header (s, ZEBRA_ROUTER_ID_UPDATE);
+ zserv_create_header (s, ZEBRA_ROUTER_ID_UPDATE, vrf_id);
/* Prefix information. */
stream_putc (s, p->family);
@@ -766,7 +776,7 @@ zsend_router_id_update (struct zserv *client, struct prefix *p,
/* Register zebra server interface information. Send current all
interface and address information. */
static int
-zread_interface_add (struct zserv *client, u_short length)
+zread_interface_add (struct zserv *client, u_short length, vrf_id_t vrf_id)
{
struct listnode *ifnode, *ifnnode;
struct listnode *cnode, *cnnode;
@@ -774,9 +784,9 @@ zread_interface_add (struct zserv *client, u_short length)
struct connected *c;
/* Interface information is needed. */
- client->ifinfo = 1;
+ vrf_bitmap_set (client->ifinfo, vrf_id);
- for (ALL_LIST_ELEMENTS (iflist, ifnode, ifnnode, ifp))
+ for (ALL_LIST_ELEMENTS (vrf_iflist (vrf_id), ifnode, ifnnode, ifp))
{
/* Skip pseudo interface. */
if (! CHECK_FLAG (ifp->status, ZEBRA_INTERFACE_ACTIVE))
@@ -798,9 +808,9 @@ zread_interface_add (struct zserv *client, u_short length)
/* Unregister zebra server interface information. */
static int
-zread_interface_delete (struct zserv *client, u_short length)
+zread_interface_delete (struct zserv *client, u_short length, vrf_id_t vrf_id)
{
- client->ifinfo = 0;
+ vrf_bitmap_unset (client->ifinfo, vrf_id);
return 0;
}
@@ -810,7 +820,7 @@ zread_interface_delete (struct zserv *client, u_short length)
* add kernel route.
*/
static int
-zread_ipv4_add (struct zserv *client, u_short length)
+zread_ipv4_add (struct zserv *client, u_short length, vrf_id_t vrf_id)
{
int i;
struct rib *rib;
@@ -845,7 +855,7 @@ zread_ipv4_add (struct zserv *client, u_short length)
stream_get (&p.prefix, s, PSIZE (p.prefixlen));
/* VRF ID */
- rib->vrf_id = VRF_DEFAULT;
+ rib->vrf_id = vrf_id;
/* Nexthop parse. */
if (CHECK_FLAG (message, ZAPI_MESSAGE_NEXTHOP))
@@ -901,7 +911,7 @@ zread_ipv4_add (struct zserv *client, u_short length)
/* Zebra server IPv4 prefix delete function. */
static int
-zread_ipv4_delete (struct zserv *client, u_short length)
+zread_ipv4_delete (struct zserv *client, u_short length, vrf_id_t vrf_id)
{
int i;
struct stream *s;
@@ -977,13 +987,14 @@ zread_ipv4_delete (struct zserv *client, u_short length)
api.metric = 0;
rib_delete_ipv4 (api.type, api.flags, &p, nexthop_p, ifindex,
- VRF_DEFAULT, api.safi);
+ vrf_id, api.safi);
return 0;
}
/* Nexthop lookup for IPv4. */
static int
-zread_ipv4_nexthop_lookup (struct zserv *client, u_short length)
+zread_ipv4_nexthop_lookup (struct zserv *client, u_short length,
+ vrf_id_t vrf_id)
{
struct in_addr addr;
char buf[BUFSIZ];
@@ -992,24 +1003,26 @@ zread_ipv4_nexthop_lookup (struct zserv *client, u_short length)
if (IS_ZEBRA_DEBUG_PACKET && IS_ZEBRA_DEBUG_RECV)
zlog_debug("%s: looking up %s", __func__,
inet_ntop (AF_INET, &addr, buf, BUFSIZ));
- return zsend_ipv4_nexthop_lookup (client, addr);
+ return zsend_ipv4_nexthop_lookup (client, addr, vrf_id);
}
/* MRIB Nexthop lookup for IPv4. */
static int
-zread_ipv4_nexthop_lookup_mrib (struct zserv *client, u_short length)
+zread_ipv4_nexthop_lookup_mrib (struct zserv *client, u_short length,
+ vrf_id_t vrf_id)
{
struct in_addr addr;
struct rib *rib;
addr.s_addr = stream_get_ipv4 (client->ibuf);
- rib = rib_match_ipv4_multicast (addr, NULL, VRF_DEFAULT);
+ rib = rib_match_ipv4_multicast (addr, NULL, vrf_id);
return zsend_ipv4_nexthop_lookup_mrib (client, addr, rib);
}
/* Nexthop lookup for IPv4. */
static int
-zread_ipv4_import_lookup (struct zserv *client, u_short length)
+zread_ipv4_import_lookup (struct zserv *client, u_short length,
+ vrf_id_t vrf_id)
{
struct prefix_ipv4 p;
@@ -1017,13 +1030,13 @@ zread_ipv4_import_lookup (struct zserv *client, u_short length)
p.prefixlen = stream_getc (client->ibuf);
p.prefix.s_addr = stream_get_ipv4 (client->ibuf);
- return zsend_ipv4_import_lookup (client, &p);
+ return zsend_ipv4_import_lookup (client, &p, vrf_id);
}
#ifdef HAVE_IPV6
/* Zebra server IPv6 prefix add function. */
static int
-zread_ipv6_add (struct zserv *client, u_short length)
+zread_ipv6_add (struct zserv *client, u_short length, vrf_id_t vrf_id)
{
int i;
struct stream *s;
@@ -1082,18 +1095,18 @@ zread_ipv6_add (struct zserv *client, u_short length)
if (IN6_IS_ADDR_UNSPECIFIED (&nexthop))
rib_add_ipv6 (api.type, api.flags, &p, NULL, ifindex,
- VRF_DEFAULT, zebrad.rtm_table_default, api.metric,
+ vrf_id, zebrad.rtm_table_default, api.metric,
api.distance, api.safi);
else
rib_add_ipv6 (api.type, api.flags, &p, &nexthop, ifindex,
- VRF_DEFAULT, zebrad.rtm_table_default, api.metric,
+ vrf_id, zebrad.rtm_table_default, api.metric,
api.distance, api.safi);
return 0;
}
/* Zebra server IPv6 prefix delete function. */
static int
-zread_ipv6_delete (struct zserv *client, u_short length)
+zread_ipv6_delete (struct zserv *client, u_short length, vrf_id_t vrf_id)
{
int i;
struct stream *s;
@@ -1150,16 +1163,17 @@ zread_ipv6_delete (struct zserv *client, u_short length)
api.metric = 0;
if (IN6_IS_ADDR_UNSPECIFIED (&nexthop))
- rib_delete_ipv6 (api.type, api.flags, &p, NULL, ifindex, VRF_DEFAULT,
+ rib_delete_ipv6 (api.type, api.flags, &p, NULL, ifindex, vrf_id,
api.safi);
else
- rib_delete_ipv6 (api.type, api.flags, &p, &nexthop, ifindex, VRF_DEFAULT,
+ rib_delete_ipv6 (api.type, api.flags, &p, &nexthop, ifindex, vrf_id,
api.safi);
return 0;
}
static int
-zread_ipv6_nexthop_lookup (struct zserv *client, u_short length)
+zread_ipv6_nexthop_lookup (struct zserv *client, u_short length,
+ vrf_id_t vrf_id)
{
struct in6_addr addr;
char buf[BUFSIZ];
@@ -1169,29 +1183,29 @@ zread_ipv6_nexthop_lookup (struct zserv *client, u_short length)
zlog_debug("%s: looking up %s", __func__,
inet_ntop (AF_INET6, &addr, buf, BUFSIZ));
- return zsend_ipv6_nexthop_lookup (client, &addr);
+ return zsend_ipv6_nexthop_lookup (client, &addr, vrf_id);
}
#endif /* HAVE_IPV6 */
/* Register zebra server router-id information. Send current router-id */
static int
-zread_router_id_add (struct zserv *client, u_short length)
+zread_router_id_add (struct zserv *client, u_short length, vrf_id_t vrf_id)
{
struct prefix p;
/* Router-id information is needed. */
- client->ridinfo = 1;
+ vrf_bitmap_set (client->ridinfo, vrf_id);
- router_id_get (&p, VRF_DEFAULT);
+ router_id_get (&p, vrf_id);
- return zsend_router_id_update (client, &p, VRF_DEFAULT);
+ return zsend_router_id_update (client, &p, vrf_id);
}
/* Unregister zebra server router-id information. */
static int
-zread_router_id_delete (struct zserv *client, u_short length)
+zread_router_id_delete (struct zserv *client, u_short length, vrf_id_t vrf_id)
{
- client->ridinfo = 0;
+ vrf_bitmap_unset (client->ridinfo, vrf_id);
return 0;
}
@@ -1220,6 +1234,21 @@ zread_hello (struct zserv *client)
}
}
+/* Unregister all information in a VRF. */
+static int
+zread_vrf_unregister (struct zserv *client, u_short length, vrf_id_t vrf_id)
+{
+ int i;
+
+ for (i = 0; i < ZEBRA_ROUTE_MAX; i++)
+ vrf_bitmap_unset (client->redist[i], vrf_id);
+ vrf_bitmap_unset (client->redist_default, vrf_id);
+ vrf_bitmap_unset (client->ifinfo, vrf_id);
+ vrf_bitmap_unset (client->ridinfo, vrf_id);
+
+ return 0;
+}
+
/* If client sent routes of specific type, zebra removes it
* and returns number of deleted routes.
*/
@@ -1276,6 +1305,7 @@ static void
zebra_client_create (int sock)
{
struct zserv *client;
+ int i;
client = XCALLOC (0, sizeof (struct zserv));
@@ -1288,6 +1318,13 @@ zebra_client_create (int sock)
/* Set table number. */
client->rtm_table = zebrad.rtm_table_default;
+ /* Initialize flags */
+ for (i = 0; i < ZEBRA_ROUTE_MAX; i++)
+ client->redist[i] = vrf_bitmap_init ();
+ client->redist_default = vrf_bitmap_init ();
+ client->ifinfo = vrf_bitmap_init ();
+ client->ridinfo = vrf_bitmap_init ();
+
/* Add this client to linked list. */
listnode_add (zebrad.client_list, client);
@@ -1304,6 +1341,7 @@ zebra_client_read (struct thread *thread)
size_t already;
uint16_t length, command;
uint8_t marker, version;
+ vrf_id_t vrf_id;
/* Get thread data. Reset reading thread because I'm running. */
sock = THREAD_FD (thread);
@@ -1345,6 +1383,7 @@ zebra_client_read (struct thread *thread)
length = stream_getw (client->ibuf);
marker = stream_getc (client->ibuf);
version = stream_getc (client->ibuf);
+ vrf_id = stream_getw (client->ibuf);
command = stream_getw (client->ibuf);
if (marker != ZEBRA_HEADER_MARKER || version != ZSERV_VERSION)
@@ -1397,66 +1436,69 @@ zebra_client_read (struct thread *thread)
zlog_debug ("zebra message comes from socket [%d]", sock);
if (IS_ZEBRA_DEBUG_PACKET && IS_ZEBRA_DEBUG_RECV)
- zlog_debug ("zebra message received [%s] %d",
- zserv_command_string (command), length);
+ zlog_debug ("zebra message received [%s] %d in VRF %u",
+ zserv_command_string (command), length, vrf_id);
switch (command)
{
case ZEBRA_ROUTER_ID_ADD:
- zread_router_id_add (client, length);
+ zread_router_id_add (client, length, vrf_id);
break;
case ZEBRA_ROUTER_ID_DELETE:
- zread_router_id_delete (client, length);
+ zread_router_id_delete (client, length, vrf_id);
break;
case ZEBRA_INTERFACE_ADD:
- zread_interface_add (client, length);
+ zread_interface_add (client, length, vrf_id);
break;
case ZEBRA_INTERFACE_DELETE:
- zread_interface_delete (client, length);
+ zread_interface_delete (client, length, vrf_id);
break;
case ZEBRA_IPV4_ROUTE_ADD:
- zread_ipv4_add (client, length);
+ zread_ipv4_add (client, length, vrf_id);
break;
case ZEBRA_IPV4_ROUTE_DELETE:
- zread_ipv4_delete (client, length);
+ zread_ipv4_delete (client, length, vrf_id);
break;
#ifdef HAVE_IPV6
case ZEBRA_IPV6_ROUTE_ADD:
- zread_ipv6_add (client, length);
+ zread_ipv6_add (client, length, vrf_id);
break;
case ZEBRA_IPV6_ROUTE_DELETE:
- zread_ipv6_delete (client, length);
+ zread_ipv6_delete (client, length, vrf_id);
break;
#endif /* HAVE_IPV6 */
case ZEBRA_REDISTRIBUTE_ADD:
- zebra_redistribute_add (command, client, length);
+ zebra_redistribute_add (command, client, length, vrf_id);
break;
case ZEBRA_REDISTRIBUTE_DELETE:
- zebra_redistribute_delete (command, client, length);
+ zebra_redistribute_delete (command, client, length, vrf_id);
break;
case ZEBRA_REDISTRIBUTE_DEFAULT_ADD:
- zebra_redistribute_default_add (command, client, length);
+ zebra_redistribute_default_add (command, client, length, vrf_id);
break;
case ZEBRA_REDISTRIBUTE_DEFAULT_DELETE:
- zebra_redistribute_default_delete (command, client, length);
+ zebra_redistribute_default_delete (command, client, length, vrf_id);
break;
case ZEBRA_IPV4_NEXTHOP_LOOKUP:
- zread_ipv4_nexthop_lookup (client, length);
+ zread_ipv4_nexthop_lookup (client, length, vrf_id);
break;
case ZEBRA_IPV4_NEXTHOP_LOOKUP_MRIB:
- zread_ipv4_nexthop_lookup_mrib (client, length);
+ zread_ipv4_nexthop_lookup_mrib (client, length, vrf_id);
break;
#ifdef HAVE_IPV6
case ZEBRA_IPV6_NEXTHOP_LOOKUP:
- zread_ipv6_nexthop_lookup (client, length);
+ zread_ipv6_nexthop_lookup (client, length, vrf_id);
break;
#endif /* HAVE_IPV6 */
case ZEBRA_IPV4_IMPORT_LOOKUP:
- zread_ipv4_import_lookup (client, length);
+ zread_ipv4_import_lookup (client, length, vrf_id);
break;
case ZEBRA_HELLO:
zread_hello (client);
break;
+ case ZEBRA_VRF_UNREGISTER:
+ zread_vrf_unregister (client, length, vrf_id);
+ break;
default:
zlog_info ("Zebra received unknown command %d", command);
break;
diff --git a/zebra/zserv.h b/zebra/zserv.h
index af005f85..fc01f961 100644
--- a/zebra/zserv.h
+++ b/zebra/zserv.h
@@ -25,6 +25,7 @@
#include "rib.h"
#include "if.h"
#include "workqueue.h"
+#include "vrf.h"
/* Default port information. */
#define ZEBRA_VTY_PORT 2601
@@ -56,16 +57,16 @@ struct zserv
int rtm_table;
/* This client's redistribute flag. */
- u_char redist[ZEBRA_ROUTE_MAX];
+ vrf_bitmap_t redist[ZEBRA_ROUTE_MAX];
/* Redistribute default route flag. */
- u_char redist_default;
+ vrf_bitmap_t redist_default;
/* Interface information. */
- u_char ifinfo;
+ vrf_bitmap_t ifinfo;
/* Router-id information. */
- u_char ridinfo;
+ vrf_bitmap_t ridinfo;
};
/* Zebra instance */