From: Feng Lu <lu.f...@6wind.com>

A new member "vrf_id" is added to "struct rib", reflecting the VRF
which it belongs to.

A new parameter "vrf_id" is added to the relative functions where
need, except those:
- which already have the parameter "vrf_id"; or
- which have a parameter in type of "struct rib"; or
- which have a parameter in type of "struct interface".

All incoming routes are set to default VRF.

In fact, all routes in FIB are kept in default VRF. And the logic
is not changed.

Signed-off-by: Feng Lu <lu.f...@6wind.com>
Reviewed-by: Alain Ritoux <alain.rit...@6wind.com>
Signed-off-by: Nicolas Dichtel <nicolas.dich...@6wind.com>
---
 zebra/connected.c     |  29 +++----
 zebra/interface.c     |   4 +-
 zebra/kernel_socket.c |  24 +++---
 zebra/rib.h           |  38 ++++++----
 zebra/rt_netlink.c    |  22 ++++--
 zebra/rtread_getmsg.c |   4 +-
 zebra/zebra_rib.c     | 205 ++++++++++++++++++++++++++++++--------------------
 zebra/zebra_vty.c     |  20 ++---
 zebra/zserv.c         |  30 +++++---
 9 files changed, 225 insertions(+), 151 deletions(-)

diff --git a/zebra/connected.c b/zebra/connected.c
index 2db981b38bcd..244f291151ee 100644
--- a/zebra/connected.c
+++ b/zebra/connected.c
@@ -192,12 +192,12 @@ connected_up_ipv4 (struct interface *ifp, struct 
connected *ifc)
     return;
 
   rib_add_ipv4 (ZEBRA_ROUTE_CONNECT, 0, &p, NULL, NULL, ifp->ifindex,
-       RT_TABLE_MAIN, ifp->metric, 0, SAFI_UNICAST);
+       ifp->vrf_id, RT_TABLE_MAIN, ifp->metric, 0, SAFI_UNICAST);
 
   rib_add_ipv4 (ZEBRA_ROUTE_CONNECT, 0, &p, NULL, NULL, ifp->ifindex,
-       RT_TABLE_MAIN, ifp->metric, 0, SAFI_MULTICAST);
+       ifp->vrf_id, RT_TABLE_MAIN, ifp->metric, 0, SAFI_MULTICAST);
 
-  rib_update ();
+  rib_update (ifp->vrf_id);
 }
 
 /* Add connected IPv4 route to the interface. */
@@ -304,11 +304,13 @@ connected_down_ipv4 (struct interface *ifp, struct 
connected *ifc)
     return;
 
   /* Same logic as for connected_up_ipv4(): push the changes into the head. */
-  rib_delete_ipv4 (ZEBRA_ROUTE_CONNECT, 0, &p, NULL, ifp->ifindex, 0, 
SAFI_UNICAST);
+  rib_delete_ipv4 (ZEBRA_ROUTE_CONNECT, 0, &p, NULL, ifp->ifindex, ifp->vrf_id,
+                   SAFI_UNICAST);
 
-  rib_delete_ipv4 (ZEBRA_ROUTE_CONNECT, 0, &p, NULL, ifp->ifindex, 0, 
SAFI_MULTICAST);
+  rib_delete_ipv4 (ZEBRA_ROUTE_CONNECT, 0, &p, NULL, ifp->ifindex, ifp->vrf_id,
+                   SAFI_MULTICAST);
 
-  rib_update ();
+  rib_update (ifp->vrf_id);
 }
 
 /* Delete connected IPv4 route to the interface. */
@@ -330,7 +332,7 @@ connected_delete_ipv4 (struct interface *ifp, int flags, 
struct in_addr *addr,
     
   connected_withdraw (ifc);
 
-  rib_update();
+  rib_update (ifp->vrf_id);
 }
 
 #ifdef HAVE_IPV6
@@ -353,10 +355,10 @@ connected_up_ipv6 (struct interface *ifp, struct 
connected *ifc)
     return;
 #endif
 
-  rib_add_ipv6 (ZEBRA_ROUTE_CONNECT, 0, &p, NULL, ifp->ifindex, RT_TABLE_MAIN,
-                ifp->metric, 0, SAFI_UNICAST);
+  rib_add_ipv6 (ZEBRA_ROUTE_CONNECT, 0, &p, NULL, ifp->ifindex, ifp->vrf_id,
+                RT_TABLE_MAIN, ifp->metric, 0, SAFI_UNICAST);
 
-  rib_update ();
+  rib_update (ifp->vrf_id);
 }
 
 /* Add connected IPv6 route to the interface. */
@@ -436,9 +438,10 @@ connected_down_ipv6 (struct interface *ifp, struct 
connected *ifc)
   if (IN6_IS_ADDR_UNSPECIFIED (&p.prefix))
     return;
 
-  rib_delete_ipv6 (ZEBRA_ROUTE_CONNECT, 0, &p, NULL, ifp->ifindex, 0, 
SAFI_UNICAST);
+  rib_delete_ipv6 (ZEBRA_ROUTE_CONNECT, 0, &p, NULL, ifp->ifindex, ifp->vrf_id,
+                   SAFI_UNICAST);
 
-  rib_update ();
+  rib_update (ifp->vrf_id);
 }
 
 void
@@ -459,6 +462,6 @@ connected_delete_ipv6 (struct interface *ifp, struct 
in6_addr *address,
 
   connected_withdraw (ifc);
 
-  rib_update();
+  rib_update (ifp->vrf_id);
 }
 #endif /* HAVE_IPV6 */
diff --git a/zebra/interface.c b/zebra/interface.c
index 07298b65829d..7d63b2ac1469 100644
--- a/zebra/interface.c
+++ b/zebra/interface.c
@@ -555,7 +555,7 @@ if_up (struct interface *ifp)
     }
 
   /* Examine all static routes. */
-  rib_update ();
+  rib_update (ifp->vrf_id);
 }
 
 /* Interface goes down.  We have to manage different behavior of based
@@ -588,7 +588,7 @@ if_down (struct interface *ifp)
     }
 
   /* Examine all static routes which direct to the interface. */
-  rib_update ();
+  rib_update (ifp->vrf_id);
 }
 
 void
diff --git a/zebra/kernel_socket.c b/zebra/kernel_socket.c
index 916dad97f8c6..0b841ec793fa 100644
--- a/zebra/kernel_socket.c
+++ b/zebra/kernel_socket.c
@@ -32,6 +32,7 @@
 #include "table.h"
 #include "rib.h"
 #include "privs.h"
+#include "vrf.h"
 
 #include "zebra/interface.h"
 #include "zebra/zserv.h"
@@ -908,7 +909,7 @@ rtm_read (struct rt_msghdr *rtm)
         int ret;
         if (! IS_ZEBRA_DEBUG_RIB)
           return;
-        ret = rib_lookup_ipv4_route (&p, &gate); 
+        ret = rib_lookup_ipv4_route (&p, &gate, VRF_DEFAULT);
         inet_ntop (AF_INET, &p.prefix, buf, INET_ADDRSTRLEN);
         switch (rtm->rtm_type)
         {
@@ -973,16 +974,16 @@ rtm_read (struct rt_msghdr *rtm)
        */
       if (rtm->rtm_type == RTM_CHANGE)
         rib_delete_ipv4 (ZEBRA_ROUTE_KERNEL, zebra_flags, &p,
-                         NULL, 0, 0, SAFI_UNICAST);
+                         NULL, 0, VRF_DEFAULT, SAFI_UNICAST);
       
       if (rtm->rtm_type == RTM_GET 
           || rtm->rtm_type == RTM_ADD
           || rtm->rtm_type == RTM_CHANGE)
-       rib_add_ipv4 (ZEBRA_ROUTE_KERNEL, zebra_flags, 
-                     &p, &gate.sin.sin_addr, NULL, 0, 0, 0, 0, SAFI_UNICAST);
+        rib_add_ipv4 (ZEBRA_ROUTE_KERNEL, zebra_flags, &p, &gate.sin.sin_addr,
+                      NULL, 0, VRF_DEFAULT, rtm->rtm_table, 0, 0, 
SAFI_UNICAST);
       else
-       rib_delete_ipv4 (ZEBRA_ROUTE_KERNEL, zebra_flags, 
-                     &p, &gate.sin.sin_addr, 0, 0, SAFI_UNICAST);
+        rib_delete_ipv4 (ZEBRA_ROUTE_KERNEL, zebra_flags, &p,
+                         &gate.sin.sin_addr, 0, VRF_DEFAULT, SAFI_UNICAST);
     }
 #ifdef HAVE_IPV6
   if (dest.sa.sa_family == AF_INET6)
@@ -1015,16 +1016,17 @@ rtm_read (struct rt_msghdr *rtm)
        */
       if (rtm->rtm_type == RTM_CHANGE)
         rib_delete_ipv6 (ZEBRA_ROUTE_KERNEL, zebra_flags, &p,
-                         NULL, 0, 0, SAFI_UNICAST);
+                         NULL, 0, VRF_DEFAULT, SAFI_UNICAST);
       
       if (rtm->rtm_type == RTM_GET 
           || rtm->rtm_type == RTM_ADD
           || rtm->rtm_type == RTM_CHANGE)
-       rib_add_ipv6 (ZEBRA_ROUTE_KERNEL, zebra_flags,
-                     &p, &gate.sin6.sin6_addr, ifindex, 0, 0, 0, SAFI_UNICAST);
+        rib_add_ipv6 (ZEBRA_ROUTE_KERNEL, zebra_flags, &p, 
&gate.sin6.sin6_addr,
+                      ifindex, VRF_DEFAULT, RT_TABLE_MAIN, 0, 0, SAFI_UNICAST);
       else
-       rib_delete_ipv6 (ZEBRA_ROUTE_KERNEL, zebra_flags,
-                        &p, &gate.sin6.sin6_addr, ifindex, 0, SAFI_UNICAST);
+        rib_delete_ipv6 (ZEBRA_ROUTE_KERNEL, zebra_flags, &p,
+                         &gate.sin6.sin6_addr, ifindex,
+                         VRF_DEFAULT, SAFI_UNICAST);
     }
 #endif /* HAVE_IPV6 */
 }
diff --git a/zebra/rib.h b/zebra/rib.h
index 802d875f8e40..2d8805a88a83 100644
--- a/zebra/rib.h
+++ b/zebra/rib.h
@@ -56,6 +56,9 @@ struct rib
   /* Type fo this route. */
   int type;
 
+  /* VRF identifier. */
+  vrf_id_t vrf_id;
+
   /* Which routing table */
   int table;                   
 
@@ -404,7 +407,8 @@ extern void rib_lookup_and_pushup (struct prefix_ipv4 *);
 #define rib_dump(prefix ,rib) _rib_dump(__func__, prefix, rib)
 extern void _rib_dump (const char *,
                       union prefix46constptr, const struct rib *);
-extern int rib_lookup_ipv4_route (struct prefix_ipv4 *, union sockunion *);
+extern int rib_lookup_ipv4_route (struct prefix_ipv4 *, union sockunion *,
+                                  vrf_id_t);
 #define ZEBRA_RIB_LOOKUP_ERROR -1
 #define ZEBRA_RIB_FOUND_EXACT 0
 #define ZEBRA_RIB_FOUND_NOGATE 1
@@ -424,23 +428,25 @@ extern struct route_table *zebra_vrf_static_table (afi_t, 
safi_t, vrf_id_t);
  * also implicitly withdraw equal prefix of same type. */
 extern int rib_add_ipv4 (int type, int flags, struct prefix_ipv4 *p, 
                         struct in_addr *gate, struct in_addr *src,
-                        unsigned int ifindex, u_int32_t vrf_id,
+                        unsigned int ifindex, vrf_id_t vrf_id, int table_id,
                         u_int32_t, u_char, safi_t);
 
 extern int rib_add_ipv4_multipath (struct prefix_ipv4 *, struct rib *, safi_t);
 
 extern int rib_delete_ipv4 (int type, int flags, struct prefix_ipv4 *p,
                            struct in_addr *gate, unsigned int ifindex, 
-                           u_int32_t, safi_t safi);
+                           vrf_id_t, safi_t safi);
 
 extern struct rib *rib_match_ipv4_safi (struct in_addr addr, safi_t safi,
-                                       int skip_bgp, struct route_node 
**rn_out);
+                                       int skip_bgp, struct route_node 
**rn_out,
+                                       vrf_id_t);
 extern struct rib *rib_match_ipv4_multicast (struct in_addr addr,
-                                            struct route_node **rn_out);
+                                            struct route_node **rn_out,
+                                            vrf_id_t);
 
-extern struct rib *rib_lookup_ipv4 (struct prefix_ipv4 *);
+extern struct rib *rib_lookup_ipv4 (struct prefix_ipv4 *, vrf_id_t);
 
-extern void rib_update (void);
+extern void rib_update (vrf_id_t);
 extern void rib_weed_tables (void);
 extern void rib_sweep_route (void);
 extern void rib_close (void);
@@ -450,35 +456,35 @@ extern unsigned long rib_score_proto (u_char proto);
 extern int
 static_add_ipv4_safi (safi_t safi, struct prefix *p, struct in_addr *gate,
                      const char *ifname, u_char flags, u_char distance,
-                     u_int32_t vrf_id);
+                     vrf_id_t vrf_id);
 extern int
 static_delete_ipv4_safi (safi_t safi, struct prefix *p, struct in_addr *gate,
-                        const char *ifname, u_char distance, u_int32_t vrf_id);
+                        const char *ifname, u_char distance, vrf_id_t vrf_id);
 
 #ifdef HAVE_IPV6
 extern int
 rib_add_ipv6 (int type, int flags, struct prefix_ipv6 *p,
-             struct in6_addr *gate, unsigned int ifindex, u_int32_t vrf_id,
-             u_int32_t metric, u_char distance, safi_t safi);
+             struct in6_addr *gate, unsigned int ifindex, vrf_id_t vrf_id,
+             int table_id, u_int32_t metric, u_char distance, safi_t safi);
 
 extern int
 rib_delete_ipv6 (int type, int flags, struct prefix_ipv6 *p,
-                struct in6_addr *gate, unsigned int ifindex, u_int32_t vrf_id, 
safi_t safi);
+                struct in6_addr *gate, unsigned int ifindex, vrf_id_t vrf_id, 
safi_t safi);
 
-extern struct rib *rib_lookup_ipv6 (struct in6_addr *);
+extern struct rib *rib_lookup_ipv6 (struct in6_addr *, vrf_id_t);
 
-extern struct rib *rib_match_ipv6 (struct in6_addr *);
+extern struct rib *rib_match_ipv6 (struct in6_addr *, vrf_id_t);
 
 extern struct route_table *rib_table_ipv6;
 
 extern int
 static_add_ipv6 (struct prefix *p, u_char type, struct in6_addr *gate,
                 const char *ifname, u_char flags, u_char distance,
-                u_int32_t vrf_id);
+                vrf_id_t vrf_id);
 
 extern int
 static_delete_ipv6 (struct prefix *p, u_char type, struct in6_addr *gate,
-                   const char *ifname, u_char distance, u_int32_t vrf_id);
+                   const char *ifname, u_char distance, vrf_id_t vrf_id);
 
 #endif /* HAVE_IPV6 */
 
diff --git a/zebra/rt_netlink.c b/zebra/rt_netlink.c
index 7e410729765d..be8600e2b450 100644
--- a/zebra/rt_netlink.c
+++ b/zebra/rt_netlink.c
@@ -36,6 +36,7 @@
 #include "rib.h"
 #include "thread.h"
 #include "privs.h"
+#include "vrf.h"
 
 #include "zebra/zserv.h"
 #include "zebra/rt.h"
@@ -743,7 +744,7 @@ netlink_routing_table (struct sockaddr_nl *snl, struct 
nlmsghdr *h)
 
       if (!tb[RTA_MULTIPATH])
           rib_add_ipv4 (ZEBRA_ROUTE_KERNEL, flags, &p, gate, src, index,
-                        table, metric, 0, SAFI_UNICAST);
+                        VRF_DEFAULT, table, metric, 0, SAFI_UNICAST);
       else
         {
           /* This is a multipath route */
@@ -759,6 +760,7 @@ netlink_routing_table (struct sockaddr_nl *snl, struct 
nlmsghdr *h)
           rib->distance = 0;
           rib->flags = flags;
           rib->metric = metric;
+          rib->vrf_id = VRF_DEFAULT;
           rib->table = table;
           rib->nexthop_num = 0;
           rib->uptime = time (NULL);
@@ -808,8 +810,8 @@ netlink_routing_table (struct sockaddr_nl *snl, struct 
nlmsghdr *h)
       memcpy (&p.prefix, dest, 16);
       p.prefixlen = rtm->rtm_dst_len;
 
-      rib_add_ipv6 (ZEBRA_ROUTE_KERNEL, flags, &p, gate, index, table,
-                   metric, 0, SAFI_UNICAST);
+      rib_add_ipv6 (ZEBRA_ROUTE_KERNEL, flags, &p, gate, index, VRF_DEFAULT,
+                    table, metric, 0, SAFI_UNICAST);
     }
 #endif /* HAVE_IPV6 */
 
@@ -944,8 +946,8 @@ netlink_route_change (struct sockaddr_nl *snl, struct 
nlmsghdr *h)
       if (h->nlmsg_type == RTM_NEWROUTE)
         {
           if (!tb[RTA_MULTIPATH])
-            rib_add_ipv4 (ZEBRA_ROUTE_KERNEL, 0, &p, gate, src, index, table,
-                          metric, 0, SAFI_UNICAST);
+            rib_add_ipv4 (ZEBRA_ROUTE_KERNEL, 0, &p, gate, src, index, 
VRF_DEFAULT,
+                          table, metric, 0, SAFI_UNICAST);
           else
             {
               /* This is a multipath route */
@@ -961,6 +963,7 @@ netlink_route_change (struct sockaddr_nl *snl, struct 
nlmsghdr *h)
               rib->distance = 0;
               rib->flags = 0;
               rib->metric = metric;
+              rib->vrf_id = VRF_DEFAULT;
               rib->table = table;
               rib->nexthop_num = 0;
               rib->uptime = time (NULL);
@@ -1003,7 +1006,8 @@ netlink_route_change (struct sockaddr_nl *snl, struct 
nlmsghdr *h)
             }
         }
       else
-        rib_delete_ipv4 (ZEBRA_ROUTE_KERNEL, 0, &p, gate, index, table, 
SAFI_UNICAST);
+        rib_delete_ipv4 (ZEBRA_ROUTE_KERNEL, 0, &p, gate, index, VRF_DEFAULT,
+                         SAFI_UNICAST);
     }
 
 #ifdef HAVE_IPV6
@@ -1029,9 +1033,11 @@ netlink_route_change (struct sockaddr_nl *snl, struct 
nlmsghdr *h)
         }
 
       if (h->nlmsg_type == RTM_NEWROUTE)
-        rib_add_ipv6 (ZEBRA_ROUTE_KERNEL, 0, &p, gate, index, table, metric, 
0, SAFI_UNICAST);
+        rib_add_ipv6 (ZEBRA_ROUTE_KERNEL, 0, &p, gate, index, VRF_DEFAULT, 
table,
+                      metric, 0, SAFI_UNICAST);
       else
-        rib_delete_ipv6 (ZEBRA_ROUTE_KERNEL, 0, &p, gate, index, table, 
SAFI_UNICAST);
+        rib_delete_ipv6 (ZEBRA_ROUTE_KERNEL, 0, &p, gate, index, VRF_DEFAULT,
+                         SAFI_UNICAST);
     }
 #endif /* HAVE_IPV6 */
 
diff --git a/zebra/rtread_getmsg.c b/zebra/rtread_getmsg.c
index 81bf0de6478a..83ef64832388 100644
--- a/zebra/rtread_getmsg.c
+++ b/zebra/rtread_getmsg.c
@@ -25,6 +25,7 @@
 #include "prefix.h"
 #include "log.h"
 #include "if.h"
+#include "vrf.h"
 
 #include "zebra/rib.h"
 #include "zebra/zserv.h"
@@ -90,7 +91,8 @@ handle_route_entry (mib2_ipRouteEntry_t *routeEntry)
        gateway.s_addr = routeEntry->ipRouteNextHop;
 
        rib_add_ipv4 (ZEBRA_ROUTE_KERNEL, zebra_flags, &prefix,
-                     &gateway, NULL, 0, 0, 0, 0, SAFI_UNICAST);
+                     &gateway, NULL, 0, VRF_DEFAULT, RT_TABLE_MAIN,
+                     0, 0, SAFI_UNICAST);
 }
 
 void
diff --git a/zebra/zebra_rib.c b/zebra/zebra_rib.c
index 39baf268ccfb..b7b4c4f00485 100644
--- a/zebra/zebra_rib.c
+++ b/zebra/zebra_rib.c
@@ -93,8 +93,9 @@ _rnode_zlog(const char *_func, struct route_node *rn, int 
priority,
 
       inet_ntop (rn->p.family, &rn->p.u.prefix, buf, INET6_ADDRSTRLEN);
       bptr = buf + strlen(buf);
-      snprintf(bptr, buf + sizeof(buf) - bptr, "/%d%s", rn->p.prefixlen,
-               info->safi == SAFI_MULTICAST ? " (MRIB)" : "");
+      snprintf(bptr, buf + sizeof(buf) - bptr, "/%d%s vrf %u", rn->p.prefixlen,
+               info->safi == SAFI_MULTICAST ? " (MRIB)" : "",
+               info->zvrf->vrf_id);
     }
   else
     {
@@ -369,7 +370,7 @@ nexthop_active_ipv4 (struct rib *rib, struct nexthop 
*nexthop, int set,
   p.prefix = nexthop->gate.ipv4;
 
   /* Lookup table.  */
-  table = zebra_vrf_table (AFI_IP, SAFI_UNICAST, VRF_DEFAULT);
+  table = zebra_vrf_table (AFI_IP, SAFI_UNICAST, rib->vrf_id);
   if (! table)
     return 0;
 
@@ -511,7 +512,7 @@ nexthop_active_ipv6 (struct rib *rib, struct nexthop 
*nexthop, int set,
   p.prefix = nexthop->gate.ipv6;
 
   /* Lookup table.  */
-  table = zebra_vrf_table (AFI_IP6, SAFI_UNICAST, VRF_DEFAULT);
+  table = zebra_vrf_table (AFI_IP6, SAFI_UNICAST, rib->vrf_id);
   if (! table)
     return 0;
 
@@ -618,7 +619,7 @@ nexthop_active_ipv6 (struct rib *rib, struct nexthop 
*nexthop, int set,
 
 struct rib *
 rib_match_ipv4_safi (struct in_addr addr, safi_t safi, int skip_bgp,
-                    struct route_node **rn_out)
+                    struct route_node **rn_out, vrf_id_t vrf_id)
 {
   struct route_table *table;
   struct route_node *rn;
@@ -627,7 +628,7 @@ rib_match_ipv4_safi (struct in_addr addr, safi_t safi, int 
skip_bgp,
   int recursing;
 
   /* Lookup table.  */
-  table = zebra_vrf_table (AFI_IP, safi, VRF_DEFAULT);
+  table = zebra_vrf_table (AFI_IP, safi, vrf_id);
   if (! table)
     return 0;
 
@@ -680,7 +681,8 @@ rib_match_ipv4_safi (struct in_addr addr, safi_t safi, int 
skip_bgp,
 }
 
 struct rib *
-rib_match_ipv4_multicast (struct in_addr addr, struct route_node **rn_out)
+rib_match_ipv4_multicast (struct in_addr addr, struct route_node **rn_out,
+    vrf_id_t vrf_id)
 {
   struct rib *rib = NULL, *mrib = NULL, *urib = NULL;
   struct route_node *m_rn = NULL, *u_rn = NULL;
@@ -689,18 +691,24 @@ rib_match_ipv4_multicast (struct in_addr addr, struct 
route_node **rn_out)
   switch (ipv4_multicast_mode)
     {
     case MCAST_MRIB_ONLY:
-      return rib_match_ipv4_safi (addr, SAFI_MULTICAST, skip_bgp, rn_out);
+      return rib_match_ipv4_safi (addr, SAFI_MULTICAST, skip_bgp, rn_out,
+                                  vrf_id);
     case MCAST_URIB_ONLY:
-      return rib_match_ipv4_safi (addr, SAFI_UNICAST, skip_bgp, rn_out);
+      return rib_match_ipv4_safi (addr, SAFI_UNICAST, skip_bgp, rn_out,
+                                  vrf_id);
     case MCAST_NO_CONFIG:
     case MCAST_MIX_MRIB_FIRST:
-      rib = mrib = rib_match_ipv4_safi (addr, SAFI_MULTICAST, skip_bgp, &m_rn);
+      rib = mrib = rib_match_ipv4_safi (addr, SAFI_MULTICAST, skip_bgp, &m_rn,
+                                        vrf_id);
       if (!mrib)
-       rib = urib = rib_match_ipv4_safi (addr, SAFI_UNICAST, skip_bgp, &u_rn);
+        rib = urib = rib_match_ipv4_safi (addr, SAFI_UNICAST, skip_bgp, &u_rn,
+                                          vrf_id);
       break;
     case MCAST_MIX_DISTANCE:
-      mrib = rib_match_ipv4_safi (addr, SAFI_MULTICAST, skip_bgp, &m_rn);
-      urib = rib_match_ipv4_safi (addr, SAFI_UNICAST, skip_bgp, &u_rn);
+      mrib = rib_match_ipv4_safi (addr, SAFI_MULTICAST, skip_bgp, &m_rn,
+                                  vrf_id);
+      urib = rib_match_ipv4_safi (addr, SAFI_UNICAST, skip_bgp, &u_rn,
+                                  vrf_id);
       if (mrib && urib)
        rib = urib->distance < mrib->distance ? urib : mrib;
       else if (mrib)
@@ -709,8 +717,10 @@ rib_match_ipv4_multicast (struct in_addr addr, struct 
route_node **rn_out)
        rib = urib;
       break;
     case MCAST_MIX_PFXLEN:
-      mrib = rib_match_ipv4_safi (addr, SAFI_MULTICAST, skip_bgp, &m_rn);
-      urib = rib_match_ipv4_safi (addr, SAFI_UNICAST, skip_bgp, &u_rn);
+      mrib = rib_match_ipv4_safi (addr, SAFI_MULTICAST, skip_bgp, &m_rn,
+                                  vrf_id);
+      urib = rib_match_ipv4_safi (addr, SAFI_UNICAST, skip_bgp, &u_rn,
+                                  vrf_id);
       if (mrib && urib)
        rib = u_rn->p.prefixlen > m_rn->p.prefixlen ? urib : mrib;
       else if (mrib)
@@ -728,8 +738,8 @@ rib_match_ipv4_multicast (struct in_addr addr, struct 
route_node **rn_out)
       char buf[BUFSIZ];
       inet_ntop (AF_INET, &addr, buf, BUFSIZ);
 
-      zlog_debug("%s: %s: found %s, using %s",
-                __func__, buf,
+      zlog_debug("%s: %s vrf %u: found %s, using %s",
+                __func__, buf, vrf_id,
                  mrib ? (urib ? "MRIB+URIB" : "MRIB") :
                          urib ? "URIB" : "nothing",
                 rib == urib ? "URIB" : rib == mrib ? "MRIB" : "none");
@@ -752,7 +762,7 @@ multicast_mode_ipv4_get (void)
 }
 
 struct rib *
-rib_lookup_ipv4 (struct prefix_ipv4 *p)
+rib_lookup_ipv4 (struct prefix_ipv4 *p, vrf_id_t vrf_id)
 {
   struct route_table *table;
   struct route_node *rn;
@@ -761,7 +771,7 @@ rib_lookup_ipv4 (struct prefix_ipv4 *p)
   int recursing;
 
   /* Lookup table.  */
-  table = zebra_vrf_table (AFI_IP, SAFI_UNICAST, VRF_DEFAULT);
+  table = zebra_vrf_table (AFI_IP, SAFI_UNICAST, vrf_id);
   if (! table)
     return 0;
 
@@ -808,7 +818,8 @@ rib_lookup_ipv4 (struct prefix_ipv4 *p)
  * 3: no matches found
  */
 int
-rib_lookup_ipv4_route (struct prefix_ipv4 *p, union sockunion * qgate)
+rib_lookup_ipv4_route (struct prefix_ipv4 *p, union sockunion * qgate,
+    vrf_id_t vrf_id)
 {
   struct route_table *table;
   struct route_node *rn;
@@ -818,7 +829,7 @@ rib_lookup_ipv4_route (struct prefix_ipv4 *p, union 
sockunion * qgate)
   int nexthops_active;
 
   /* Lookup table.  */
-  table = zebra_vrf_table (AFI_IP, SAFI_UNICAST, VRF_DEFAULT);
+  table = zebra_vrf_table (AFI_IP, SAFI_UNICAST, vrf_id);
   if (! table)
     return ZEBRA_RIB_LOOKUP_ERROR;
 
@@ -874,7 +885,7 @@ rib_lookup_ipv4_route (struct prefix_ipv4 *p, union 
sockunion * qgate)
 
 #ifdef HAVE_IPV6
 struct rib *
-rib_match_ipv6 (struct in6_addr *addr)
+rib_match_ipv6 (struct in6_addr *addr, vrf_id_t vrf_id)
 {
   struct prefix_ipv6 p;
   struct route_table *table;
@@ -884,7 +895,7 @@ rib_match_ipv6 (struct in6_addr *addr)
   int recursing;
 
   /* Lookup table.  */
-  table = zebra_vrf_table (AFI_IP6, SAFI_UNICAST, VRF_DEFAULT);
+  table = zebra_vrf_table (AFI_IP6, SAFI_UNICAST, vrf_id);
   if (! table)
     return 0;
 
@@ -965,7 +976,7 @@ nexthop_active_check (struct route_node *rn, struct rib 
*rib,
   switch (nexthop->type)
     {
     case NEXTHOP_TYPE_IFINDEX:
-      ifp = if_lookup_by_index (nexthop->ifindex);
+      ifp = if_lookup_by_index_vrf (nexthop->ifindex, rib->vrf_id);
       if (ifp && if_is_operative(ifp))
        SET_FLAG (nexthop->flags, NEXTHOP_FLAG_ACTIVE);
       else
@@ -974,7 +985,7 @@ nexthop_active_check (struct route_node *rn, struct rib 
*rib,
     case NEXTHOP_TYPE_IPV6_IFNAME:
       family = AFI_IP6;
     case NEXTHOP_TYPE_IFNAME:
-      ifp = if_lookup_by_name (nexthop->ifname);
+      ifp = if_lookup_by_name_vrf (nexthop->ifname, rib->vrf_id);
       if (ifp && if_is_operative(ifp))
        {
          if (set)
@@ -1008,7 +1019,7 @@ nexthop_active_check (struct route_node *rn, struct rib 
*rib,
       family = AFI_IP6;
       if (IN6_IS_ADDR_LINKLOCAL (&nexthop->gate.ipv6))
        {
-         ifp = if_lookup_by_index (nexthop->ifindex);
+         ifp = if_lookup_by_index_vrf (nexthop->ifindex, rib->vrf_id);
          if (ifp && if_is_operative(ifp))
            SET_FLAG (nexthop->flags, NEXTHOP_FLAG_ACTIVE);
          else
@@ -1792,7 +1803,7 @@ rib_delnode (struct route_node *rn, struct rib *rib)
 int
 rib_add_ipv4 (int type, int flags, struct prefix_ipv4 *p, 
              struct in_addr *gate, struct in_addr *src,
-             unsigned int ifindex, u_int32_t vrf_id,
+             unsigned int ifindex, vrf_id_t vrf_id, int table_id,
              u_int32_t metric, u_char distance, safi_t safi)
 {
   struct rib *rib;
@@ -1802,7 +1813,7 @@ rib_add_ipv4 (int type, int flags, struct prefix_ipv4 *p,
   struct nexthop *nexthop;
 
   /* Lookup table.  */
-  table = zebra_vrf_table (AFI_IP, safi, VRF_DEFAULT);
+  table = zebra_vrf_table (AFI_IP, safi, vrf_id);
   if (! table)
     return 0;
 
@@ -1856,7 +1867,8 @@ rib_add_ipv4 (int type, int flags, struct prefix_ipv4 *p,
   rib->distance = distance;
   rib->flags = flags;
   rib->metric = metric;
-  rib->table = vrf_id;
+  rib->vrf_id = vrf_id;
+  rib->table = table_id;
   rib->nexthop_num = 0;
   rib->uptime = time (NULL);
 
@@ -1909,8 +1921,8 @@ void _rib_dump (const char * func,
   int recursing;
 
   inet_ntop (p->family, &p->u.prefix, straddr, INET6_ADDRSTRLEN);
-  zlog_debug ("%s: dumping RIB entry %p for %s/%d", func, (void *)rib,
-              straddr, p->prefixlen);
+  zlog_debug ("%s: dumping RIB entry %p for %s/%d vrf %u", func, (void *)rib,
+              straddr, p->prefixlen, rib->vrf_id);
   zlog_debug
   (
     "%s: refcnt == %lu, uptime == %lu, type == %u, table == %d",
@@ -2065,7 +2077,7 @@ rib_add_ipv4_multipath (struct prefix_ipv4 *p, struct rib 
*rib, safi_t safi)
   struct nexthop *nexthop;
   
   /* Lookup table.  */
-  table = zebra_vrf_table (AFI_IP, safi, VRF_DEFAULT);
+  table = zebra_vrf_table (AFI_IP, safi, rib->vrf_id);
   if (! table)
     return 0;
 
@@ -2131,7 +2143,7 @@ rib_add_ipv4_multipath (struct prefix_ipv4 *p, struct rib 
*rib, safi_t safi)
 /* XXX factor with rib_delete_ipv6 */
 int
 rib_delete_ipv4 (int type, int flags, struct prefix_ipv4 *p,
-                struct in_addr *gate, unsigned int ifindex, u_int32_t vrf_id, 
safi_t safi)
+                struct in_addr *gate, unsigned int ifindex, vrf_id_t vrf_id, 
safi_t safi)
 {
   struct route_table *table;
   struct route_node *rn;
@@ -2144,7 +2156,7 @@ rib_delete_ipv4 (int type, int flags, struct prefix_ipv4 
*p,
   char buf2[INET_ADDRSTRLEN];
 
   /* Lookup table.  */
-  table = zebra_vrf_table (AFI_IP, safi, VRF_DEFAULT);
+  table = zebra_vrf_table (AFI_IP, safi, vrf_id);
   if (! table)
     return 0;
 
@@ -2154,15 +2166,15 @@ rib_delete_ipv4 (int type, int flags, struct 
prefix_ipv4 *p,
   if (IS_ZEBRA_DEBUG_KERNEL)
     {
       if (gate)
-       zlog_debug ("rib_delete_ipv4(): route delete %s/%d via %s ifindex %d",
+       zlog_debug ("rib_delete_ipv4(): route delete %s/%d vrf %u via %s 
ifindex %d",
                    inet_ntop (AF_INET, &p->prefix, buf1, INET_ADDRSTRLEN),
-                   p->prefixlen,
+                   p->prefixlen, vrf_id,
                    inet_ntoa (*gate),
                    ifindex);
       else
-       zlog_debug ("rib_delete_ipv4(): route delete %s/%d ifindex %d",
+       zlog_debug ("rib_delete_ipv4(): route delete %s/%d vrf %u ifindex %d",
                    inet_ntop (AF_INET, &p->prefix, buf1, INET_ADDRSTRLEN),
-                   p->prefixlen,
+                   p->prefixlen, vrf_id,
                    ifindex);
     }
 
@@ -2173,15 +2185,15 @@ rib_delete_ipv4 (int type, int flags, struct 
prefix_ipv4 *p,
       if (IS_ZEBRA_DEBUG_KERNEL)
        {
          if (gate)
-           zlog_debug ("route %s/%d via %s ifindex %d doesn't exist in rib",
+           zlog_debug ("route %s/%d vrf %u via %s ifindex %d doesn't exist in 
rib",
                       inet_ntop (AF_INET, &p->prefix, buf1, INET_ADDRSTRLEN),
-                      p->prefixlen,
+                      p->prefixlen, vrf_id,
                       inet_ntop (AF_INET, gate, buf2, INET_ADDRSTRLEN),
                       ifindex);
          else
-           zlog_debug ("route %s/%d ifindex %d doesn't exist in rib",
+           zlog_debug ("route %s/%d vrf %u ifindex %d doesn't exist in rib",
                       inet_ntop (AF_INET, &p->prefix, buf1, INET_ADDRSTRLEN),
-                      p->prefixlen,
+                      p->prefixlen, vrf_id,
                       ifindex);
        }
       return ZEBRA_ERR_RTNOEXIST;
@@ -2248,16 +2260,17 @@ rib_delete_ipv4 (int type, int flags, struct 
prefix_ipv4 *p,
          if (IS_ZEBRA_DEBUG_KERNEL)
            {
              if (gate)
-               zlog_debug ("route %s/%d via %s ifindex %d type %d doesn't 
exist in rib",
+               zlog_debug ("route %s/%d vrf %u via %s ifindex %d type %d "
+                          "doesn't exist in rib",
                           inet_ntop (AF_INET, &p->prefix, buf1, 
INET_ADDRSTRLEN),
-                          p->prefixlen,
+                          p->prefixlen, vrf_id,
                           inet_ntop (AF_INET, gate, buf2, INET_ADDRSTRLEN),
                           ifindex,
                           type);
              else
-               zlog_debug ("route %s/%d ifindex %d type %d doesn't exist in 
rib",
+               zlog_debug ("route %s/%d vrf %u ifindex %d type %d doesn't 
exist in rib",
                           inet_ntop (AF_INET, &p->prefix, buf1, 
INET_ADDRSTRLEN),
-                          p->prefixlen,
+                          p->prefixlen, vrf_id,
                           ifindex,
                           type);
            }
@@ -2324,6 +2337,7 @@ static_install_ipv4 (safi_t safi, struct prefix *p, 
struct static_ipv4 *si)
       rib->type = ZEBRA_ROUTE_STATIC;
       rib->distance = si->distance;
       rib->metric = 0;
+      rib->vrf_id = VRF_DEFAULT;
       rib->table = zebrad.rtm_table_default;
       rib->nexthop_num = 0;
 
@@ -2429,7 +2443,7 @@ static_uninstall_ipv4 (safi_t safi, struct prefix *p, 
struct static_ipv4 *si)
 int
 static_add_ipv4_safi (safi_t safi, struct prefix *p, struct in_addr *gate,
                      const char *ifname, u_char flags, u_char distance,
-                     u_int32_t vrf_id)
+                     vrf_id_t vrf_id)
 {
   u_char type = 0;
   struct route_node *rn;
@@ -2437,10 +2451,9 @@ static_add_ipv4_safi (safi_t safi, struct prefix *p, 
struct in_addr *gate,
   struct static_ipv4 *pp;
   struct static_ipv4 *cp;
   struct static_ipv4 *update = NULL;
-  struct route_table *stable;
+  struct zebra_vrf *zvrf = vrf_info_get (vrf_id);
+  struct route_table *stable = zvrf->stable[AFI_IP][safi];
 
-  /* Lookup table.  */
-  stable = zebra_vrf_static_table (AFI_IP, safi, vrf_id);
   if (! stable)
     return -1;
   
@@ -2523,7 +2536,7 @@ static_add_ipv4_safi (safi_t safi, struct prefix *p, 
struct in_addr *gate,
 
 int
 static_delete_ipv4_safi (safi_t safi, struct prefix *p, struct in_addr *gate,
-                        const char *ifname, u_char distance, u_int32_t vrf_id)
+                        const char *ifname, u_char distance, vrf_id_t vrf_id)
 {
   u_char type = 0;
   struct route_node *rn;
@@ -2587,7 +2600,8 @@ static_delete_ipv4_safi (safi_t safi, struct prefix *p, 
struct in_addr *gate,
 #ifdef HAVE_IPV6
 int
 rib_add_ipv6 (int type, int flags, struct prefix_ipv6 *p,
-             struct in6_addr *gate, unsigned int ifindex, u_int32_t vrf_id,
+             struct in6_addr *gate, unsigned int ifindex,
+             vrf_id_t vrf_id, int table_id,
              u_int32_t metric, u_char distance, safi_t safi)
 {
   struct rib *rib;
@@ -2597,7 +2611,7 @@ rib_add_ipv6 (int type, int flags, struct prefix_ipv6 *p,
   struct nexthop *nexthop;
 
   /* Lookup table.  */
-  table = zebra_vrf_table (AFI_IP6, safi, VRF_DEFAULT);
+  table = zebra_vrf_table (AFI_IP6, safi, vrf_id);
   if (! table)
     return 0;
 
@@ -2644,7 +2658,8 @@ rib_add_ipv6 (int type, int flags, struct prefix_ipv6 *p,
   rib->distance = distance;
   rib->flags = flags;
   rib->metric = metric;
-  rib->table = vrf_id;
+  rib->vrf_id = vrf_id;
+  rib->table = table_id;
   rib->nexthop_num = 0;
   rib->uptime = time (NULL);
 
@@ -2692,7 +2707,7 @@ rib_add_ipv6 (int type, int flags, struct prefix_ipv6 *p,
 /* XXX factor with rib_delete_ipv6 */
 int
 rib_delete_ipv6 (int type, int flags, struct prefix_ipv6 *p,
-                struct in6_addr *gate, unsigned int ifindex, u_int32_t vrf_id, 
safi_t safi)
+                struct in6_addr *gate, unsigned int ifindex, vrf_id_t vrf_id, 
safi_t safi)
 {
   struct route_table *table;
   struct route_node *rn;
@@ -2708,7 +2723,7 @@ rib_delete_ipv6 (int type, int flags, struct prefix_ipv6 
*p,
   apply_mask_ipv6 (p);
 
   /* Lookup table.  */
-  table = zebra_vrf_table (AFI_IP6, safi, VRF_DEFAULT);
+  table = zebra_vrf_table (AFI_IP6, safi, vrf_id);
   if (! table)
     return 0;
   
@@ -2719,15 +2734,15 @@ rib_delete_ipv6 (int type, int flags, struct 
prefix_ipv6 *p,
       if (IS_ZEBRA_DEBUG_KERNEL)
        {
          if (gate)
-           zlog_debug ("route %s/%d via %s ifindex %d doesn't exist in rib",
+           zlog_debug ("route %s/%d vrf %u via %s ifindex %d doesn't exist in 
rib",
                       inet_ntop (AF_INET6, &p->prefix, buf1, INET6_ADDRSTRLEN),
-                      p->prefixlen,
+                      p->prefixlen, vrf_id,
                       inet_ntop (AF_INET6, gate, buf2, INET6_ADDRSTRLEN),
                       ifindex);
          else
-           zlog_debug ("route %s/%d ifindex %d doesn't exist in rib",
+           zlog_debug ("route %s/%d vrf %u ifindex %d doesn't exist in rib",
                       inet_ntop (AF_INET6, &p->prefix, buf1, INET6_ADDRSTRLEN),
-                      p->prefixlen,
+                      p->prefixlen, vrf_id,
                       ifindex);
        }
       return ZEBRA_ERR_RTNOEXIST;
@@ -2795,16 +2810,17 @@ rib_delete_ipv6 (int type, int flags, struct 
prefix_ipv6 *p,
          if (IS_ZEBRA_DEBUG_KERNEL)
            {
              if (gate)
-               zlog_debug ("route %s/%d via %s ifindex %d type %d doesn't 
exist in rib",
+               zlog_debug ("route %s/%d vrf %u via %s ifindex %d type %d "
+                          "doesn't exist in rib",
                           inet_ntop (AF_INET6, &p->prefix, buf1, 
INET6_ADDRSTRLEN),
-                          p->prefixlen,
+                          p->prefixlen, vrf_id,
                           inet_ntop (AF_INET6, gate, buf2, INET6_ADDRSTRLEN),
                           ifindex,
                           type);
              else
-               zlog_debug ("route %s/%d ifindex %d type %d doesn't exist in 
rib",
+               zlog_debug ("route %s/%d vrf %u ifindex %d type %d doesn't 
exist in rib",
                           inet_ntop (AF_INET6, &p->prefix, buf1, 
INET6_ADDRSTRLEN),
-                          p->prefixlen,
+                          p->prefixlen, vrf_id,
                           ifindex,
                           type);
            }
@@ -2872,6 +2888,7 @@ static_install_ipv6 (struct prefix *p, struct static_ipv6 
*si)
       rib->type = ZEBRA_ROUTE_STATIC;
       rib->distance = si->distance;
       rib->metric = 0;
+      rib->vrf_id = VRF_DEFAULT;
       rib->table = zebrad.rtm_table_default;
       rib->nexthop_num = 0;
 
@@ -2981,16 +2998,15 @@ static_uninstall_ipv6 (struct prefix *p, struct 
static_ipv6 *si)
 int
 static_add_ipv6 (struct prefix *p, u_char type, struct in6_addr *gate,
                 const char *ifname, u_char flags, u_char distance,
-                u_int32_t vrf_id)
+                vrf_id_t vrf_id)
 {
   struct route_node *rn;
   struct static_ipv6 *si;
   struct static_ipv6 *pp;
   struct static_ipv6 *cp;
-  struct route_table *stable;
+  struct zebra_vrf *zvrf = vrf_info_get (vrf_id);
+  struct route_table *stable = zvrf->stable[AFI_IP6][SAFI_UNICAST];
 
-  /* Lookup table.  */
-  stable = zebra_vrf_static_table (AFI_IP6, SAFI_UNICAST, vrf_id);
   if (! stable)
     return -1;
     
@@ -3068,7 +3084,7 @@ static_add_ipv6 (struct prefix *p, u_char type, struct 
in6_addr *gate,
 /* Delete static route from static route configuration. */
 int
 static_delete_ipv6 (struct prefix *p, u_char type, struct in6_addr *gate,
-                   const char *ifname, u_char distance, u_int32_t vrf_id)
+                   const char *ifname, u_char distance, vrf_id_t vrf_id)
 {
   struct route_node *rn;
   struct static_ipv6 *si;
@@ -3121,18 +3137,18 @@ static_delete_ipv6 (struct prefix *p, u_char type, 
struct in6_addr *gate,
 
 /* RIB update function. */
 void
-rib_update (void)
+rib_update (vrf_id_t vrf_id)
 {
   struct route_node *rn;
   struct route_table *table;
   
-  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))
       if (rnode_to_ribs (rn))
         rib_queue_add (&zebrad, rn);
 
-  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))
       if (rnode_to_ribs (rn))
@@ -3165,8 +3181,15 @@ rib_weed_table (struct route_table *table)
 void
 rib_weed_tables (void)
 {
-  rib_weed_table (zebra_vrf_table (AFI_IP, SAFI_UNICAST, VRF_DEFAULT));
-  rib_weed_table (zebra_vrf_table (AFI_IP6, SAFI_UNICAST, VRF_DEFAULT));
+  vrf_iter_t iter;
+  struct zebra_vrf *zvrf;
+
+  for (iter = vrf_first (); iter != VRF_ITER_INVALID; iter = vrf_next (iter))
+    if ((zvrf = vrf_iter2info (iter)) != NULL)
+      {
+        rib_weed_table (zvrf->table[AFI_IP][SAFI_UNICAST]);
+        rib_weed_table (zvrf->table[AFI_IP6][SAFI_UNICAST]);
+      }
 }
 
 /* Delete self installed routes after zebra is relaunched.  */
@@ -3199,8 +3222,15 @@ rib_sweep_table (struct route_table *table)
 void
 rib_sweep_route (void)
 {
-  rib_sweep_table (zebra_vrf_table (AFI_IP, SAFI_UNICAST, VRF_DEFAULT));
-  rib_sweep_table (zebra_vrf_table (AFI_IP6, SAFI_UNICAST, VRF_DEFAULT));
+  vrf_iter_t iter;
+  struct zebra_vrf *zvrf;
+
+  for (iter = vrf_first (); iter != VRF_ITER_INVALID; iter = vrf_next (iter))
+    if ((zvrf = vrf_iter2info (iter)) != NULL)
+      {
+        rib_weed_table (zvrf->table[AFI_IP][SAFI_UNICAST]);
+        rib_weed_table (zvrf->table[AFI_IP6][SAFI_UNICAST]);
+      }
 }
 
 /* Remove specific by protocol routes from 'table'. */
@@ -3232,8 +3262,16 @@ rib_score_proto_table (u_char proto, struct route_table 
*table)
 unsigned long
 rib_score_proto (u_char proto)
 {
-  return  rib_score_proto_table (proto, zebra_vrf_table (AFI_IP,  
SAFI_UNICAST, VRF_DEFAULT))
-         +rib_score_proto_table (proto, zebra_vrf_table (AFI_IP6, 
SAFI_UNICAST, VRF_DEFAULT));
+  vrf_iter_t iter;
+  struct zebra_vrf *zvrf;
+  unsigned long cnt = 0;
+
+  for (iter = vrf_first (); iter != VRF_ITER_INVALID; iter = vrf_next (iter))
+    if ((zvrf = vrf_iter2info (iter)) != NULL)
+      cnt += rib_score_proto_table (proto, zvrf->table[AFI_IP][SAFI_UNICAST])
+            +rib_score_proto_table (proto, zvrf->table[AFI_IP6][SAFI_UNICAST]);
+
+  return cnt;
 }
 
 /* Close RIB and clean up kernel routes. */
@@ -3263,8 +3301,15 @@ rib_close_table (struct route_table *table)
 void
 rib_close (void)
 {
-  rib_close_table (zebra_vrf_table (AFI_IP, SAFI_UNICAST, VRF_DEFAULT));
-  rib_close_table (zebra_vrf_table (AFI_IP6, SAFI_UNICAST, VRF_DEFAULT));
+  vrf_iter_t iter;
+  struct zebra_vrf *zvrf;
+
+  for (iter = vrf_first (); iter != VRF_ITER_INVALID; iter = vrf_next (iter))
+    if ((zvrf = vrf_iter2info (iter)) != NULL)
+      {
+        rib_close_table (zvrf->table[AFI_IP][SAFI_UNICAST]);
+        rib_close_table (zvrf->table[AFI_IP6][SAFI_UNICAST]);
+      }
 }
 
 /* Routing information base initialize. */
diff --git a/zebra/zebra_vty.c b/zebra/zebra_vty.c
index 331dba69b083..fff76c19678b 100644
--- a/zebra/zebra_vty.c
+++ b/zebra/zebra_vty.c
@@ -285,7 +285,7 @@ DEFUN (show_ip_rpf_addr,
       return CMD_WARNING;
     }
 
-  rib = rib_match_ipv4_multicast (addr, &rn);
+  rib = rib_match_ipv4_multicast (addr, &rn, VRF_DEFAULT);
 
   if (rib)
     vty_show_ip_route_detail (vty, rn, 1);
@@ -769,11 +769,12 @@ vty_show_ip_route_detail (struct vty *vty, struct 
route_node *rn, int mcast)
            case NEXTHOP_TYPE_IPV4_IFINDEX:
              vty_out (vty, " %s", inet_ntoa (nexthop->gate.ipv4));
              if (nexthop->ifindex)
-               vty_out (vty, ", via %s", ifindex2ifname (nexthop->ifindex));
+               vty_out (vty, ", via %s",
+                        ifindex2ifname_vrf (nexthop->ifindex, rib->vrf_id));
              break;
            case NEXTHOP_TYPE_IFINDEX:
              vty_out (vty, " directly connected, %s",
-                      ifindex2ifname (nexthop->ifindex));
+                      ifindex2ifname_vrf (nexthop->ifindex, rib->vrf_id));
              break;
            case NEXTHOP_TYPE_IFNAME:
              vty_out (vty, " directly connected, %s", nexthop->ifname);
@@ -867,11 +868,11 @@ vty_show_ip_route (struct vty *vty, struct route_node 
*rn, struct rib *rib)
        case NEXTHOP_TYPE_IPV4_IFINDEX:
          vty_out (vty, " via %s", inet_ntoa (nexthop->gate.ipv4));
          if (nexthop->ifindex)
-           vty_out (vty, ", %s", ifindex2ifname (nexthop->ifindex));
+           vty_out (vty, ", %s", ifindex2ifname_vrf (nexthop->ifindex, 
rib->vrf_id));
          break;
        case NEXTHOP_TYPE_IFINDEX:
          vty_out (vty, " is directly connected, %s",
-                  ifindex2ifname (nexthop->ifindex));
+                  ifindex2ifname_vrf (nexthop->ifindex, rib->vrf_id));
          break;
        case NEXTHOP_TYPE_IFNAME:
          vty_out (vty, " is directly connected, %s", nexthop->ifname);
@@ -1865,11 +1866,12 @@ vty_show_ipv6_route_detail (struct vty *vty, struct 
route_node *rn)
              if (nexthop->type == NEXTHOP_TYPE_IPV6_IFNAME)
                vty_out (vty, ", %s", nexthop->ifname);
              else if (nexthop->ifindex)
-               vty_out (vty, ", via %s", ifindex2ifname (nexthop->ifindex));
+               vty_out (vty, ", via %s",
+                        ifindex2ifname_vrf (nexthop->ifindex, rib->vrf_id));
              break;
            case NEXTHOP_TYPE_IFINDEX:
              vty_out (vty, " directly connected, %s",
-                      ifindex2ifname (nexthop->ifindex));
+                      ifindex2ifname_vrf (nexthop->ifindex, rib->vrf_id));
              break;
            case NEXTHOP_TYPE_IFNAME:
              vty_out (vty, " directly connected, %s",
@@ -1939,11 +1941,11 @@ vty_show_ipv6_route (struct vty *vty, struct route_node 
*rn,
          if (nexthop->type == NEXTHOP_TYPE_IPV6_IFNAME)
            vty_out (vty, ", %s", nexthop->ifname);
          else if (nexthop->ifindex)
-           vty_out (vty, ", %s", ifindex2ifname (nexthop->ifindex));
+           vty_out (vty, ", %s", ifindex2ifname_vrf (nexthop->ifindex, 
rib->vrf_id));
          break;
        case NEXTHOP_TYPE_IFINDEX:
          vty_out (vty, " is directly connected, %s",
-                  ifindex2ifname (nexthop->ifindex));
+                  ifindex2ifname_vrf (nexthop->ifindex, rib->vrf_id));
          break;
        case NEXTHOP_TYPE_IFNAME:
          vty_out (vty, " is directly connected, %s",
diff --git a/zebra/zserv.c b/zebra/zserv.c
index 432c3182422c..85f448c420f0 100644
--- a/zebra/zserv.c
+++ b/zebra/zserv.c
@@ -36,6 +36,7 @@
 #include "privs.h"
 #include "network.h"
 #include "buffer.h"
+#include "vrf.h"
 
 #include "zebra/zserv.h"
 #include "zebra/router-id.h"
@@ -473,7 +474,7 @@ zsend_ipv6_nexthop_lookup (struct zserv *client, struct 
in6_addr *addr)
   struct nexthop *nexthop;
 
   /* Lookup nexthop. */
-  rib = rib_match_ipv6 (addr);
+  rib = rib_match_ipv6 (addr, VRF_DEFAULT);
 
   /* Get output stream. */
   s = client->obuf;
@@ -540,7 +541,7 @@ 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);
+  rib = rib_match_ipv4_safi (addr, SAFI_UNICAST, 1, NULL, VRF_DEFAULT);
 
   /* Get output stream. */
   s = client->obuf;
@@ -679,7 +680,7 @@ zsend_ipv4_import_lookup (struct zserv *client, struct 
prefix_ipv4 *p)
   struct nexthop *nexthop;
 
   /* Lookup nexthop. */
-  rib = rib_lookup_ipv4 (p);
+  rib = rib_lookup_ipv4 (p, VRF_DEFAULT);
 
   /* Get output stream. */
   s = client->obuf;
@@ -842,6 +843,9 @@ zread_ipv4_add (struct zserv *client, u_short length)
   p.prefixlen = stream_getc (s);
   stream_get (&p.prefix, s, PSIZE (p.prefixlen));
 
+  /* VRF ID */
+  rib->vrf_id = VRF_DEFAULT;
+
   /* Nexthop parse. */
   if (CHECK_FLAG (message, ZAPI_MESSAGE_NEXTHOP))
     {
@@ -972,7 +976,7 @@ zread_ipv4_delete (struct zserv *client, u_short length)
     api.metric = 0;
     
   rib_delete_ipv4 (api.type, api.flags, &p, nexthop_p, ifindex,
-                  client->rtm_table, api.safi);
+                   VRF_DEFAULT, api.safi);
   return 0;
 }
 
@@ -998,7 +1002,7 @@ zread_ipv4_nexthop_lookup_mrib (struct zserv *client, 
u_short length)
   struct rib *rib;
 
   addr.s_addr = stream_get_ipv4 (client->ibuf);
-  rib = rib_match_ipv4_multicast (addr, NULL);
+  rib = rib_match_ipv4_multicast (addr, NULL, VRF_DEFAULT);
   return zsend_ipv4_nexthop_lookup_mrib (client, addr, rib);
 }
 
@@ -1076,11 +1080,13 @@ zread_ipv6_add (struct zserv *client, u_short length)
     api.metric = 0;
     
   if (IN6_IS_ADDR_UNSPECIFIED (&nexthop))
-    rib_add_ipv6 (api.type, api.flags, &p, NULL, ifindex, 
zebrad.rtm_table_default, api.metric,
-                 api.distance, api.safi);
+    rib_add_ipv6 (api.type, api.flags, &p, NULL, ifindex,
+                  VRF_DEFAULT, zebrad.rtm_table_default, api.metric,
+                  api.distance, api.safi);
   else
-    rib_add_ipv6 (api.type, api.flags, &p, &nexthop, ifindex, 
zebrad.rtm_table_default, api.metric,
-                 api.distance, api.safi);
+    rib_add_ipv6 (api.type, api.flags, &p, &nexthop, ifindex,
+                  VRF_DEFAULT, zebrad.rtm_table_default, api.metric,
+                  api.distance, api.safi);
   return 0;
 }
 
@@ -1143,9 +1149,11 @@ 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, 
client->rtm_table, api.safi);
+    rib_delete_ipv6 (api.type, api.flags, &p, NULL, ifindex, VRF_DEFAULT,
+                     api.safi);
   else
-    rib_delete_ipv6 (api.type, api.flags, &p, &nexthop, ifindex, 
client->rtm_table, api.safi);
+    rib_delete_ipv6 (api.type, api.flags, &p, &nexthop, ifindex, VRF_DEFAULT,
+                     api.safi);
   return 0;
 }
 
-- 
2.2.2


_______________________________________________
Quagga-dev mailing list
Quagga-dev@lists.quagga.net
https://lists.quagga.net/mailman/listinfo/quagga-dev

Reply via email to