Hi,

Also, this needs some kind of commit message to explain what it's meant to achieve and the approach the commit is taking.

Thanks,

Paul

On Fri, 22 Jan 2016, 林守磊 wrote:

Donald

Patchwork reports fail again with the same reason (
http://patchwork.quagga.net/patch/1794/ ). That really hit my passion :)

re-post patch as attachment, may it help you read patch conveniently.

By the way, please look my github of branch perfect_table_command_master
which contains change

Thank you

2016-01-21 10:28 GMT+08:00 林守磊 <linxiu...@gmail.com>:

Donald -

Thank you for your suggestion. I try to use git format-patch and push my
work onto github ( https://github.com/linxiulei/quagga ). See results
below

From 3ce69a48ec8bb52e4019c5424f6ba82d6495fb7c Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?=E7=9F=B3=E7=A5=A4?= <leilei....@alibaba-inc.com>
Date: Sun, 10 Jan 2016 14:36:56 +0800
Subject: [PATCH 3511/3511] perfect cmd table

---
 lib/table.h       |   1 +
 zebra/main.c      |   7 +-
 zebra/rib.h       |  49 ++++++++++--
 zebra/test_main.c |   5 +-
 zebra/zebra_rib.c | 167 ++++++++++++++++++++++++++++++++-------
 zebra/zebra_vty.c | 232
++++++++++++++++++++++++++++++++++++++++--------------
 6 files changed, 359 insertions(+), 102 deletions(-)

diff --git a/lib/table.h b/lib/table.h
index 2ffd79b..9906729 100644
--- a/lib/table.h
+++ b/lib/table.h
@@ -54,6 +54,7 @@ struct route_table
 {
   struct route_node *top;

+  int table_id;
   /*
    * Delegate that performs certain functions for this table.
    */
diff --git a/zebra/main.c b/zebra/main.c
index f3c08f1..4d25475 100644
--- a/zebra/main.c
+++ b/zebra/main.c
@@ -249,8 +249,11 @@ zebra_vrf_disable (vrf_id_t vrf_id, void **info)

   assert (zvrf);

-  rib_close_table (zvrf->table[AFI_IP][SAFI_UNICAST]);
-  rib_close_table (zvrf->table[AFI_IP6][SAFI_UNICAST]);
+  ZVRF_FOREACH_RTINFO(zvrf)
+  {
+  rib_close_table (rt_info->table[AFI_IP][SAFI_UNICAST]);
+  rib_close_table (rt_info->table[AFI_IP6][SAFI_UNICAST]);
+  }

   for (ALL_LIST_ELEMENTS_RO (vrf_iflist (vrf_id), list_node, ifp))
     {
diff --git a/zebra/rib.h b/zebra/rib.h
index ffe7e2f..ccce064 100644
--- a/zebra/rib.h
+++ b/zebra/rib.h
@@ -27,6 +27,7 @@
 #include "prefix.h"
 #include "table.h"
 #include "queue.h"
+#include "vector.h"

 #define DISTANCE_INFINITY  255

@@ -330,14 +331,29 @@ struct nlsock
 };
 #endif

+struct route_table_info
+{
+  /* Routing table id */
+  int table_id;
+
+  /* Routing table name.  */
+  char *name;
+
+  /* Routing table.  */
+  struct route_table *table[AFI_MAX][SAFI_MAX];
+
+  /* Static route configuration.  */
+  struct route_table *stable[AFI_MAX][SAFI_MAX];
+
+};
 /* Routing table instance.  */
 struct zebra_vrf
 {
   /* Identifier. */
   vrf_id_t vrf_id;

-  /* Routing table name.  */
-  char *name;
+  /* Contain all the route tables */
+  vector route_tables_info;

   /* Description.  */
   char *desc;
@@ -345,12 +361,6 @@ struct zebra_vrf
   /* FIB identifier.  */
   u_char fib_id;

-  /* Routing table.  */
-  struct route_table *table[AFI_MAX][SAFI_MAX];
-
-  /* Static route configuration.  */
-  struct route_table *stable[AFI_MAX][SAFI_MAX];
-
 #ifdef HAVE_NETLINK
   struct nlsock netlink;     /* kernel messages */
   struct nlsock netlink_cmd; /* command channel */
@@ -520,6 +530,11 @@ static_delete_ipv6 (struct prefix *p, u_char type,
struct in6_addr *gate,
 extern int rib_gc_dest (struct route_node *rn);
 extern struct route_table *rib_tables_iter_next (rib_tables_iter_t *iter);

+extern struct route_table_info *get_route_table_info(
+        struct zebra_vrf *zvrf, int table_id);
+
+extern struct route_table *zebra_vrf_table_id (
+        afi_t afi, safi_t safi, vrf_id_t vrf_id, int table_id);
 /*
  * Inline functions.
  */
@@ -630,4 +645,22 @@ rib_tables_iter_cleanup (rib_tables_iter_t *iter)
   iter->state = RIB_TABLES_ITER_S_DONE;
 }

+#define VRF_FOREACH_TABLE(vrf_id, table, afi, safi)\
+  struct zebra_vrf *zvrf = vrf_info_lookup (vrf_id);\
+  (table) = ((struct
route_table_info*)vector_lookup((zvrf)->route_tables_info,
0))->table[afi][safi];\
+  for(int i = 0; i < vector_count((zvrf)->route_tables_info);\
+     (table) = ((struct
route_table_info*)vector_lookup((zvrf)->route_tables_info,
i))->table[afi][safi], \
+     i++)
+
+#define ZVRF_FOREACH_TABLE(zvrf, table, afi, safi)\
+  (table) = ((struct
route_table_info*)vector_lookup((zvrf)->route_tables_info,
0))->table[afi][safi];\
+  for(int i = 0; i < vector_count((zvrf)->route_tables_info);\
+     (table) = ((struct
route_table_info*)vector_lookup((zvrf)->route_tables_info,
i))->table[afi][safi], \
+     i++)
+
+#define ZVRF_FOREACH_RTINFO(zvrf)\
+  struct route_table_info *rt_info =
vector_lookup((zvrf)->route_tables_info, 0);\
+  for(int i = 0; i < vector_count((zvrf)->route_tables_info);\
+     (rt_info) = vector_lookup((zvrf)->route_tables_info, i), \
+     i++)
 #endif /*_ZEBRA_RIB_H */
diff --git a/zebra/test_main.c b/zebra/test_main.c
index 448d1ef..a705a20 100644
--- a/zebra/test_main.c
+++ b/zebra/test_main.c
@@ -233,11 +233,12 @@ zebra_vrf_disable (vrf_id_t vrf_id, void **info)
   struct zebra_vrf *zvrf = (struct zebra_vrf *) (*info);
   struct listnode *list_node;
   struct interface *ifp;
+  struct route_table_info *rt_info = get_route_table_info(zvrf,
RT_TABLE_MAIN);

   assert (zvrf);

-  rib_close_table (zvrf->table[AFI_IP][SAFI_UNICAST]);
-  rib_close_table (zvrf->table[AFI_IP6][SAFI_UNICAST]);
+  rib_close_table (rt_info->table[AFI_IP][SAFI_UNICAST]);
+  rib_close_table (rt_info->table[AFI_IP6][SAFI_UNICAST]);

   for (ALL_LIST_ELEMENTS_RO (vrf_iflist (vrf_id), list_node, ifp))
     {
diff --git a/zebra/zebra_rib.c b/zebra/zebra_rib.c
index 38357ff..9bcb7ec 100644
--- a/zebra/zebra_rib.c
+++ b/zebra/zebra_rib.c
@@ -1810,9 +1810,16 @@ rib_add_ipv4 (int type, int flags, struct
prefix_ipv4 *p,
   struct nexthop *nexthop;

   /* Lookup table.  */
-  table = zebra_vrf_table (AFI_IP, safi, vrf_id);
+  table = zebra_vrf_table_id(AFI_IP, safi, vrf_id, table_id);
   if (! table)
-    return 0;
+  {
+    struct zebra_vrf *zvrf = vrf_info_lookup (vrf_id);
+    if (!zvrf)
+      return NULL;
+
+    zebra_route_tables_create(zvrf, table_id);
+    table = zebra_vrf_table_id(AFI_IP, safi, vrf_id, table_id);
+  }

   /* Make it sure prefixlen is applied to the prefix. */
   apply_mask_ipv4 (p);
@@ -2286,9 +2293,16 @@ static_install_route (afi_t afi, safi_t safi,
struct prefix *p, struct static_ro
   struct route_table *table;

   /* Lookup table.  */
-  table = zebra_vrf_table (afi, safi, si->vrf_id);
+  table = zebra_vrf_table_id(afi, safi, si->vrf_id,
zebrad.rtm_table_default);
   if (! table)
-    return;
+  {
+    struct zebra_vrf *zvrf = vrf_info_lookup (si->vrf_id);
+    if (!zvrf)
+      return NULL;
+
+    zebra_route_tables_create(zvrf, zebrad.rtm_table_default);
+    table = zebra_vrf_table_id(afi, safi, si->vrf_id,
zebrad.rtm_table_default);
+  }

   /* Lookup existing route */
   rn = route_node_get (table, p);
@@ -2474,7 +2488,15 @@ static_add_ipv4_safi (safi_t safi, struct prefix
*p, struct in_addr *gate,
   struct static_route *cp;
   struct static_route *update = NULL;
   struct zebra_vrf *zvrf = vrf_info_get (vrf_id);
-  struct route_table *stable = zvrf->stable[AFI_IP][safi];
+  struct route_table_info *rt_info = get_route_table_info(
+          zvrf, zebrad.rtm_table_default);
+  if (! rt_info)
+  {
+    zebra_route_tables_create(zvrf, zebrad.rtm_table_default);
+    rt_info = get_route_table_info(
+          zvrf, zebrad.rtm_table_default);
+  }
+  struct route_table *stable = rt_info->stable[AFI_IP][safi];

   if (! stable)
     return -1;
@@ -2868,7 +2890,15 @@ static_add_ipv6 (struct prefix *p, u_char type,
struct in6_addr *gate,
   struct static_route *cp;
   struct static_route *update = NULL;
   struct zebra_vrf *zvrf = vrf_info_get (vrf_id);
-  struct route_table *stable = zvrf->stable[AFI_IP6][SAFI_UNICAST];
+  struct route_table_info *rt_info = get_route_table_info(
+          zvrf, zebrad.rtm_table_default);
+  if (! rt_info)
+  {
+    zebra_route_tables_create(zvrf, zebrad.rtm_table_default);
+    rt_info = get_route_table_info(
+          zvrf, zebrad.rtm_table_default);
+  }
+  struct route_table *stable = rt_info->stable[AFI_IP6][SAFI_UNICAST];

   if (! stable)
     return -1;
@@ -3028,7 +3058,7 @@ rib_update (vrf_id_t vrf_id)

 /* Remove all routes which comes from non main table.  */
 static void
-rib_weed_table (struct route_table *table)
+rib_weed_table (struct route_table *table, int table_id)
 {
   struct route_node *rn;
   struct rib *rib;
@@ -3042,7 +3072,8 @@ rib_weed_table (struct route_table *table)
         continue;

       if (rib->table != zebrad.rtm_table_default &&
-          rib->table != RT_TABLE_MAIN)
+          rib->table != RT_TABLE_MAIN &&
+          rib->table != table_id)
             rib_delnode (rn, rib);
     }
 }
@@ -3053,12 +3084,19 @@ rib_weed_tables (void)
 {
   vrf_iter_t iter;
   struct zebra_vrf *zvrf;
+  struct route_table_info *rt_info;

   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]);
+        for (int i=0; i < vector_count(zvrf->route_tables_info); i++)
+        {
+          rt_info = vector_lookup(zvrf->route_tables_info, i);
+          rib_weed_table (rt_info->table[AFI_IP][SAFI_UNICAST],
+                  rt_info->table_id);
+          rib_weed_table (rt_info->table[AFI_IP6][SAFI_UNICAST],
+                  rt_info->table_id);
+        }
       }
 }

@@ -3100,8 +3138,11 @@ rib_sweep_route (void)
   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]);
+        struct route_table_info *rt_info = get_route_table_info(zvrf,
RT_TABLE_MAIN);
+        rib_weed_table (rt_info->table[AFI_IP][SAFI_UNICAST],
+                rt_info->table_id);
+        rib_weed_table (rt_info->table[AFI_IP6][SAFI_UNICAST],
+                rt_info->table_id);
       }
 }

@@ -3140,8 +3181,11 @@ rib_score_proto (u_char proto)

   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]);
+    {
+      struct route_table_info *rt_info = get_route_table_info(zvrf,
RT_TABLE_MAIN);
+      cnt += rib_score_proto_table (proto,
rt_info->table[AFI_IP][SAFI_UNICAST])
+            +rib_score_proto_table (proto,
rt_info->table[AFI_IP6][SAFI_UNICAST]);
+    }

   return cnt;
 }
@@ -3175,12 +3219,17 @@ rib_close (void)
 {
   vrf_iter_t iter;
   struct zebra_vrf *zvrf;
+  struct route_table_info *rt_info;

   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]);
+        for (int i=0; i < vector_count(zvrf->route_tables_info); i++)
+        {
+          rt_info = vector_lookup(zvrf->route_tables_info, i);
+          rib_close_table (rt_info->table[AFI_IP][SAFI_UNICAST]);
+          rib_close_table (rt_info->table[AFI_IP6][SAFI_UNICAST]);
+        }
       }
 }

@@ -3302,15 +3351,15 @@ rib_tables_iter_next (rib_tables_iter_t *iter)
  * Create a routing table for the specific AFI/SAFI in the given VRF.
  */
 static void
-zebra_vrf_table_create (struct zebra_vrf *zvrf, afi_t afi, safi_t safi)
+zebra_vrf_table_create (struct zebra_vrf *zvrf, struct route_table_info
*rt_info, afi_t afi, safi_t safi)
 {
   rib_table_info_t *info;
   struct route_table *table;

-  assert (!zvrf->table[afi][safi]);
+  assert (!rt_info->table[afi][safi]);

   table = route_table_init ();
-  zvrf->table[afi][safi] = table;
+  rt_info->table[afi][safi] = table;

   info = XCALLOC (MTYPE_RIB_TABLE_INFO, sizeof (*info));
   info->zvrf = zvrf;
@@ -3324,21 +3373,14 @@ struct zebra_vrf *
 zebra_vrf_alloc (vrf_id_t vrf_id)
 {
   struct zebra_vrf *zvrf;
+  struct route_table_info *rt_info;
 #ifdef HAVE_NETLINK
   char nl_name[64];
 #endif

   zvrf = XCALLOC (MTYPE_ZEBRA_VRF, sizeof (struct zebra_vrf));

-  /* Allocate routing table and static table.  */
-  zebra_vrf_table_create (zvrf, AFI_IP, SAFI_UNICAST);
-  zebra_vrf_table_create (zvrf, AFI_IP6, SAFI_UNICAST);
-  zvrf->stable[AFI_IP][SAFI_UNICAST] = route_table_init ();
-  zvrf->stable[AFI_IP6][SAFI_UNICAST] = route_table_init ();
-  zebra_vrf_table_create (zvrf, AFI_IP, SAFI_MULTICAST);
-  zebra_vrf_table_create (zvrf, AFI_IP6, SAFI_MULTICAST);
-  zvrf->stable[AFI_IP][SAFI_MULTICAST] = route_table_init ();
-  zvrf->stable[AFI_IP6][SAFI_MULTICAST] = route_table_init ();
+  init_zebra_route_tables_info(zvrf);

   /* Set VRF ID */
   zvrf->vrf_id = vrf_id;
@@ -3369,9 +3411,40 @@ zebra_vrf_table (afi_t afi, safi_t safi, vrf_id_t
vrf_id)
   if (afi >= AFI_MAX || safi >= SAFI_MAX)
     return NULL;

-  return zvrf->table[afi][safi];
+  struct route_table_info * rt_info = get_route_table_info(zvrf,
RT_TABLE_MAIN);
+
+  return rt_info->table[afi][safi];
 }

+/* Lookup the routing table in an enabled VRF. */
+struct route_table *
+zebra_vrf_table_id (afi_t afi, safi_t safi, vrf_id_t vrf_id, int table_id)
+{
+  struct zebra_vrf *zvrf = vrf_info_lookup (vrf_id);
+
+  if (!zvrf)
+    return NULL;
+
+  if (afi >= AFI_MAX || safi >= SAFI_MAX)
+    return NULL;
+
+  struct route_table_info * rt_info = get_route_table_info(zvrf,
table_id);
+  if (rt_info)
+    return rt_info->table[afi][safi];
+}
+
+struct route_table_info *
+get_route_table_info(struct zebra_vrf *zvrf, int table_id)
+{
+  struct route_table_info* rt_info;
+  for (int i=0; i < vector_count(zvrf->route_tables_info); i++)
+  {
+    rt_info = vector_lookup(zvrf->route_tables_info, i);
+    if (rt_info->table_id == table_id)
+      return rt_info;
+  }
+  return NULL;
+}
 /* Lookup the static routing table in a VRF. */
 struct route_table *
 zebra_vrf_static_table (afi_t afi, safi_t safi, vrf_id_t vrf_id)
@@ -3384,6 +3457,40 @@ zebra_vrf_static_table (afi_t afi, safi_t safi,
vrf_id_t vrf_id)
   if (afi >= AFI_MAX || safi >= SAFI_MAX)
     return NULL;

-  return zvrf->stable[afi][safi];
+  struct route_table_info *rt_info = get_route_table_info(zvrf,
RT_TABLE_MAIN);
+  return rt_info->stable[afi][safi];
 }

+void
+init_zebra_route_tables_info(struct zebra_vrf *zvrf)
+{
+  zvrf->route_tables_info = vector_init(1);
+  struct route_table_info *rt_info = malloc (sizeof(struct
route_table_info));
+  rt_info->table_id = RT_TABLE_MAIN;
+
+  init_zebra_route_table(zvrf, rt_info);
+  vector_set_index (zvrf->route_tables_info, 0, rt_info);
+}
+
+void
+zebra_route_tables_create(struct zebra_vrf *zvrf, int table_id)
+{
+  struct route_table_info *rt_info =  malloc (sizeof(struct
route_table_info));
+  rt_info->table_id = table_id;
+  init_zebra_route_table(zvrf, rt_info);
+  vector_set_index (zvrf->route_tables_info,
vector_count(zvrf->route_tables_info), rt_info);
+}
+
+void
+init_zebra_route_table(struct zebra_vrf *zvrf, struct route_table_info
*rt_info)
+{
+  /* Allocate routing table and static table.  */
+  zebra_vrf_table_create (zvrf, rt_info, AFI_IP, SAFI_UNICAST);
+  zebra_vrf_table_create (zvrf, rt_info, AFI_IP6, SAFI_UNICAST);
+  rt_info->stable[AFI_IP][SAFI_UNICAST] = route_table_init ();
+  rt_info->stable[AFI_IP6][SAFI_UNICAST] = route_table_init ();
+  zebra_vrf_table_create (zvrf, rt_info, AFI_IP, SAFI_MULTICAST);
+  zebra_vrf_table_create (zvrf, rt_info, AFI_IP6, SAFI_MULTICAST);
+  rt_info->stable[AFI_IP][SAFI_MULTICAST] = route_table_init ();
+  rt_info->stable[AFI_IP6][SAFI_MULTICAST] = route_table_init ();
+}
diff --git a/zebra/zebra_vty.c b/zebra/zebra_vty.c
index 656f55d..5369212 100644
--- a/zebra/zebra_vty.c
+++ b/zebra/zebra_vty.c
@@ -404,8 +404,11 @@ DEFUN (show_ip_rpf_vrf_all,

   for (iter = vrf_first (); iter != VRF_ITER_INVALID; iter = vrf_next
(iter))
     {
+      zvrf = vrf_iter2info (iter);
+      ZVRF_FOREACH_RTINFO(zvrf)
+      {
       if ((zvrf = vrf_iter2info (iter)) == NULL ||
-          (table = zvrf->table[AFI_IP][SAFI_MULTICAST]) == NULL)
+          (table = rt_info->table[AFI_IP][SAFI_MULTICAST]) == NULL)
         continue;

       /* Show all IPv4 routes. */
@@ -419,6 +422,7 @@ DEFUN (show_ip_rpf_vrf_all,
               }
             vty_show_ip_route (vty, rn, rib);
           }
+      }
     }

   return CMD_SUCCESS;
@@ -1579,21 +1583,24 @@ static int do_show_ip_route(struct vty *vty,
safi_t safi, vrf_id_t vrf_id)
   struct rib *rib;
   int first = 1;

-  table = zebra_vrf_table (AFI_IP, safi, vrf_id);
+
+  VRF_FOREACH_TABLE(vrf_id, table, AFI_IP, safi)
+  {
   if (! table)
-    return CMD_SUCCESS;
+    continue;

   /* Show all IPv4 routes. */
   for (rn = route_top (table); rn; rn = route_next (rn))
     RNODE_FOREACH_RIB (rn, rib)
       {
-    if (first)
-      {
-        vty_out (vty, SHOW_ROUTE_V4_HEADER);
-        first = 0;
-      }
-    vty_show_ip_route (vty, rn, rib);
+    if (first)
+      {
+        vty_out (vty, SHOW_ROUTE_V4_HEADER);
+        first = 0;
       }
+    vty_show_ip_route (vty, rn, rib);
+      }
+  }
   return CMD_SUCCESS;
 }

@@ -1632,9 +1639,10 @@ DEFUN (show_ip_route_prefix_longer,
   if (argc > 1)
     VTY_GET_INTEGER ("VRF ID", vrf_id, argv[1]);

-  table = zebra_vrf_table (AFI_IP, SAFI_UNICAST, vrf_id);
+  VRF_FOREACH_TABLE(vrf_id, table, AFI_IP, SAFI_UNICAST)
+  {
   if (! table)
-    return CMD_SUCCESS;
+    continue;

   /* Show matched type IPv4 routes. */
   for (rn = route_top (table); rn; rn = route_next (rn))
@@ -1648,6 +1656,7 @@ DEFUN (show_ip_route_prefix_longer,
         }
       vty_show_ip_route (vty, rn, rib);
     }
+  }
   return CMD_SUCCESS;
 }

@@ -1679,9 +1688,10 @@ DEFUN (show_ip_route_supernets,
   if (argc > 0)
     VTY_GET_INTEGER ("VRF ID", vrf_id, argv[0]);

-  table = zebra_vrf_table (AFI_IP, SAFI_UNICAST, vrf_id);
+  VRF_FOREACH_TABLE(vrf_id, table, AFI_IP, SAFI_UNICAST)
+  {
   if (! table)
-    return CMD_SUCCESS;
+    continue;

   /* Show matched type IPv4 routes. */
   for (rn = route_top (table); rn; rn = route_next (rn))
@@ -1701,6 +1711,7 @@ DEFUN (show_ip_route_supernets,
         vty_show_ip_route (vty, rn, rib);
       }
       }
+  }
   return CMD_SUCCESS;
 }

@@ -1738,9 +1749,10 @@ DEFUN (show_ip_route_protocol,
   if (argc > 1)
     VTY_GET_INTEGER ("VRF ID", vrf_id, argv[1]);

-  table = zebra_vrf_table (AFI_IP, SAFI_UNICAST, vrf_id);
+  VRF_FOREACH_TABLE(vrf_id, table, AFI_IP, SAFI_UNICAST)
+  {
   if (! table)
-    return CMD_SUCCESS;
+    continue;

   /* Show matched type IPv4 routes. */
   for (rn = route_top (table); rn; rn = route_next (rn))
@@ -1754,6 +1766,7 @@ DEFUN (show_ip_route_protocol,
         }
       vty_show_ip_route (vty, rn, rib);
     }
+  }
   return CMD_SUCCESS;
 }

@@ -1790,9 +1803,10 @@ DEFUN (show_ip_route_addr,
   if (argc > 1)
     VTY_GET_INTEGER ("VRF ID", vrf_id, argv[1]);

-  table = zebra_vrf_table (AFI_IP, SAFI_UNICAST, vrf_id);
+  VRF_FOREACH_TABLE(vrf_id, table, AFI_IP, SAFI_UNICAST)
+  {
   if (! table)
-    return CMD_SUCCESS;
+    continue;

   rn = route_node_match (table, (struct prefix *) &p);
   if (! rn)
@@ -1804,6 +1818,7 @@ DEFUN (show_ip_route_addr,
   vty_show_ip_route_detail (vty, rn, 0);

   route_unlock_node (rn);
+  }

   return CMD_SUCCESS;
 }
@@ -1841,9 +1856,10 @@ DEFUN (show_ip_route_prefix,
   if (argc > 1)
     VTY_GET_INTEGER ("VRF ID", vrf_id, argv[1]);

-  table = zebra_vrf_table (AFI_IP, SAFI_UNICAST, vrf_id);
+  VRF_FOREACH_TABLE(vrf_id, table, AFI_IP, SAFI_UNICAST)
+  {
   if (! table)
-    return CMD_SUCCESS;
+    continue;

   rn = route_node_match (table, (struct prefix *) &p);
   if (! rn || rn->p.prefixlen != p.prefixlen)
@@ -1857,6 +1873,7 @@ DEFUN (show_ip_route_prefix,
   vty_show_ip_route_detail (vty, rn, 0);

   route_unlock_node (rn);
+  }

   return CMD_SUCCESS;
 }
@@ -2033,12 +2050,14 @@ DEFUN (show_ip_route_summary,
   if (argc > 0)
     VTY_GET_INTEGER ("VRF ID", vrf_id, argv[0]);

-  table = zebra_vrf_table (AFI_IP, SAFI_UNICAST, vrf_id);
+  VRF_FOREACH_TABLE(vrf_id, table, AFI_IP, SAFI_UNICAST)
+  {
   if (! table)
-    return CMD_SUCCESS;
+    continue;

   vty_show_ip_route_summary (vty, table);

+  }
   return CMD_SUCCESS;
 }

@@ -2067,11 +2086,13 @@ DEFUN (show_ip_route_summary_prefix,
   if (argc > 0)
     VTY_GET_INTEGER ("VRF ID", vrf_id, argv[0]);

-  table = zebra_vrf_table (AFI_IP, SAFI_UNICAST, vrf_id);
+  VRF_FOREACH_TABLE(vrf_id, table, AFI_IP, SAFI_UNICAST)
+  {
   if (! table)
-    return CMD_SUCCESS;
+    continue;

   vty_show_ip_route_summary_prefix (vty, table);
+  }

   return CMD_SUCCESS;
 }
@@ -2103,8 +2124,11 @@ DEFUN (show_ip_route_vrf_all,

   for (iter = vrf_first (); iter != VRF_ITER_INVALID; iter = vrf_next
(iter))
     {
+      zvrf = vrf_iter2info (iter);
+      ZVRF_FOREACH_RTINFO(zvrf)
+      {
       if ((zvrf = vrf_iter2info (iter)) == NULL ||
-          (table = zvrf->table[AFI_IP][SAFI_UNICAST]) == NULL)
+          (table = rt_info->table[AFI_IP][SAFI_UNICAST]) == NULL)
         continue;

       /* Show all IPv4 routes. */
@@ -2118,6 +2142,7 @@ DEFUN (show_ip_route_vrf_all,
               }
             vty_show_ip_route (vty, rn, rib);
           }
+      }
     }

   return CMD_SUCCESS;
@@ -2151,8 +2176,11 @@ DEFUN (show_ip_route_prefix_longer_vrf_all,

   for (iter = vrf_first (); iter != VRF_ITER_INVALID; iter = vrf_next
(iter))
     {
+      zvrf = vrf_iter2info (iter);
+      ZVRF_FOREACH_RTINFO(zvrf)
+      {
       if ((zvrf = vrf_iter2info (iter)) == NULL ||
-          (table = zvrf->table[AFI_IP][SAFI_UNICAST]) == NULL)
+          (table = rt_info->table[AFI_IP][SAFI_UNICAST]) == NULL)
         continue;

       /* Show matched type IPv4 routes. */
@@ -2167,6 +2195,7 @@ DEFUN (show_ip_route_prefix_longer_vrf_all,
                 }
               vty_show_ip_route (vty, rn, rib);
             }
+      }
     }

   return CMD_SUCCESS;
@@ -2191,8 +2220,11 @@ DEFUN (show_ip_route_supernets_vrf_all,

   for (iter = vrf_first (); iter != VRF_ITER_INVALID; iter = vrf_next
(iter))
     {
+      zvrf = vrf_iter2info (iter);
+      ZVRF_FOREACH_RTINFO(zvrf)
+      {
       if ((zvrf = vrf_iter2info (iter)) == NULL ||
-          (table = zvrf->table[AFI_IP][SAFI_UNICAST]) == NULL)
+          (table = rt_info->table[AFI_IP][SAFI_UNICAST]) == NULL)
         continue;

       /* Show matched type IPv4 routes. */
@@ -2213,6 +2245,7 @@ DEFUN (show_ip_route_supernets_vrf_all,
                 vty_show_ip_route (vty, rn, rib);
               }
           }
+      }
     }

   return CMD_SUCCESS;
@@ -2244,8 +2277,11 @@ DEFUN (show_ip_route_protocol_vrf_all,

   for (iter = vrf_first (); iter != VRF_ITER_INVALID; iter = vrf_next
(iter))
     {
+      zvrf = vrf_iter2info (iter);
+      ZVRF_FOREACH_RTINFO(zvrf)
+      {
       if ((zvrf = vrf_iter2info (iter)) == NULL ||
-          (table = zvrf->table[AFI_IP][SAFI_UNICAST]) == NULL)
+          (table = rt_info->table[AFI_IP][SAFI_UNICAST]) == NULL)
         continue;

       /* Show matched type IPv4 routes. */
@@ -2260,6 +2296,7 @@ DEFUN (show_ip_route_protocol_vrf_all,
                 }
               vty_show_ip_route (vty, rn, rib);
             }
+      }
     }

   return CMD_SUCCESS;
@@ -2290,8 +2327,11 @@ DEFUN (show_ip_route_addr_vrf_all,

   for (iter = vrf_first (); iter != VRF_ITER_INVALID; iter = vrf_next
(iter))
     {
+      zvrf = vrf_iter2info (iter);
+      ZVRF_FOREACH_RTINFO(zvrf)
+      {
       if ((zvrf = vrf_iter2info (iter)) == NULL ||
-          (table = zvrf->table[AFI_IP][SAFI_UNICAST]) == NULL)
+          (table = rt_info->table[AFI_IP][SAFI_UNICAST]) == NULL)
         continue;

       rn = route_node_match (table, (struct prefix *) &p);
@@ -2302,6 +2342,7 @@ DEFUN (show_ip_route_addr_vrf_all,

       route_unlock_node (rn);
     }
+    }

   return CMD_SUCCESS;
 }
@@ -2331,8 +2372,11 @@ DEFUN (show_ip_route_prefix_vrf_all,

   for (iter = vrf_first (); iter != VRF_ITER_INVALID; iter = vrf_next
(iter))
     {
+      zvrf = vrf_iter2info (iter);
+      ZVRF_FOREACH_RTINFO(zvrf)
+      {
       if ((zvrf = vrf_iter2info (iter)) == NULL ||
-          (table = zvrf->table[AFI_IP][SAFI_UNICAST]) == NULL)
+          (table = rt_info->table[AFI_IP][SAFI_UNICAST]) == NULL)
         continue;

       rn = route_node_match (table, (struct prefix *) &p);
@@ -2348,6 +2392,7 @@ DEFUN (show_ip_route_prefix_vrf_all,

       route_unlock_node (rn);
     }
+    }

   return CMD_SUCCESS;
 }
@@ -2366,7 +2411,12 @@ DEFUN (show_ip_route_summary_vrf_all,

   for (iter = vrf_first (); iter != VRF_ITER_INVALID; iter = vrf_next
(iter))
     if ((zvrf = vrf_iter2info (iter)) != NULL)
-      vty_show_ip_route_summary (vty, zvrf->table[AFI_IP][SAFI_UNICAST]);
+    {
+      ZVRF_FOREACH_RTINFO(zvrf)
+      {
+      vty_show_ip_route_summary (vty,
rt_info->table[AFI_IP][SAFI_UNICAST]);
+      }
+    }

   return CMD_SUCCESS;
 }
@@ -2386,7 +2436,12 @@ DEFUN (show_ip_route_summary_prefix_vrf_all,

   for (iter = vrf_first (); iter != VRF_ITER_INVALID; iter = vrf_next
(iter))
     if ((zvrf = vrf_iter2info (iter)) != NULL)
-      vty_show_ip_route_summary_prefix (vty,
zvrf->table[AFI_IP][SAFI_UNICAST]);
+    {
+      ZVRF_FOREACH_RTINFO(zvrf)
+      {
+      vty_show_ip_route_summary_prefix (vty,
rt_info->table[AFI_IP][SAFI_UNICAST]);
+      }
+    }

   return CMD_SUCCESS;
 }
@@ -2406,8 +2461,11 @@ static_config_ipv4 (struct vty *vty, safi_t safi,
const char *cmd)

   for (iter = vrf_first (); iter != VRF_ITER_INVALID; iter = vrf_next
(iter))
     {
+      zvrf = vrf_iter2info (iter);
+      ZVRF_FOREACH_RTINFO(zvrf)
+      {
       if ((zvrf = vrf_iter2info (iter)) == NULL ||
-          (stable = zvrf->stable[AFI_IP][safi]) == NULL)
+          (stable = rt_info->stable[AFI_IP][safi]) == NULL)
         continue;

       for (rn = route_top (stable); rn; rn = route_next (rn))
@@ -2449,6 +2507,7 @@ static_config_ipv4 (struct vty *vty, safi_t safi,
const char *cmd)

             write = 1;
           }
+      }
     }
   return write;
 }
@@ -3072,9 +3131,10 @@ DEFUN (show_ipv6_route,
   if (argc > 0)
     VTY_GET_INTEGER ("VRF ID", vrf_id, argv[0]);

-  table = zebra_vrf_table (AFI_IP6, SAFI_UNICAST, vrf_id);
+  VRF_FOREACH_TABLE(vrf_id, table, AFI_IP6, SAFI_UNICAST)
+  {
   if (! table)
-    return CMD_SUCCESS;
+    continue;

   /* Show all IPv6 route. */
   for (rn = route_top (table); rn; rn = route_next (rn))
@@ -3087,6 +3147,7 @@ DEFUN (show_ipv6_route,
       }
     vty_show_ip_route (vty, rn, rib);
       }
+  }
   return CMD_SUCCESS;
 }

@@ -3125,9 +3186,10 @@ DEFUN (show_ipv6_route_prefix_longer,
   if (argc > 1)
     VTY_GET_INTEGER ("VRF ID", vrf_id, argv[1]);

-  table = zebra_vrf_table (AFI_IP6, SAFI_UNICAST, vrf_id);
+  VRF_FOREACH_TABLE(vrf_id, table, AFI_IP6, SAFI_UNICAST)
+  {
   if (! table)
-    return CMD_SUCCESS;
+    continue;

   /* Show matched type IPv6 routes. */
   for (rn = route_top (table); rn; rn = route_next (rn))
@@ -3141,6 +3203,7 @@ DEFUN (show_ipv6_route_prefix_longer,
         }
       vty_show_ip_route (vty, rn, rib);
     }
+  }
   return CMD_SUCCESS;
 }

@@ -3179,9 +3242,10 @@ DEFUN (show_ipv6_route_protocol,
   if (argc > 1)
     VTY_GET_INTEGER ("VRF ID", vrf_id, argv[1]);

-  table = zebra_vrf_table (AFI_IP6, SAFI_UNICAST, vrf_id);
+  VRF_FOREACH_TABLE(vrf_id, table, AFI_IP6, SAFI_UNICAST)
+  {
   if (! table)
-    return CMD_SUCCESS;
+    continue;

   /* Show matched type IPv6 routes. */
   for (rn = route_top (table); rn; rn = route_next (rn))
@@ -3195,6 +3259,7 @@ DEFUN (show_ipv6_route_protocol,
         }
       vty_show_ip_route (vty, rn, rib);
     }
+  }
   return CMD_SUCCESS;
 }

@@ -3231,9 +3296,10 @@ DEFUN (show_ipv6_route_addr,
   if (argc > 1)
     VTY_GET_INTEGER ("VRF ID", vrf_id, argv[1]);

-  table = zebra_vrf_table (AFI_IP6, SAFI_UNICAST, vrf_id);
+  VRF_FOREACH_TABLE(vrf_id, table, AFI_IP6, SAFI_UNICAST)
+  {
   if (! table)
-    return CMD_SUCCESS;
+    continue;

   rn = route_node_match (table, (struct prefix *) &p);
   if (! rn)
@@ -3246,6 +3312,7 @@ DEFUN (show_ipv6_route_addr,

   route_unlock_node (rn);

+  }
   return CMD_SUCCESS;
 }

@@ -3282,9 +3349,10 @@ DEFUN (show_ipv6_route_prefix,
   if (argc > 1)
     VTY_GET_INTEGER ("VRF ID", vrf_id, argv[1]);

-  table = zebra_vrf_table (AFI_IP6, SAFI_UNICAST, vrf_id);
+  VRF_FOREACH_TABLE(vrf_id, table, AFI_IP6, SAFI_UNICAST)
+  {
   if (! table)
-    return CMD_SUCCESS;
+    continue;

   rn = route_node_match (table, (struct prefix *) &p);
   if (! rn || rn->p.prefixlen != p.prefixlen)
@@ -3298,6 +3366,7 @@ DEFUN (show_ipv6_route_prefix,
   vty_show_ip_route_detail (vty, rn, 0);

   route_unlock_node (rn);
+  }

   return CMD_SUCCESS;
 }
@@ -3326,12 +3395,13 @@ DEFUN (show_ipv6_route_summary,
   if (argc > 0)
     VTY_GET_INTEGER ("VRF ID", vrf_id, argv[0]);

-  table = zebra_vrf_table (AFI_IP6, SAFI_UNICAST, vrf_id);
+  VRF_FOREACH_TABLE(vrf_id, table, AFI_IP6, SAFI_UNICAST)
+  {
   if (! table)
-    return CMD_SUCCESS;
+    continue;

   vty_show_ip_route_summary (vty, table);
-
+  }
   return CMD_SUCCESS;
 }

@@ -3360,11 +3430,13 @@ DEFUN (show_ipv6_route_summary_prefix,
   if (argc > 0)
     VTY_GET_INTEGER ("VRF ID", vrf_id, argv[0]);

-  table = zebra_vrf_table (AFI_IP6, SAFI_UNICAST, vrf_id);
+  VRF_FOREACH_TABLE(vrf_id, table, AFI_IP6, SAFI_UNICAST)
+  {
   if (! table)
-    return CMD_SUCCESS;
+    continue;

   vty_show_ip_route_summary_prefix (vty, table);
+  }

   return CMD_SUCCESS;
 }
@@ -3400,14 +3472,14 @@ DEFUN (show_ipv6_mroute,
   if (argc > 0)
     VTY_GET_INTEGER ("VRF ID", vrf_id, argv[0]);

-  table = zebra_vrf_table (AFI_IP6, SAFI_MULTICAST, vrf_id);
+  VRF_FOREACH_TABLE(vrf_id, table, AFI_IP6, SAFI_MULTICAST)
+  {
   if (! table)
-    return CMD_SUCCESS;
+    continue;

   /* Show all IPv6 route. */
   for (rn = route_top (table); rn; rn = route_next (rn))
-    RNODE_FOREACH_RIB (rn, rib)
-      {
+    RNODE_FOREACH_RIB (rn, rib) {
        if (first)
          {
        vty_out (vty, SHOW_ROUTE_V6_HEADER);
@@ -3415,6 +3487,7 @@ DEFUN (show_ipv6_mroute,
          }
        vty_show_ip_route (vty, rn, rib);
       }
+  }
   return CMD_SUCCESS;
 }

@@ -3443,8 +3516,11 @@ DEFUN (show_ipv6_route_vrf_all,

   for (iter = vrf_first (); iter != VRF_ITER_INVALID; iter = vrf_next
(iter))
     {
+      zvrf = vrf_iter2info (iter);
+      ZVRF_FOREACH_RTINFO(zvrf)
+      {
       if ((zvrf = vrf_iter2info (iter)) == NULL ||
-          (table = zvrf->table[AFI_IP6][SAFI_UNICAST]) == NULL)
+          (table = rt_info->table[AFI_IP6][SAFI_UNICAST]) == NULL)
         continue;

       /* Show all IPv6 route. */
@@ -3458,6 +3534,7 @@ DEFUN (show_ipv6_route_vrf_all,
               }
             vty_show_ip_route (vty, rn, rib);
           }
+      }
     }

   return CMD_SUCCESS;
@@ -3491,8 +3568,11 @@ DEFUN (show_ipv6_route_prefix_longer_vrf_all,

   for (iter = vrf_first (); iter != VRF_ITER_INVALID; iter = vrf_next
(iter))
     {
+      zvrf = vrf_iter2info (iter);
+      ZVRF_FOREACH_RTINFO(zvrf)
+      {
       if ((zvrf = vrf_iter2info (iter)) == NULL ||
-          (table = zvrf->table[AFI_IP6][SAFI_UNICAST]) == NULL)
+          (table = rt_info->table[AFI_IP6][SAFI_UNICAST]) == NULL)
         continue;

       /* Show matched type IPv6 routes. */
@@ -3507,6 +3587,7 @@ DEFUN (show_ipv6_route_prefix_longer_vrf_all,
                 }
               vty_show_ip_route (vty, rn, rib);
             }
+      }
     }

   return CMD_SUCCESS;
@@ -3538,8 +3619,11 @@ DEFUN (show_ipv6_route_protocol_vrf_all,

   for (iter = vrf_first (); iter != VRF_ITER_INVALID; iter = vrf_next
(iter))
     {
+      zvrf = vrf_iter2info (iter);
+      ZVRF_FOREACH_RTINFO(zvrf)
+      {
       if ((zvrf = vrf_iter2info (iter)) == NULL ||
-          (table = zvrf->table[AFI_IP6][SAFI_UNICAST]) == NULL)
+          (table = rt_info->table[AFI_IP6][SAFI_UNICAST]) == NULL)
         continue;

       /* Show matched type IPv6 routes. */
@@ -3554,6 +3638,7 @@ DEFUN (show_ipv6_route_protocol_vrf_all,
                 }
               vty_show_ip_route (vty, rn, rib);
             }
+      }
     }

   return CMD_SUCCESS;
@@ -3584,8 +3669,11 @@ DEFUN (show_ipv6_route_addr_vrf_all,

   for (iter = vrf_first (); iter != VRF_ITER_INVALID; iter = vrf_next
(iter))
     {
+      zvrf = vrf_iter2info (iter);
+      ZVRF_FOREACH_RTINFO(zvrf)
+      {
       if ((zvrf = vrf_iter2info (iter)) == NULL ||
-          (table = zvrf->table[AFI_IP6][SAFI_UNICAST]) == NULL)
+          (table = rt_info->table[AFI_IP6][SAFI_UNICAST]) == NULL)
         continue;

       rn = route_node_match (table, (struct prefix *) &p);
@@ -3596,6 +3684,7 @@ DEFUN (show_ipv6_route_addr_vrf_all,

       route_unlock_node (rn);
     }
+    }

   return CMD_SUCCESS;
 }
@@ -3625,8 +3714,11 @@ DEFUN (show_ipv6_route_prefix_vrf_all,

   for (iter = vrf_first (); iter != VRF_ITER_INVALID; iter = vrf_next
(iter))
     {
+      zvrf = vrf_iter2info (iter);
+      ZVRF_FOREACH_RTINFO(zvrf)
+      {
       if ((zvrf = vrf_iter2info (iter)) == NULL ||
-          (table = zvrf->table[AFI_IP6][SAFI_UNICAST]) == NULL)
+          (table = rt_info->table[AFI_IP6][SAFI_UNICAST]) == NULL)
         continue;

       rn = route_node_match (table, (struct prefix *) &p);
@@ -3642,6 +3734,7 @@ DEFUN (show_ipv6_route_prefix_vrf_all,

       route_unlock_node (rn);
     }
+    }

   return CMD_SUCCESS;
 }
@@ -3660,8 +3753,14 @@ DEFUN (show_ipv6_route_summary_vrf_all,
   vrf_iter_t iter;

   for (iter = vrf_first (); iter != VRF_ITER_INVALID; iter = vrf_next
(iter))
+  {
+      zvrf = vrf_iter2info (iter);
+    ZVRF_FOREACH_RTINFO(zvrf)
+    {
     if ((zvrf = vrf_iter2info (iter)) != NULL)
-      vty_show_ip_route_summary (vty, zvrf->table[AFI_IP6][SAFI_UNICAST]);
+      vty_show_ip_route_summary (vty,
rt_info->table[AFI_IP6][SAFI_UNICAST]);
+    }
+  }

   return CMD_SUCCESS;
 }
@@ -3683,8 +3782,11 @@ DEFUN (show_ipv6_mroute_vrf_all,

   for (iter = vrf_first (); iter != VRF_ITER_INVALID; iter = vrf_next
(iter))
     {
+      zvrf = vrf_iter2info (iter);
+      ZVRF_FOREACH_RTINFO(zvrf)
+      {
       if ((zvrf = vrf_iter2info (iter)) == NULL ||
-          (table = zvrf->table[AFI_IP6][SAFI_UNICAST]) == NULL)
+          (table = rt_info->table[AFI_IP6][SAFI_UNICAST]) == NULL)
         continue;

       /* Show all IPv6 route. */
@@ -3698,6 +3800,7 @@ DEFUN (show_ipv6_mroute_vrf_all,
              }
            vty_show_ip_route (vty, rn, rib);
           }
+      }
     }
   return CMD_SUCCESS;
 }
@@ -3717,7 +3820,12 @@ DEFUN (show_ipv6_route_summary_prefix_vrf_all,

   for (iter = vrf_first (); iter != VRF_ITER_INVALID; iter = vrf_next
(iter))
     if ((zvrf = vrf_iter2info (iter)) != NULL)
-      vty_show_ip_route_summary_prefix (vty,
zvrf->table[AFI_IP6][SAFI_UNICAST]);
+    {
+    ZVRF_FOREACH_RTINFO(zvrf)
+    {
+      vty_show_ip_route_summary_prefix (vty,
rt_info->table[AFI_IP6][SAFI_UNICAST]);
+    }
+    }

   return CMD_SUCCESS;
 }
@@ -3738,8 +3846,11 @@ static_config_ipv6 (struct vty *vty)

   for (iter = vrf_first (); iter != VRF_ITER_INVALID; iter = vrf_next
(iter))
     {
+      zvrf = vrf_iter2info (iter);
+      ZVRF_FOREACH_RTINFO(zvrf)
+      {
       if ((zvrf = vrf_iter2info (iter)) == NULL ||
-          (stable = zvrf->stable[AFI_IP6][SAFI_UNICAST]) == NULL)
+          (stable = rt_info->stable[AFI_IP6][SAFI_UNICAST]) == NULL)
         continue;

       for (rn = route_top (stable); rn; rn = route_next (rn))
@@ -3779,6 +3890,7 @@ static_config_ipv6 (struct vty *vty)

             write = 1;
           }
+      }
     }
   return write;
 }
--
2.1.2



2016-01-20 21:12 GMT+08:00 Donald Sharp <sha...@cumulusnetworks.com>:

Lin -

Can you use 'git format-patch' or 'git send-email' to send me the patch
you want?  The patch you just sent is some weird amalgamation of some
previous patches that I don't quite understand.

Perhaps additionally you could push your work onto github and I can take
a look at it from there?

thanks!

donald

On Wed, Jan 20, 2016 at 1:37 AM, 林守磊 <linxiu...@gmail.com> wrote:

Donald

I figure it out!

My patch is all right when patch it to commit
eae18d16fefed42af33e63e096a2889b9c70b9cb.
It is just something happen when the Patchwork receive this patch. That
patch was cut short unexpectedly. See
http://patchwork.quagga.net/patch/1750/

I re-post patch as attachment

2016-01-20 14:10 GMT+08:00 林守磊 <linxiu...@gmail.com>:

Donald -

That patch was base on master, commit is
eae18d16fefed42af33e63e096a2889b9c70b9cb.

Is that right? or can you give a guide, Thank you

2016-01-19 11:12 GMT+08:00 Donald Sharp <sha...@cumulusnetworks.com>:

Lin -

I attempted to apply this patch to the next patch tree:

sharpd@Robot:/work/robot/sharpd/q-six$ patch -p1 <
quagga-dev-14488-Re-Patch-Perfect-command-table.patch
patching file lib/table.h
patching file zebra/main.c
patching file zebra/rib.h
patch: **** malformed patch at line 1691: struct in6_addr *gate,

Can you fix it and resend?  The patch is messed up enough that I'm not
going to attempt to fix it.

donald

On Fri, Jan 15, 2016 at 7:57 AM, Donald Sharp <
sha...@cumulusnetworks.com> wrote:

Lin -

I believe this patch is fine from a posting standpoint.  I haven't
had a chance to look at it yet.  It's on my list of things to do today.

donald

On Fri, Jan 15, 2016 at 1:50 AM, 林守磊 <linxiu...@gmail.com> wrote:

Should I re-post this patch in a new mail?


Regard

2016-01-10 11:54 GMT+08:00 林守磊 <linxiu...@gmail.com>:

Thanks for your commets. These are really helpful.
I update my patch for adapt to the latest quagga code.

This code add a new struct route_table_info between zebra_vrf and
route_table, which help us for select route_table by table id

 lib/table.h       |   1 +
 zebra/main.c      |   7 ++++--
 zebra/rib.h       |  49 ++++++++++++++++++++++++++++++-------
 zebra/test_main.c |   5 ++--
 zebra/zebra_rib.c | 167
+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++-----------------------
 zebra/zebra_vty.c | 232
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++----------------------------------------------
 6 files changed, 359 insertions(+), 102 deletions(-)

diff --git a/lib/table.h b/lib/table.h
index 2ffd79b..9906729 100644
--- a/lib/table.h
+++ b/lib/table.h
@@ -54,6 +54,7 @@ struct route_table
 {
   struct route_node *top;

+  int table_id;
   /*
    * Delegate that performs certain functions for this table.
    */
diff --git a/zebra/main.c b/zebra/main.c
index f3c08f1..4d25475 100644
--- a/zebra/main.c
+++ b/zebra/main.c
@@ -249,8 +249,11 @@ zebra_vrf_disable (vrf_id_t vrf_id, void
**info)

   assert (zvrf);

-  rib_close_table (zvrf->table[AFI_IP][SAFI_UNICAST]);
-  rib_close_table (zvrf->table[AFI_IP6][SAFI_UNICAST]);
+  ZVRF_FOREACH_RTINFO(zvrf)
+  {
+  rib_close_table (rt_info->table[AFI_IP][SAFI_UNICAST]);
+  rib_close_table (rt_info->table[AFI_IP6][SAFI_UNICAST]);
+  }

   for (ALL_LIST_ELEMENTS_RO (vrf_iflist (vrf_id), list_node, ifp))
     {
diff --git a/zebra/rib.h b/zebra/rib.h
index ffe7e2f..ccce064 100644
--- a/zebra/rib.h
+++ b/zebra/rib.h
@@ -27,6 +27,7 @@
 #include "prefix.h"
 #include "table.h"
 #include "queue.h"
+#include "vector.h"

 #define DISTANCE_INFINITY  255

@@ -330,14 +331,29 @@ struct nlsock
 };
 #endif

+struct route_table_info
+{
+  /* Routing table id */
+  int table_id;
+
+  /* Routing table name.  */
+  char *name;
+
+  /* Routing table.  */
+  struct route_table *table[AFI_MAX][SAFI_MAX];
+
+  /* Static route configuration.  */
+  struct route_table *stable[AFI_MAX][SAFI_MAX];
+
+};
 /* Routing table instance.  */
 struct zebra_vrf
 {
   /* Identifier. */
   vrf_id_t vrf_id;

-  /* Routing table name.  */
-  char *name;
+  /* Contain all the route tables */
+  vector route_tables_info;

   /* Description.  */
   char *desc;
@@ -345,12 +361,6 @@ struct zebra_vrf
   /* FIB identifier.  */
   u_char fib_id;

-  /* Routing table.  */
-  struct route_table *table[AFI_MAX][SAFI_MAX];
-
-  /* Static route configuration.  */
-  struct route_table *stable[AFI_MAX][SAFI_MAX];
-
 #ifdef HAVE_NETLINK
   struct nlsock netlink;     /* kernel messages */
   struct nlsock netlink_cmd; /* command channel */
@@ -520,6 +530,11 @@ static_delete_ipv6 (struct prefix *p, u_char
type, struct in6_addr *gate,
 extern int rib_gc_dest (struct route_node *rn);
 extern struct route_table *rib_tables_iter_next (rib_tables_iter_t
*iter);

+extern struct route_table_info *get_route_table_info(
+        struct zebra_vrf *zvrf, int table_id);
+
+extern struct route_table *zebra_vrf_table_id (
+        afi_t afi, safi_t safi, vrf_id_t vrf_id, int table_id);
 /*
  * Inline functions.
  */
@@ -630,4 +645,22 @@ rib_tables_iter_cleanup (rib_tables_iter_t
*iter)
   iter->state = RIB_TABLES_ITER_S_DONE;
 }

+#define VRF_FOREACH_TABLE(vrf_id, table, afi, safi)\
+  struct zebra_vrf *zvrf = vrf_info_lookup (vrf_id);\
+  (table) = ((struct
route_table_info*)vector_lookup((zvrf)->route_tables_info,
0))->table[afi][safi];\
+  for(int i = 0; i < vector_count((zvrf)->route_tables_info);\
+     (table) = ((struct
route_table_info*)vector_lookup((zvrf)->route_tables_info,
i))->table[afi][safi], \
+     i++)
+
+#define ZVRF_FOREACH_TABLE(zvrf, table, afi, safi)\
+  (table) = ((struct
route_table_info*)vector_lookup((zvrf)->route_tables_info,
0))->table[afi][safi];\
+  for(int i = 0; i < vector_count((zvrf)->route_tables_info);\
+     (table) = ((struct
route_table_info*)vector_lookup((zvrf)->route_tables_info,
i))->table[afi][safi], \
+     i++)
+
+#define ZVRF_FOREACH_RTINFO(zvrf)\
+  struct route_table_info *rt_info =
vector_lookup((zvrf)->route_tables_info, 0);\
+  for(int i = 0; i < vector_count((zvrf)->route_tables_info);\
+     (rt_info) = vector_lookup((zvrf)->route_tables_info, i), \
+     i++)
 #endif /*_ZEBRA_RIB_H */
diff --git a/zebra/test_main.c b/zebra/test_main.c
index 448d1ef..a705a20 100644
--- a/zebra/test_main.c
+++ b/zebra/test_main.c
@@ -233,11 +233,12 @@ zebra_vrf_disable (vrf_id_t vrf_id, void
**info)
   struct zebra_vrf *zvrf = (struct zebra_vrf *) (*info);
   struct listnode *list_node;
   struct interface *ifp;
+  struct route_table_info *rt_info = get_route_table_info(zvrf,
RT_TABLE_MAIN);

   assert (zvrf);

-  rib_close_table (zvrf->table[AFI_IP][SAFI_UNICAST]);
-  rib_close_table (zvrf->table[AFI_IP6][SAFI_UNICAST]);
+  rib_close_table (rt_info->table[AFI_IP][SAFI_UNICAST]);
+  rib_close_table (rt_info->table[AFI_IP6][SAFI_UNICAST]);

   for (ALL_LIST_ELEMENTS_RO (vrf_iflist (vrf_id), list_node, ifp))
     {
diff --git a/zebra/zebra_rib.c b/zebra/zebra_rib.c
index 38357ff..9bcb7ec 100644
--- a/zebra/zebra_rib.c
+++ b/zebra/zebra_rib.c
@@ -1810,9 +1810,16 @@ rib_add_ipv4 (int type, int flags, struct
prefix_ipv4 *p,
   struct nexthop *nexthop;

   /* Lookup table.  */
-  table = zebra_vrf_table (AFI_IP, safi, vrf_id);
+  table = zebra_vrf_table_id(AFI_IP, safi, vrf_id, table_id);
   if (! table)
-    return 0;
+  {
+    struct zebra_vrf *zvrf = vrf_info_lookup (vrf_id);
+    if (!zvrf)
+      return NULL;
+
+    zebra_route_tables_create(zvrf, table_id);
+    table = zebra_vrf_table_id(AFI_IP, safi, vrf_id, table_id);
+  }

   /* Make it sure prefixlen is applied to the prefix. */
   apply_mask_ipv4 (p);
@@ -2286,9 +2293,16 @@ static_install_route (afi_t afi, safi_t
safi, struct prefix *p, struct static_ro
   struct route_table *table;

   /* Lookup table.  */
-  table = zebra_vrf_table (afi, safi, si->vrf_id);
+  table = zebra_vrf_table_id(afi, safi, si->vrf_id,
zebrad.rtm_table_default);
   if (! table)
-    return;
+  {
+    struct zebra_vrf *zvrf = vrf_info_lookup (si->vrf_id);
+    if (!zvrf)
+      return NULL;
+
+    zebra_route_tables_create(zvrf, zebrad.rtm_table_default);
+    table = zebra_vrf_table_id(afi, safi, si->vrf_id,
zebrad.rtm_table_default);
+  }

   /* Lookup existing route */
   rn = route_node_get (table, p);
@@ -2474,7 +2488,15 @@ static_add_ipv4_safi (safi_t safi, struct
prefix *p, struct in_addr *gate,
   struct static_route *cp;
   struct static_route *update = NULL;
   struct zebra_vrf *zvrf = vrf_info_get (vrf_id);
-  struct route_table *stable = zvrf->stable[AFI_IP][safi];
+  struct route_table_info *rt_info = get_route_table_info(
+          zvrf, zebrad.rtm_table_default);
+  if (! rt_info)
+  {
+    zebra_route_tables_create(zvrf, zebrad.rtm_table_default);
+    rt_info = get_route_table_info(
+          zvrf, zebrad.rtm_table_default);
+  }
+  struct route_table *stable = rt_info->stable[AFI_IP][safi];

   if (! stable)
     return -1;
@@ -2868,7 +2890,15 @@ static_add_ipv6 (struct prefix *p, u_char
type, struct in6_addr *gate,
   struct static_route *cp;
   struct static_route *update = NULL;
   struct zebra_vrf *zvrf = vrf_info_get (vrf_id);
-  struct route_table *stable = zvrf->stable[AFI_IP6][SAFI_UNICAST];
+  struct route_table_info *rt_info = get_route_table_info(
+          zvrf, zebrad.rtm_table_default);
+  if (! rt_info)
+  {
+    zebra_route_tables_create(zvrf, zebrad.rtm_table_default);
+    rt_info = get_route_table_info(
+          zvrf, zebrad.rtm_table_default);
+  }
+  struct route_table *stable =
rt_info->stable[AFI_IP6][SAFI_UNICAST];

   if (! stable)
     return -1;
@@ -3028,7 +3058,7 @@ rib_update (vrf_id_t vrf_id)

 /* Remove all routes which comes from non main table.  */
 static void
-rib_weed_table (struct route_table *table)
+rib_weed_table (struct route_table *table, int table_id)
 {
   struct route_node *rn;
   struct rib *rib;
@@ -3042,7 +3072,8 @@ rib_weed_table (struct route_table *table)
         continue;

       if (rib->table != zebrad.rtm_table_default &&
-          rib->table != RT_TABLE_MAIN)
+          rib->table != RT_TABLE_MAIN &&
+          rib->table != table_id)
             rib_delnode (rn, rib);
     }
 }
@@ -3053,12 +3084,19 @@ rib_weed_tables (void)
 {
   vrf_iter_t iter;
   struct zebra_vrf *zvrf;
+  struct route_table_info *rt_info;

   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]);
+        for (int i=0; i < vector_count(zvrf->route_tables_info);
i++)
+        {
+          rt_info = vector_lookup(zvrf->route_tables_info, i);
+          rib_weed_table (rt_info->table[AFI_IP][SAFI_UNICAST],
+                  rt_info->table_id);
+          rib_weed_table (rt_info->table[AFI_IP6][SAFI_UNICAST],
+                  rt_info->table_id);
+        }
       }
 }

@@ -3100,8 +3138,11 @@ rib_sweep_route (void)
   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]);
+        struct route_table_info *rt_info =
get_route_table_info(zvrf, RT_TABLE_MAIN);
+        rib_weed_table (rt_info->table[AFI_IP][SAFI_UNICAST],
+                rt_info->table_id);
+        rib_weed_table (rt_info->table[AFI_IP6][SAFI_UNICAST],
+                rt_info->table_id);
       }
 }

@@ -3140,8 +3181,11 @@ rib_score_proto (u_char proto)

   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]);
+    {
+      struct route_table_info *rt_info =
get_route_table_info(zvrf, RT_TABLE_MAIN);
+      cnt += rib_score_proto_table (proto,
rt_info->table[AFI_IP][SAFI_UNICAST])
+            +rib_score_proto_table (proto,
rt_info->table[AFI_IP6][SAFI_UNICAST]);
+    }

   return cnt;
 }
@@ -3175,12 +3219,17 @@ rib_close (void)
 {
   vrf_iter_t iter;
   struct zebra_vrf *zvrf;
+  struct route_table_info *rt_info;

   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]);
+        for (int i=0; i < vector_count(zvrf->route_tables_info);
i++)
+        {
+          rt_info = vector_lookup(zvrf->route_tables_info, i);
+          rib_close_table (rt_info->table[AFI_IP][SAFI_UNICAST]);
+          rib_close_table (rt_info->table[AFI_IP6][SAFI_UNICAST]);
+        }
       }
 }

@@ -3302,15 +3351,15 @@ rib_tables_iter_next (rib_tables_iter_t
*iter)
  * Create a routing table for the specific AFI/SAFI in the given
VRF.
  */
 static void
-zebra_vrf_table_create (struct zebra_vrf *zvrf, afi_t afi, safi_t
safi)
+zebra_vrf_table_create (struct zebra_vrf *zvrf, struct
route_table_info *rt_info, afi_t afi, safi_t safi)
 {
   rib_table_info_t *info;
   struct route_table *table;

-  assert (!zvrf->table[afi][safi]);
+  assert (!rt_info->table[afi][safi]);

   table = route_table_init ();
-  zvrf->table[afi][safi] = table;
+  rt_info->table[afi][safi] = table;

   info = XCALLOC (MTYPE_RIB_TABLE_INFO, sizeof (*info));
   info->zvrf = zvrf;
@@ -3324,21 +3373,14 @@ struct zebra_vrf *
 zebra_vrf_alloc (vrf_id_t vrf_id)
 {
   struct zebra_vrf *zvrf;
+  struct route_table_info *rt_info;
 #ifdef HAVE_NETLINK
   char nl_name[64];
 #endif

   zvrf = XCALLOC (MTYPE_ZEBRA_VRF, sizeof (struct zebra_vrf));

-  /* Allocate routing table and static table.  */
-  zebra_vrf_table_create (zvrf, AFI_IP, SAFI_UNICAST);
-  zebra_vrf_table_create (zvrf, AFI_IP6, SAFI_UNICAST);
-  zvrf->stable[AFI_IP][SAFI_UNICAST] = route_table_init ();
-  zvrf->stable[AFI_IP6][SAFI_UNICAST] = route_table_init ();
-  zebra_vrf_table_create (zvrf, AFI_IP, SAFI_MULTICAST);
-  zebra_vrf_table_create (zvrf, AFI_IP6, SAFI_MULTICAST);
-  zvrf->stable[AFI_IP][SAFI_MULTICAST] = route_table_init ();
-  zvrf->stable[AFI_IP6][SAFI_MULTICAST] = route_table_init ();
+  init_zebra_route_tables_info(zvrf);

   /* Set VRF ID */
   zvrf->vrf_id = vrf_id;
@@ -3369,9 +3411,40 @@ zebra_vrf_table (afi_t afi, safi_t safi,
vrf_id_t vrf_id)
   if (afi >= AFI_MAX || safi >= SAFI_MAX)
     return NULL;

-  return zvrf->table[afi][safi];
+  struct route_table_info * rt_info = get_route_table_info(zvrf,
RT_TABLE_MAIN);
+
+  return rt_info->table[afi][safi];
 }

+/* Lookup the routing table in an enabled VRF. */
+struct route_table *
+zebra_vrf_table_id (afi_t afi, safi_t safi, vrf_id_t vrf_id, int
table_id)
+{
+  struct zebra_vrf *zvrf = vrf_info_lookup (vrf_id);
+
+  if (!zvrf)
+    return NULL;
+
+  if (afi >= AFI_MAX || safi >= SAFI_MAX)
+    return NULL;
+
+  struct route_table_info * rt_info = get_route_table_info(zvrf,
table_id);
+  if (rt_info)
+    return rt_info->table[afi][safi];
+}
+
+struct route_table_info *
+get_route_table_info(struct zebra_vrf *zvrf, int table_id)
+{
+  struct route_table_info* rt_info;
+  for (int i=0; i < vector_count(zvrf->route_tables_info); i++)
+  {
+    rt_info = vector_lookup(zvrf->route_tables_info, i);
+    if (rt_info->table_id == table_id)
+      return rt_info;
+  }
+  return NULL;
+}
 /* Lookup the static routing table in a VRF. */
 struct route_table *
 zebra_vrf_static_table (afi_t afi, safi_t safi, vrf_id_t vrf_id)
@@ -3384,6 +3457,40 @@ zebra_vrf_static_table (afi_t afi, safi_t
safi, vrf_id_t vrf_id)
   if (afi >= AFI_MAX || safi >= SAFI_MAX)
     return NULL;

-  return zvrf->stable[afi][safi];
+  struct route_table_info *rt_info = get_route_table_info(zvrf,
RT_TABLE_MAIN);
+  return rt_info->stable[afi][safi];
 }

+void
+init_zebra_route_tables_info(struct zebra_vrf *zvrf)
+{
+  zvrf->route_tables_info = vector_init(1);
+  struct route_table_info *rt_info = malloc (sizeof(struct
route_table_info));
+  rt_info->table_id = RT_TABLE_MAIN;
+
+  init_zebra_route_table(zvrf, rt_info);
+  vector_set_index (zvrf->route_tables_info, 0, rt_info);
+}
+
+void
+zebra_route_tables_create(struct zebra_vrf *zvrf, int table_id)
+{
+  struct route_table_info *rt_info =  malloc (sizeof(struct
route_table_info));
+  rt_info->table_id = table_id;
+  init_zebra_route_table(zvrf, rt_info);
+  vector_set_index (zvrf->route_tables_info,
vector_count(zvrf->route_tables_info), rt_info);
+}
+
+void
+init_zebra_route_table(struct zebra_vrf *zvrf, struct
route_table_info *rt_info)
+{
+  /* Allocate routing table and static table.  */
+  zebra_vrf_table_create (zvrf, rt_info, AFI_IP, SAFI_UNICAST);
+  zebra_vrf_table_create (zvrf, rt_info, AFI_IP6, SAFI_UNICAST);
+  rt_info->stable[AFI_IP][SAFI_UNICAST] = route_table_init ();
+  rt_info->stable[AFI_IP6][SAFI_UNICAST] = route_table_init ();
+  zebra_vrf_table_create (zvrf, rt_info, AFI_IP, SAFI_MULTICAST);
+  zebra_vrf_table_create (zvrf, rt_info, AFI_IP6, SAFI_MULTICAST);
+  rt_info->stable[AFI_IP][SAFI_MULTICAST] = route_table_init ();
+  rt_info->stable[AFI_IP6][SAFI_MULTICAST] = route_table_init ();
+}
diff --git a/zebra/zebra_vty.c b/zebra/zebra_vty.c
index 656f55d..5369212 100644
--- a/zebra/zebra_vty.c
+++ b/zebra/zebra_vty.c
@@ -404,8 +404,11 @@ DEFUN (show_ip_rpf_vrf_all,

   for (iter = vrf_first (); iter != VRF_ITER_INVALID; iter =
vrf_next (iter))
     {
+      zvrf = vrf_iter2info (iter);
+      ZVRF_FOREACH_RTINFO(zvrf)
+      {
       if ((zvrf = vrf_iter2info (iter)) == NULL ||
-          (table = zvrf->table[AFI_IP][SAFI_MULTICAST]) == NULL)
+          (table = rt_info->table[AFI_IP][SAFI_MULTICAST]) == NULL)
         continue;

       /* Show all IPv4 routes. */
@@ -419,6 +422,7 @@ DEFUN (show_ip_rpf_vrf_all,
               }
             vty_show_ip_route (vty, rn, rib);
           }
+      }
     }

   return CMD_SUCCESS;
@@ -1579,21 +1583,24 @@ static int do_show_ip_route(struct vty
*vty, safi_t safi, vrf_id_t vrf_id)
   struct rib *rib;
   int first = 1;

-  table = zebra_vrf_table (AFI_IP, safi, vrf_id);
+
+  VRF_FOREACH_TABLE(vrf_id, table, AFI_IP, safi)
+  {
   if (! table)
-    return CMD_SUCCESS;
+    continue;

   /* Show all IPv4 routes. */
   for (rn = route_top (table); rn; rn = route_next (rn))
     RNODE_FOREACH_RIB (rn, rib)
       {
-    if (first)
-      {
-        vty_out (vty, SHOW_ROUTE_V4_HEADER);
-        first = 0;
-      }
-    vty_show_ip_route (vty, rn, rib);
+    if (first)
+      {
+        vty_out (vty, SHOW_ROUTE_V4_HEADER);
+        first = 0;
       }
+    vty_show_ip_route (vty, rn, rib);
+      }
+  }
   return CMD_SUCCESS;
 }

@@ -1632,9 +1639,10 @@ DEFUN (show_ip_route_prefix_longer,
   if (argc > 1)
     VTY_GET_INTEGER ("VRF ID", vrf_id, argv[1]);

-  table = zebra_vrf_table (AFI_IP, SAFI_UNICAST, vrf_id);
+  VRF_FOREACH_TABLE(vrf_id, table, AFI_IP, SAFI_UNICAST)
+  {
   if (! table)
-    return CMD_SUCCESS;
+    continue;

   /* Show matched type IPv4 routes. */
   for (rn = route_top (table); rn; rn = route_next (rn))
@@ -1648,6 +1656,7 @@ DEFUN (show_ip_route_prefix_longer,
         }
       vty_show_ip_route (vty, rn, rib);
     }
+  }
   return CMD_SUCCESS;
 }

@@ -1679,9 +1688,10 @@ DEFUN (show_ip_route_supernets,
   if (argc > 0)
     VTY_GET_INTEGER ("VRF ID", vrf_id, argv[0]);

-  table = zebra_vrf_table (AFI_IP, SAFI_UNICAST, vrf_id);
+  VRF_FOREACH_TABLE(vrf_id, table, AFI_IP, SAFI_UNICAST)
+  {
   if (! table)
-    return CMD_SUCCESS;
+    continue;

   /* Show matched type IPv4 routes. */
   for (rn = route_top (table); rn; rn = route_next (rn))
@@ -1701,6 +1711,7 @@ DEFUN (show_ip_route_supernets,
         vty_show_ip_route (vty, rn, rib);
       }
       }
+  }
   return CMD_SUCCESS;
 }

@@ -1738,9 +1749,10 @@ DEFUN (show_ip_route_protocol,
   if (argc > 1)
     VTY_GET_INTEGER ("VRF ID", vrf_id, argv[1]);

-  table = zebra_vrf_table (AFI_IP, SAFI_UNICAST, vrf_id);
+  VRF_FOREACH_TABLE(vrf_id, table, AFI_IP, SAFI_UNICAST)
+  {
   if (! table)
-    return CMD_SUCCESS;
+    continue;

   /* Show matched type IPv4 routes. */
   for (rn = route_top (table); rn; rn = route_next (rn))
@@ -1754,6 +1766,7 @@ DEFUN (show_ip_route_protocol,
         }
       vty_show_ip_route (vty, rn, rib);
     }
+  }
   return CMD_SUCCESS;
 }

@@ -1790,9 +1803,10 @@ DEFUN (show_ip_route_addr,
   if (argc > 1)
     VTY_GET_INTEGER ("VRF ID", vrf_id, argv[1]);

-  table = zebra_vrf_table (AFI_IP, SAFI_UNICAST, vrf_id);
+  VRF_FOREACH_TABLE(vrf_id, table, AFI_IP, SAFI_UNICAST)
+  {
   if (! table)
-    return CMD_SUCCESS;
+    continue;

   rn = route_node_match (table, (struct prefix *) &p);
   if (! rn)
@@ -1804,6 +1818,7 @@ DEFUN (show_ip_route_addr,
   vty_show_ip_route_detail (vty, rn, 0);

   route_unlock_node (rn);
+  }

   return CMD_SUCCESS;
 }
@@ -1841,9 +1856,10 @@ DEFUN (show_ip_route_prefix,
   if (argc > 1)
     VTY_GET_INTEGER ("VRF ID", vrf_id, argv[1]);

-  table = zebra_vrf_table (AFI_IP, SAFI_UNICAST, vrf_id);
+  VRF_FOREACH_TABLE(vrf_id, table, AFI_IP, SAFI_UNICAST)
+  {
   if (! table)
-    return CMD_SUCCESS;
+    continue;

   rn = route_node_match (table, (struct prefix *) &p);
   if (! rn || rn->p.prefixlen != p.prefixlen)
@@ -1857,6 +1873,7 @@ DEFUN (show_ip_route_prefix,
   vty_show_ip_route_detail (vty, rn, 0);

   route_unlock_node (rn);
+  }

   return CMD_SUCCESS;
 }
@@ -2033,12 +2050,14 @@ DEFUN (show_ip_route_summary,
   if (argc > 0)
     VTY_GET_INTEGER ("VRF ID", vrf_id, argv[0]);

-  table = zebra_vrf_table (AFI_IP, SAFI_UNICAST, vrf_id);
+  VRF_FOREACH_TABLE(vrf_id, table, AFI_IP, SAFI_UNICAST)
+  {
   if (! table)
-    return CMD_SUCCESS;
+    continue;

   vty_show_ip_route_summary (vty, table);

+  }
   return CMD_SUCCESS;
 }

@@ -2067,11 +2086,13 @@ DEFUN (show_ip_route_summary_prefix,
   if (argc > 0)
     VTY_GET_INTEGER ("VRF ID", vrf_id, argv[0]);

-  table = zebra_vrf_table (AFI_IP, SAFI_UNICAST, vrf_id);
+  VRF_FOREACH_TABLE(vrf_id, table, AFI_IP, SAFI_UNICAST)
+  {
   if (! table)
-    return CMD_SUCCESS;
+    continue;

   vty_show_ip_route_summary_prefix (vty, table);
+  }

   return CMD_SUCCESS;
 }
@@ -2103,8 +2124,11 @@ DEFUN (show_ip_route_vrf_all,

   for (iter = vrf_first (); iter != VRF_ITER_INVALID; iter =
vrf_next (iter))
     {
+      zvrf = vrf_iter2info (iter);
+      ZVRF_FOREACH_RTINFO(zvrf)
+      {
       if ((zvrf = vrf_iter2info (iter)) == NULL ||
-          (table = zvrf->table[AFI_IP][SAFI_UNICAST]) == NULL)
+          (table = rt_info->table[AFI_IP][SAFI_UNICAST]) == NULL)
         continue;

       /* Show all IPv4 routes. */
@@ -2118,6 +2142,7 @@ DEFUN (show_ip_route_vrf_all,
               }
             vty_show_ip_route (vty, rn, rib);
           }
+      }
     }

   return CMD_SUCCESS;
@@ -2151,8 +2176,11 @@ DEFUN (show_ip_route_prefix_longer_vrf_all,

   for (iter = vrf_first (); iter != VRF_ITER_INVALID; iter =
vrf_next (iter))
     {
+      zvrf = vrf_iter2info (iter);
+      ZVRF_FOREACH_RTINFO(zvrf)
+      {
       if ((zvrf = vrf_iter2info (iter)) == NULL ||
-          (table = zvrf->table[AFI_IP][SAFI_UNICAST]) == NULL)
+          (table = rt_info->table[AFI_IP][SAFI_UNICAST]) == NULL)
         continue;

       /* Show matched type IPv4 routes. */
@@ -2167,6 +2195,7 @@ DEFUN (show_ip_route_prefix_longer_vrf_all,
                 }
               vty_show_ip_route (vty, rn, rib);
             }
+      }
     }

   return CMD_SUCCESS;
@@ -2191,8 +2220,11 @@ DEFUN (show_ip_route_supernets_vrf_all,

   for (iter = vrf_first (); iter != VRF_ITER_INVALID; iter =
vrf_next (iter))
     {
+      zvrf = vrf_iter2info (iter);
+      ZVRF_FOREACH_RTINFO(zvrf)
+      {
       if ((zvrf = vrf_iter2info (iter)) == NULL ||
-          (table = zvrf->table[AFI_IP][SAFI_UNICAST]) == NULL)
+          (table = rt_info->table[AFI_IP][SAFI_UNICAST]) == NULL)
         continue;

       /* Show matched type IPv4 routes. */
@@ -2213,6 +2245,7 @@ DEFUN (show_ip_route_supernets_vrf_all,
                 vty_show_ip_route (vty, rn, rib);
               }
           }
+      }
     }

   return CMD_SUCCESS;
@@ -2244,8 +2277,11 @@ DEFUN (show_ip_route_protocol_vrf_all,

   for (iter = vrf_first (); iter != VRF_ITER_INVALID; iter =
vrf_next (iter))
     {
+      zvrf = vrf_iter2info (iter);
+      ZVRF_FOREACH_RTINFO(zvrf)
+      {
       if ((zvrf = vrf_iter2info (iter)) == NULL ||
-          (table = zvrf->table[AFI_IP][SAFI_UNICAST]) == NULL)
+          (table = rt_info->table[AFI_IP][SAFI_UNICAST]) == NULL)
         continue;

       /* Show matched type IPv4 routes. */
@@ -2260,6 +2296,7 @@ DEFUN (show_ip_route_protocol_vrf_all,
                 }
               vty_show_ip_route (vty, rn, rib);
             }
+      }
     }

   return CMD_SUCCESS;
@@ -2290,8 +2327,11 @@ DEFUN (show_ip_route_addr_vrf_all,

   for (iter = vrf_first (); iter != VRF_ITER_INVALID; iter =
vrf_next (iter))
     {
+      zvrf = vrf_iter2info (iter);
+      ZVRF_FOREACH_RTINFO(zvrf)
+      {
       if ((zvrf = vrf_iter2info (iter)) == NULL ||
-          (table = zvrf->table[AFI_IP][SAFI_UNICAST]) == NULL)
+          (table = rt_info->table[AFI_IP][SAFI_UNICAST]) == NULL)
         continue;

       rn = route_node_match (table, (struct prefix *) &p);
@@ -2302,6 +2342,7 @@ DEFUN (show_ip_route_addr_vrf_all,

       route_unlock_node (rn);
     }
+    }

   return CMD_SUCCESS;
 }
@@ -2331,8 +2372,11 @@ DEFUN (show_ip_route_prefix_vrf_all,

   for (iter = vrf_first (); iter != VRF_ITER_INVALID; iter =
vrf_next (iter))
     {
+      zvrf = vrf_iter2info (iter);
+      ZVRF_FOREACH_RTINFO(zvrf)
+      {
       if ((zvrf = vrf_iter2info (iter)) == NULL ||
-          (table = zvrf->table[AFI_IP][SAFI_UNICAST]) == NULL)
+          (table = rt_info->table[AFI_IP][SAFI_UNICAST]) == NULL)
         continue;

       rn = route_node_match (table, (struct prefix *) &p);
@@ -2348,6 +2392,7 @@ DEFUN (show_ip_route_prefix_vrf_all,

       route_unlock_node (rn);
     }
+    }

   return CMD_SUCCESS;
 }
@@ -2366,7 +2411,12 @@ DEFUN (show_ip_route_summary_vrf_all,

   for (iter = vrf_first (); iter != VRF_ITER_INVALID; iter =
vrf_next (iter))
     if ((zvrf = vrf_iter2info (iter)) != NULL)
-      vty_show_ip_route_summary (vty,
zvrf->table[AFI_IP][SAFI_UNICAST]);
+    {
+      ZVRF_FOREACH_RTINFO(zvrf)
+      {
+      vty_show_ip_route_summary (vty,
rt_info->table[AFI_IP][SAFI_UNICAST]);
+      }
+    }

   return CMD_SUCCESS;
 }
@@ -2386,7 +2436,12 @@ DEFUN (show_ip_route_summary_prefix_vrf_all,

   for (iter = vrf_first (); iter != VRF_ITER_INVALID; iter =
vrf_next (iter))
     if ((zvrf = vrf_iter2info (iter)) != NULL)
-      vty_show_ip_route_summary_prefix (vty,
zvrf->table[AFI_IP][SAFI_UNICAST]);
+    {
+      ZVRF_FOREACH_RTINFO(zvrf)
+      {
+      vty_show_ip_route_summary_prefix (vty,
rt_info->table[AFI_IP][SAFI_UNICAST]);
+      }
+    }

   return CMD_SUCCESS;
 }
@@ -2406,8 +2461,11 @@ static_config_ipv4 (struct vty *vty, safi_t
safi, const char *cmd)

   for (iter = vrf_first (); iter != VRF_ITER_INVALID; iter =
vrf_next (iter))
     {
+      zvrf = vrf_iter2info (iter);
+      ZVRF_FOREACH_RTINFO(zvrf)
+      {
       if ((zvrf = vrf_iter2info (iter)) == NULL ||
-          (stable = zvrf->stable[AFI_IP][safi]) == NULL)
+          (stable = rt_info->stable[AFI_IP][safi]) == NULL)
         continue;

       for (rn = route_top (stable); rn; rn = route_next (rn))
@@ -2449,6 +2507,7 @@ static_config_ipv4 (struct vty *vty, safi_t
safi, const char *cmd)

             write = 1;
           }
+      }
     }
   return write;
 }
@@ -3072,9 +3131,10 @@ DEFUN (show_ipv6_route,
   if (argc > 0)
     VTY_GET_INTEGER ("VRF ID", vrf_id, argv[0]);

-  table = zebra_vrf_table (AFI_IP6, SAFI_UNICAST, vrf_id);
+  VRF_FOREACH_TABLE(vrf_id, table, AFI_IP6, SAFI_UNICAST)
+  {
   if (! table)
-    return CMD_SUCCESS;
+    continue;

   /* Show all IPv6 route. */
   for (rn = route_top (table); rn; rn = route_next (rn))
@@ -3087,6 +3147,7 @@ DEFUN (show_ipv6_route,
       }
     vty_show_ip_route (vty, rn, rib);
       }
+  }
   return CMD_SUCCESS;
 }

@@ -3125,9 +3186,10 @@ DEFUN (show_ipv6_route_prefix_longer,
   if (argc > 1)
     VTY_GET_INTEGER ("VRF ID", vrf_id, argv[1]);

-  table = zebra_vrf_table (AFI_IP6, SAFI_UNICAST, vrf_id);
+  VRF_FOREACH_TABLE(vrf_id, table, AFI_IP6, SAFI_UNICAST)
+  {
   if (! table)
-    return CMD_SUCCESS;
+    continue;

   /* Show matched type IPv6 routes. */
   for (rn = route_top (table); rn; rn = route_next (rn))
@@ -3141,6 +3203,7 @@ DEFUN (show_ipv6_route_prefix_longer,
         }
       vty_show_ip_route (vty, rn, rib);
     }
+  }
   return CMD_SUCCESS;
 }

@@ -3179,9 +3242,10 @@ DEFUN (show_ipv6_route_protocol,
   if (argc > 1)
     VTY_GET_INTEGER ("VRF ID", vrf_id, argv[1]);

-  table = zebra_vrf_table (AFI_IP6, SAFI_UNICAST, vrf_id);
+  VRF_FOREACH_TABLE(vrf_id, table, AFI_IP6, SAFI_UNICAST)
+  {
   if (! table)
-    return CMD_SUCCESS;
+    continue;

   /* Show matched type IPv6 routes. */
   for (rn = route_top (table); rn; rn = route_next (rn))
@@ -3195,6 +3259,7 @@ DEFUN (show_ipv6_route_protocol,
         }
       vty_show_ip_route (vty, rn, rib);
     }
+  }
   return CMD_SUCCESS;
 }

@@ -3231,9 +3296,10 @@ DEFUN (show_ipv6_route_addr,
   if (argc > 1)
     VTY_GET_INTEGER ("VRF ID", vrf_id, argv[1]);

-  table = zebra_vrf_table (AFI_IP6, SAFI_UNICAST, vrf_id);
+  VRF_FOREACH_TABLE(vrf_id, table, AFI_IP6, SAFI_UNICAST)
+  {
   if (! table)
-    return CMD_SUCCESS;
+    continue;

   rn = route_node_match (table, (struct prefix *) &p);
   if (! rn)
@@ -3246,6 +3312,7 @@ DEFUN (show_ipv6_route_addr,

   route_unlock_node (rn);

+  }
   return CMD_SUCCESS;
 }

@@ -3282,9 +3349,10 @@ DEFUN (show_ipv6_route_prefix,
   if (argc > 1)
     VTY_GET_INTEGER ("VRF ID", vrf_id, argv[1]);

-  table = zebra_vrf_table (AFI_IP6, SAFI_UNICAST, vrf_id);
+  VRF_FOREACH_TABLE(vrf_id, table, AFI_IP6, SAFI_UNICAST)
+  {
   if (! table)
-    return CMD_SUCCESS;
+    continue;

   rn = route_node_match (table, (struct prefix *) &p);
   if (! rn || rn->p.prefixlen != p.prefixlen)
@@ -3298,6 +3366,7 @@ DEFUN (show_ipv6_route_prefix,
   vty_show_ip_route_detail (vty, rn, 0);

   route_unlock_node (rn);
+  }

   return CMD_SUCCESS;
 }
@@ -3326,12 +3395,13 @@ DEFUN (show_ipv6_route_summary,
   if (argc > 0)
     VTY_GET_INTEGER ("VRF ID", vrf_id, argv[0]);

-  table = zebra_vrf_table (AFI_IP6, SAFI_UNICAST, vrf_id);
+  VRF_FOREACH_TABLE(vrf_id, table, AFI_IP6, SAFI_UNICAST)
+  {
   if (! table)
-    return CMD_SUCCESS;
+    continue;

   vty_show_ip_route_summary (vty, table);
-
+  }
   return CMD_SUCCESS;
 }

@@ -3360,11 +3430,13 @@ DEFUN (show_ipv6_route_summary_prefix,
   if (argc > 0)
     VTY_GET_INTEGER ("VRF ID", vrf_id, argv[0]);

-  table = zebra_vrf_table (AFI_IP6, SAFI_UNICAST, vrf_id);
+  VRF_FOREACH_TABLE(vrf_id, table, AFI_IP6, SAFI_UNICAST)
+  {
   if (! table)
-    return CMD_SUCCESS;
+    continue;

   vty_show_ip_route_summary_prefix (vty, table);
+  }

   return CMD_SUCCESS;
 }
@@ -3400,14 +3472,14 @@ DEFUN (show_ipv6_mroute,
   if (argc > 0)
     VTY_GET_INTEGER ("VRF ID", vrf_id, argv[0]);

-  table = zebra_vrf_table (AFI_IP6, SAFI_MULTICAST, vrf_id);
+  VRF_FOREACH_TABLE(vrf_id, table, AFI_IP6, SAFI_MULTICAST)
+  {
   if (! table)
-    return CMD_SUCCESS;
+    continue;

   /* Show all IPv6 route. */
   for (rn = route_top (table); rn; rn = route_next (rn))
-    RNODE_FOREACH_RIB (rn, rib)
-      {
+    RNODE_FOREACH_RIB (rn, rib) {
        if (first)
          {
        vty_out (vty, SHOW_ROUTE_V6_HEADER);
@@ -3415,6 +3487,7 @@ DEFUN (show_ipv6_mroute,
          }
        vty_show_ip_route (vty, rn, rib);
       }
+  }
   return CMD_SUCCESS;
 }

@@ -3443,8 +3516,11 @@ DEFUN (show_ipv6_route_vrf_all,

   for (iter = vrf_first (); iter != VRF_ITER_INVALID; iter =
vrf_next (iter))
     {
+      zvrf = vrf_iter2info (iter);
+      ZVRF_FOREACH_RTINFO(zvrf)
+      {
       if ((zvrf = vrf_iter2info (iter)) == NULL ||
-          (table = zvrf->table[AFI_IP6][SAFI_UNICAST]) == NULL)
+          (table = rt_info->table[AFI_IP6][SAFI_UNICAST]) == NULL)
         continue;

       /* Show all IPv6 route. */
@@ -3458,6 +3534,7 @@ DEFUN (show_ipv6_route_vrf_all,
               }
             vty_show_ip_route (vty, rn, rib);
           }
+      }
     }

   return CMD_SUCCESS;
@@ -3491,8 +3568,11 @@ DEFUN (show_ipv6_route_prefix_longer_vrf_all,

   for (iter = vrf_first (); iter != VRF_ITER_INVALID; iter =
vrf_next (iter))
     {
+      zvrf = vrf_iter2info (iter);
+      ZVRF_FOREACH_RTINFO(zvrf)
+      {
       if ((zvrf = vrf_iter2info (iter)) == NULL ||
-          (table = zvrf->table[AFI_IP6][SAFI_UNICAST]) == NULL)
+          (table = rt_info->table[AFI_IP6][SAFI_UNICAST]) == NULL)
         continue;

       /* Show matched type IPv6 routes. */
@@ -3507,6 +3587,7 @@ DEFUN (show_ipv6_route_prefix_longer_vrf_all,
                 }
               vty_show_ip_route (vty, rn, rib);
             }
+      }
     }

   return CMD_SUCCESS;
@@ -3538,8 +3619,11 @@ DEFUN (show_ipv6_route_protocol_vrf_all,

   for (iter = vrf_first (); iter != VRF_ITER_INVALID; iter =
vrf_next (iter))
     {
+      zvrf = vrf_iter2info (iter);
+      ZVRF_FOREACH_RTINFO(zvrf)
+      {
       if ((zvrf = vrf_iter2info (iter)) == NULL ||
-          (table = zvrf->table[AFI_IP6][SAFI_UNICAST]) == NULL)
+          (table = rt_info->table[AFI_IP6][SAFI_UNICAST]) == NULL)
         continue;

       /* Show matched type IPv6 routes. */
@@ -3554,6 +3638,7 @@ DEFUN (show_ipv6_route_protocol_vrf_all,
                 }
               vty_show_ip_route (vty, rn, rib);
             }
+      }
     }

   return CMD_SUCCESS;
@@ -3584,8 +3669,11 @@ DEFUN (show_ipv6_route_addr_vrf_all,

   for (iter = vrf_first (); iter != VRF_ITER_INVALID; iter =
vrf_next (iter))
     {
+      zvrf = vrf_iter2info (iter);
+      ZVRF_FOREACH_RTINFO(zvrf)
+      {
       if ((zvrf = vrf_iter2info (iter)) == NULL ||
-          (table = zvrf->table[AFI_IP6][SAFI_UNICAST]) == NULL)
+          (table = rt_info->table[AFI_IP6][SAFI_UNICAST]) == NULL)
         continue;

       rn = route_node_match (table, (struct prefix *) &p);
@@ -3596,6 +3684,7 @@ DEFUN (show_ipv6_route_addr_vrf_all,

       route_unlock_node (rn);
     }
+    }

   return CMD_SUCCESS;
 }
@@ -3625,8 +3714,11 @@ DEFUN (show_ipv6_route_prefix_vrf_all,

   for (iter = vrf_first (); iter != VRF_ITER_INVALID; iter =
vrf_next (iter))
     {
+      zvrf = vrf_iter2info (iter);
+      ZVRF_FOREACH_RTINFO(zvrf)
+      {
       if ((zvrf = vrf_iter2info (iter)) == NULL ||
-          (table = zvrf->table[AFI_IP6][SAFI_UNICAST]) == NULL)
+          (table = rt_info->table[AFI_IP6][SAFI_UNICAST]) == NULL)
         continue;

       rn = route_node_match (table, (struct prefix *) &p);
@@ -3642,6 +3734,7 @@ DEFUN (show_ipv6_route_prefix_vrf_all,

       route_unlock_node (rn);
     }
+    }

   return CMD_SUCCESS;
 }
@@ -3660,8 +3753,14 @@ DEFUN (show_ipv6_route_summary_vrf_all,
   vrf_iter_t iter;

   for (iter = vrf_first (); iter != VRF_ITER_INVALID; iter =
vrf_next (iter))
+  {
+      zvrf = vrf_iter2info (iter);
+    ZVRF_FOREACH_RTINFO(zvrf)
+    {
     if ((zvrf = vrf_iter2info (iter)) != NULL)
-      vty_show_ip_route_summary (vty,
zvrf->table[AFI_IP6][SAFI_UNICAST]);
+      vty_show_ip_route_summary (vty,
rt_info->table[AFI_IP6][SAFI_UNICAST]);
+    }
+  }

   return CMD_SUCCESS;
 }
@@ -3683,8 +3782,11 @@ DEFUN (show_ipv6_mroute_vrf_all,

   for (iter = vrf_first (); iter != VRF_ITER_INVALID; iter =
vrf_next (iter))
     {
+      zvrf = vrf_iter2info (iter);
+      ZVRF_FOREACH_RTINFO(zvrf)
+      {
       if ((zvrf = vrf_iter2info (iter)) == NULL ||
-          (table = zvrf->table[AFI_IP6][SAFI_UNICAST]) == NULL)
+          (table = rt_info->table[AFI_IP6][SAFI_UNICAST]) == NULL)
         continue;

       /* Show all IPv6 route. */
@@ -3698,6 +3800,7 @@ DEFUN (show_ipv6_mroute_vrf_all,
              }
            vty_show_ip_route (vty, rn, rib);
           }
+      }
     }
   return CMD_SUCCESS;
 }
@@ -3717,7 +3820,12 @@ DEFUN
(show_ipv6_route_summary_prefix_vrf_all,

   for (iter = vrf_first (); iter != VRF_ITER_INVALID; iter =
vrf_next (iter))
     if ((zvrf = vrf_iter2info (iter)) != NULL)
-      vty_show_ip_route_summary_prefix (vty,
zvrf->table[AFI_IP6][SAFI_UNICAST]);
+    {
+    ZVRF_FOREACH_RTINFO(zvrf)
+    {
+      vty_show_ip_route_summary_prefix (vty,
rt_info->table[AFI_IP6][SAFI_UNICAST]);
+    }
+    }

   return CMD_SUCCESS;
 }
@@ -3738,8 +3846,11 @@ static_config_ipv6 (struct vty *vty)

   for (iter = vrf_first (); iter != VRF_ITER_INVALID; iter =
vrf_next (iter))
     {
+      zvrf = vrf_iter2info (iter);
+      ZVRF_FOREACH_RTINFO(zvrf)
+      {
       if ((zvrf = vrf_iter2info (iter)) == NULL ||
-          (stable = zvrf->stable[AFI_IP6][SAFI_UNICAST]) == NULL)
+          (stable = rt_info->stable[AFI_IP6][SAFI_UNICAST]) ==
NULL)
         continue;

       for (rn = route_top (stable); rn; rn = route_next (rn))
@@ -3779,6 +3890,7 @@ static_config_ipv6 (struct vty *vty)

             write = 1;
           }
+      }
     }
   return write;
 }


2016-01-07 21:56 GMT+08:00 Donald Sharp <sha...@cumulusnetworks.com
:

Comments inline...


On Thu, Jan 7, 2016 at 8:09 AM, 林守磊 <linxiu...@gmail.com> wrote:

diff --git a/lib/table.h b/lib/table.h
index ab357a0..946fcb2 100644
--- a/lib/table.h
+++ b/lib/table.h
@@ -53,6 +53,7 @@ struct route_table_delegate_t_
 struct route_table
 {
   struct route_node *top;
+  int tableno;

   /*
    * Delegate that performs certain functions for this table.
diff --git a/zebra/rib.h b/zebra/rib.h
index d3a83c6..78df691 100644
--- a/zebra/rib.h
+++ b/zebra/rib.h
@@ -577,4 +577,24 @@ rib_tables_iter_cleanup (rib_tables_iter_t
*iter)
   iter->state = RIB_TABLES_ITER_S_DONE;
 }

+typedef enum { false, true } bool;


irrespective of whether or not we want to introduce true/false to
the code it does not belong in zebra/rib.h.
I would prefer just returning 0/1 and using that instead of
true/false enum's.  Unless someone would be willing to retrofit the
entirety of the code base.


+struct route_table_iter;
+
+struct route_table_iter
+{
+    struct route_table_iter *pre;
+    struct route_table_iter *next;
+    struct route_table *route_table;
+};
+
+int vrf_create(int tableno);
+bool vrf_tableno_exists(int tableno);
+int get_table_count();
+


vrf_create is a poorly named function imo, it should fit in with
the current code in quagga..  There is already a zebra_vrf_alloc() and
zebra_vrf_table_create().  The code you are working on needs to work in the
confines of those functions.  Possibly you are working on an old code base?


+#define VRF_FOREACH_TABLE(afi, safi, table)      \
+  (table) = vrf_table((afi), (safi), 0);\
+  for (int i = 0, j = get_table_count();\
+    i < j;\
+    i++, (table) = vrf_table((afi), (safi), i))
+
 #endif /*_ZEBRA_RIB_H */
diff --git a/zebra/rt_netlink.c b/zebra/rt_netlink.c
index 95a82fd..e94c47e 100644
--- a/zebra/rt_netlink.c
+++ b/zebra/rt_netlink.c
@@ -685,6 +685,7 @@ netlink_routing_table (struct sockaddr_nl
*snl, struct nlmsghdr *h)
     return 0;

   table = rtm->rtm_table;
+  vrf_create(table);


I don't think that this is the concern of netlink_routing_table.
It should be passing the route to zebra_rib.c and zebra_rib.c should do the
right thing with it.


 #if 0                           /* we weed them out later in
rib_weed_tables () */
   if (table != RT_TABLE_MAIN && table !=
zebrad.rtm_table_default)
     return 0;
diff --git a/zebra/zebra_rib.c b/zebra/zebra_rib.c
index dc7e1ca..e00cf83 100644
--- a/zebra/zebra_rib.c
+++ b/zebra/zebra_rib.c
@@ -122,6 +122,39 @@ vrf_alloc (const char *name)
   return vrf;
 }

+static struct vrf*
+vrf_alloc_tableno(const char *name, int tableno)
+{
+  struct vrf *vrf;
+  vrf = vrf_alloc(name);
+
+  vrf->stable[AFI_IP][SAFI_UNICAST]->tableno = tableno;
+  vrf->stable[AFI_IP6][SAFI_UNICAST]->tableno = tableno;
+  vrf->stable[AFI_IP][SAFI_MULTICAST]->tableno = tableno;
+  vrf->stable[AFI_IP6][SAFI_MULTICAST]->tableno = tableno;
+
+  vrf->table[AFI_IP][SAFI_UNICAST]->tableno = tableno;
+  vrf->table[AFI_IP6][SAFI_UNICAST]->tableno = tableno;
+  vrf->table[AFI_IP][SAFI_MULTICAST]->tableno = tableno;
+  vrf->table[AFI_IP6][SAFI_MULTICAST]->tableno = tableno;
+  return vrf;
+}



Again this sure looks like code that is already in the latest
master.  Are you working off of it?


+
+int
+get_vrfid_by_tableno(afi_t afi, safi_t safi, int tableno)
+{
+  if (tableno == 0 || tableno == RT_TABLE_MAIN)
+      return 0;
+
+  struct route_table *table;
+  for (int i = 0; i < vector_count(vrf_vector); i++)
+  {
+    table = vrf_table(afi, safi, i);
+    if (table->tableno == tableno)
+        return i;
+  }
+  return -1;
+}
 /* Lookup VRF by identifier.  */
 struct vrf *
 vrf_lookup (u_int32_t id)
@@ -136,7 +169,7 @@ vrf_init (void)
   struct vrf *default_table;

   /* Allocate VRF vector.  */
-  vrf_vector = vector_init (1);
+  vrf_vector = vector_init (2);

   /* Allocate default main table.  */
   default_table = vrf_alloc ("Default-IP-Routing-Table");
@@ -145,6 +178,43 @@ vrf_init (void)
   vector_set_index (vrf_vector, 0, default_table);
 }

+int
+get_table_count()
+{
+  return vector_count(vrf_vector);
+}
+
+int
+vrf_create(int tableno)
+{
+  if (vrf_tableno_exists(tableno))
+  {
+      return -1;
+  }
+
+  unsigned int table_nums = vector_count(vrf_vector);
+  struct vrf *table;
+  char tablename[40];
+  sprintf(tablename, "%d-IP-Routing-Table", tableno);
+  table = vrf_alloc_tableno (tablename, tableno);
+  vector_set_index (vrf_vector, table_nums, table);
+}
+
+bool
+vrf_tableno_exists(int tableno)
+{
+  if (tableno == 0 || tableno == RT_TABLE_MAIN)
+      return true;
+
+  struct route_table *table;
+  VRF_FOREACH_TABLE(AFI_IP, SAFI_UNICAST, table)
+  {
+    if (table->tableno == tableno)
+        return true;
+  }
+  return false;
+}
+
 /* Lookup route table.  */
 struct route_table *
 vrf_table (afi_t afi, safi_t safi, u_int32_t id)
@@ -484,7 +554,6 @@ nexthop_active_ipv4 (struct rib *rib, struct
nexthop *nexthop, int set,
           newhop = match->nexthop;
           if (newhop && nexthop->type == NEXTHOP_TYPE_IPV4)
         nexthop->ifindex = newhop->ifindex;
-


Whitespace change?


           return 1;
         }
       else if (CHECK_FLAG (rib->flags, ZEBRA_FLAG_INTERNAL))
@@ -1033,7 +1102,7 @@ nexthop_active_check (struct route_node
*rn, struct rib *rib,
   if (RIB_SYSTEM_ROUTE(rib) ||
       (family == AFI_IP && rn->p.family != AF_INET) ||
       (family == AFI_IP6 && rn->p.family != AF_INET6))
-    return CHECK_FLAG (nexthop->flags, NEXTHOP_FLAG_ACTIVE);
+  return CHECK_FLAG (nexthop->flags, NEXTHOP_FLAG_ACTIVE);


Whitespace change?



   /* The original code didn't determine the family correctly
    * e.g. for NEXTHOP_TYPE_IFINDEX. Retrieve the correct afi
@@ -1059,6 +1128,12 @@ nexthop_active_check (struct route_node
*rn, struct rib *rib,
   return CHECK_FLAG (nexthop->flags, NEXTHOP_FLAG_ACTIVE);
 }

+void
+print_rib(struct route_node *rn)
+{
+  char buf[INET6_ADDRSTRLEN];
+  inet_ntop (rn->p.family, &rn->p.u.prefix, buf, sizeof (buf));
+}


This function doesn't do anything with the output of inet_ntop,
just remove?


 /* Iterate over all nexthops of the given RIB entry and refresh
their
  * ACTIVE flag. rib->nexthop_active_num is updated accordingly.
If any
  * nexthop is found to toggle the ACTIVE flag, the whole rib
structure
@@ -1082,7 +1157,7 @@ nexthop_active_update (struct route_node
*rn, struct rib *rib, int set)
     prev_active = CHECK_FLAG (nexthop->flags,
NEXTHOP_FLAG_ACTIVE);
     prev_index = nexthop->ifindex;
     if ((new_active = nexthop_active_check (rn, rib, nexthop,
set)))
-      rib->nexthop_active_num++;
+    rib->nexthop_active_num++;


whitespace change?


     if (prev_active != new_active ||
     prev_index != nexthop->ifindex)
       SET_FLAG (rib->flags, ZEBRA_FLAG_CHANGED);
@@ -1255,6 +1330,7 @@ rib_process (struct route_node *rn)
   if (IS_ZEBRA_DEBUG_RIB || IS_ZEBRA_DEBUG_RIB_Q)
     inet_ntop (rn->p.family, &rn->p.u.prefix, buf,
INET6_ADDRSTRLEN);

+  inet_ntop (rn->p.family, &rn->p.u.prefix, buf,
INET6_ADDRSTRLEN);


Why the addition of this line? The exact same thing is done above
but protected by the DEBUG guards.


   RNODE_FOREACH_RIB_SAFE (rn, rib, next)
     {
       /* Currently installed rib. */
@@ -1815,8 +1891,15 @@ rib_add_ipv4 (int type, int flags, struct
prefix_ipv4 *p,
   struct route_node *rn;
   struct nexthop *nexthop;

+  int id;
+  // in this case vrf_id is the real tableno
+  // and id is the vector index
+  id = get_vrfid_by_tableno(AFI_IP, safi, vrf_id);
+  assert(id >= 0);
+


Let's name our variables appropriately here and consistent with
the rest of the code base.


+
   /* Lookup table.  */
-  table = vrf_table (AFI_IP, safi, 0);
+  table = vrf_table (AFI_IP, safi, id);
   if (! table)
     return 0;

@@ -2154,8 +2237,10 @@ rib_delete_ipv4 (int type, int flags,
struct prefix_ipv4 *p,
   char buf1[INET_ADDRSTRLEN];
   char buf2[INET_ADDRSTRLEN];

+  int id;
+  id = get_vrfid_by_tableno(AFI_IP, safi, vrf_id);
   /* Lookup table.  */
-  table = vrf_table (AFI_IP, safi, 0);
+  table = vrf_table (AFI_IP, safi, id);
   if (! table)
     return 0;

@@ -2292,10 +2377,25 @@ static_install_ipv4 (struct prefix *p,
struct static_ipv4 *si)
   struct route_node *rn;
   struct route_table *table;

-  /* Lookup table.  */
-  table = vrf_table (AFI_IP, SAFI_UNICAST, 0);
+  VRF_FOREACH_TABLE(AFI_IP, SAFI_UNICAST, table)
+  {
   if (! table)
-    return;
+  {
+    continue;
+  }
+
+  if ((zebrad.rtm_table_default == 0 || zebrad.rtm_table_default
== RT_TABLE_MAIN) && \
+         (table->tableno == 0 || table->tableno ==
RT_TABLE_MAIN) ) {
+    ;
+  }
+  else if (table->tableno == zebrad.rtm_table_default)
+  {
+    ;
+  }
+  else
+  {
+    continue;
+  }

   /* Lookup existing route */
   rn = route_node_get (table, p);
@@ -2357,6 +2457,7 @@ static_install_ipv4 (struct prefix *p,
struct static_ipv4 *si)
       /* Link this rib to the tree. */
       rib_addnode (rn, rib);
     }
+  }
 }

 static int
@@ -2450,11 +2551,14 @@ static_add_ipv4 (struct prefix *p, struct
in_addr *gate, const char *ifname,
   struct static_ipv4 *update = NULL;
   struct route_table *stable;

+  // ignore vrf_id, because it is always zero. And it sucks
+  vrf_id = get_vrfid_by_tableno(AFI_IP, SAFI_UNICAST,
zebrad.rtm_table_default);
+  assert(vrf_id >= 0);
+
   /* Lookup table.  */
   stable = vrf_static_table (AFI_IP, SAFI_UNICAST, vrf_id);
   if (! stable)
     return -1;
-
   /* Lookup static route prefix. */
   rn = route_node_get (stable, p);

@@ -2630,8 +2734,10 @@ rib_add_ipv6 (int type, int flags, struct
prefix_ipv6 *p,
   struct route_node *rn;
   struct nexthop *nexthop;

+  int id;
+  id = get_vrfid_by_tableno(AFI_IP6, safi, vrf_id);


again, can we name the variables a bit better?


In any event, I would highly suggest respinning your code with the
latest Quagga, this version is old and won't work properly with the current
code base.

donald

   /* Lookup table.  */
-  table = vrf_table (AFI_IP6, safi, 0);
+  table = vrf_table (AFI_IP6, safi, id);
   if (! table)
     return 0;

@@ -2745,8 +2851,10 @@ rib_delete_ipv6 (int type, int flags,
struct prefix_ipv6 *p,
   /* Apply mask. */
   apply_mask_ipv6 (p);

+  int id;
+  id = get_vrfid_by_tableno(AFI_IP6, safi, vrf_id);
   /* Lookup table.  */
-  table = vrf_table (AFI_IP6, safi, 0);
+  table = vrf_table (AFI_IP6, safi, id);
   if (! table)
     return 0;

@@ -3163,17 +3271,21 @@ rib_update (void)
   struct route_node *rn;
   struct route_table *table;

-  table = vrf_table (AFI_IP, SAFI_UNICAST, 0);
+  VRF_FOREACH_TABLE(AFI_IP, SAFI_UNICAST, table)
+  {
   if (table)
     for (rn = route_top (table); rn; rn = route_next (rn))
       if (rnode_to_ribs (rn))
         rib_queue_add (&zebrad, rn);
+  }

-  table = vrf_table (AFI_IP6, SAFI_UNICAST, 0);
+  VRF_FOREACH_TABLE(AFI_IP6, SAFI_UNICAST, table)
+  {
   if (table)
     for (rn = route_top (table); rn; rn = route_next (rn))
       if (rnode_to_ribs (rn))
         rib_queue_add (&zebrad, rn);
+  }
 }


@@ -3193,8 +3305,9 @@ rib_weed_table (struct route_table *table)
         continue;

       if (rib->table != zebrad.rtm_table_default &&
-          rib->table != RT_TABLE_MAIN)
-            rib_delnode (rn, rib);
+          rib->table != RT_TABLE_MAIN &&
+          rib->table != 0)
+        rib_delnode (rn, rib);
     }
 }

@@ -3298,8 +3411,11 @@ rib_close_table (struct route_table *table)
 void
 rib_close (void)
 {
-  rib_close_table (vrf_table (AFI_IP, SAFI_UNICAST, 0));
-  rib_close_table (vrf_table (AFI_IP6, SAFI_UNICAST, 0));
+  for (int i = 0; i < vector_count(vrf_vector); i++)
+  {
+    rib_close_table (vrf_table (AFI_IP, SAFI_UNICAST, i));
+    rib_close_table (vrf_table (AFI_IP6, SAFI_UNICAST, i));
+  }
 }

 /* Routing information base initialize. */
diff --git a/zebra/zebra_vty.c b/zebra/zebra_vty.c
index baa60db..df3b353 100644
--- a/zebra/zebra_vty.c
+++ b/zebra/zebra_vty.c
@@ -777,6 +777,7 @@ vty_show_ip_route (struct vty *vty, struct
route_node *rn, struct rib *rib)
              tm->tm_yday/7,
              tm->tm_yday - ((tm->tm_yday/7) * 7), tm->tm_hour);
     }
+      //vty_out (vty, ", tableno %d", rib->table);


Dead code, please remove..


       vty_out (vty, "%s", VTY_NEWLINE);
     }
 }
@@ -793,9 +794,10 @@ DEFUN (show_ip_route,
   struct rib *rib;
   int first = 1;

-  table = vrf_table (AFI_IP, SAFI_UNICAST, 0);
+  VRF_FOREACH_TABLE(AFI_IP, SAFI_UNICAST, table)
+  {
   if (! table)
-    return CMD_SUCCESS;
+    continue;

   /* Show all IPv4 routes. */
   for (rn = route_top (table); rn; rn = route_next (rn))
@@ -808,6 +810,7 @@ DEFUN (show_ip_route,
       }
     vty_show_ip_route (vty, rn, rib);
       }
+  }
   return CMD_SUCCESS;
 }

@@ -834,9 +837,10 @@ DEFUN (show_ip_route_prefix_longer,
       return CMD_WARNING;
     }

-  table = vrf_table (AFI_IP, SAFI_UNICAST, 0);
+  VRF_FOREACH_TABLE(AFI_IP, SAFI_UNICAST, table)
+  {
   if (! table)
-    return CMD_SUCCESS;
+    continue;

   /* Show matched type IPv4 routes. */
   for (rn = route_top (table); rn; rn = route_next (rn))
@@ -850,6 +854,7 @@ DEFUN (show_ip_route_prefix_longer,
         }
       vty_show_ip_route (vty, rn, rib);
     }
+  }
   return CMD_SUCCESS;
 }

@@ -867,9 +872,10 @@ DEFUN (show_ip_route_supernets,
   u_int32_t addr;
   int first = 1;

-  table = vrf_table (AFI_IP, SAFI_UNICAST, 0);
+  VRF_FOREACH_TABLE(AFI_IP, SAFI_UNICAST, table)
+  {
   if (! table)
-    return CMD_SUCCESS;
+    continue;

   /* Show matched type IPv4 routes. */
   for (rn = route_top (table); rn; rn = route_next (rn))
@@ -889,6 +895,7 @@ DEFUN (show_ip_route_supernets,
         vty_show_ip_route (vty, rn, rib);
       }
       }
+  }
   return CMD_SUCCESS;
 }

@@ -913,9 +920,10 @@ DEFUN (show_ip_route_protocol,
       return CMD_WARNING;
     }

-  table = vrf_table (AFI_IP, SAFI_UNICAST, 0);
+  VRF_FOREACH_TABLE(AFI_IP, SAFI_UNICAST, table)
+  {
   if (! table)
-    return CMD_SUCCESS;
+    continue;

   /* Show matched type IPv4 routes. */
   for (rn = route_top (table); rn; rn = route_next (rn))
@@ -929,6 +937,7 @@ DEFUN (show_ip_route_protocol,
         }
       vty_show_ip_route (vty, rn, rib);
     }
+  }
   return CMD_SUCCESS;
 }

@@ -952,9 +961,10 @@ DEFUN (show_ip_route_addr,
       return CMD_WARNING;
     }

-  table = vrf_table (AFI_IP, SAFI_UNICAST, 0);
+  VRF_FOREACH_TABLE(AFI_IP, SAFI_UNICAST, table)
+  {
   if (! table)
-    return CMD_SUCCESS;
+    continue;

   rn = route_node_match (table, (struct prefix *) &p);
   if (! rn)
@@ -967,6 +977,7 @@ DEFUN (show_ip_route_addr,

   route_unlock_node (rn);

+  }
   return CMD_SUCCESS;
 }

@@ -990,9 +1001,10 @@ DEFUN (show_ip_route_prefix,
       return CMD_WARNING;
     }

-  table = vrf_table (AFI_IP, SAFI_UNICAST, 0);
+  VRF_FOREACH_TABLE(AFI_IP, SAFI_UNICAST, table)
+  {
   if (! table)
-    return CMD_SUCCESS;
+    continue;

   rn = route_node_match (table, (struct prefix *) &p);
   if (! rn || rn->p.prefixlen != p.prefixlen)
@@ -1005,6 +1017,7 @@ DEFUN (show_ip_route_prefix,

   route_unlock_node (rn);

+  }
   return CMD_SUCCESS;
 }

@@ -1083,12 +1096,14 @@ DEFUN (show_ip_route_summary,
 {
   struct route_table *table;

-  table = vrf_table (AFI_IP, SAFI_UNICAST, 0);
+  VRF_FOREACH_TABLE(AFI_IP, SAFI_UNICAST, table)
+  {
   if (! table)
-    return CMD_SUCCESS;
+    continue;

   vty_show_ip_route_summary (vty, table);

+  }
   return CMD_SUCCESS;
 }

@@ -1192,9 +1207,10 @@ DEFUN (show_ip_mroute,
   struct rib *rib;
   int first = 1;

-  table = vrf_table (AFI_IP, SAFI_MULTICAST, 0);
+  VRF_FOREACH_TABLE(AFI_IP, SAFI_MULTICAST, table)
+  {
   if (! table)
-    return CMD_SUCCESS;
+    continue;

   /* Show all IPv4 routes. */
   for (rn = route_top (table); rn; rn = route_next (rn))
@@ -1207,6 +1223,7 @@ DEFUN (show_ip_mroute,
          }
        vty_show_ip_route (vty, rn, rib);
       }
+  }
   return CMD_SUCCESS;
 }

@@ -1731,9 +1748,10 @@ DEFUN (show_ipv6_route,
   struct rib *rib;
   int first = 1;

-  table = vrf_table (AFI_IP6, SAFI_UNICAST, 0);
+  VRF_FOREACH_TABLE(AFI_IP6, SAFI_UNICAST, table)
+  {
   if (! table)
-    return CMD_SUCCESS;
+    continue;

   /* Show all IPv6 route. */
   for (rn = route_top (table); rn; rn = route_next (rn))
@@ -1746,6 +1764,7 @@ DEFUN (show_ipv6_route,
       }
     vty_show_ipv6_route (vty, rn, rib);
       }
+  }
   return CMD_SUCCESS;
 }

@@ -1765,9 +1784,10 @@ DEFUN (show_ipv6_route_prefix_longer,
   int ret;
   int first = 1;

-  table = vrf_table (AFI_IP6, SAFI_UNICAST, 0);
+  VRF_FOREACH_TABLE(AFI_IP6, SAFI_UNICAST, table)
+  {
   if (! table)
-    return CMD_SUCCESS;
+    continue;

   ret = str2prefix (argv[0], &p);
   if (! ret)
@@ -1788,6 +1808,7 @@ DEFUN (show_ipv6_route_prefix_longer,
         }
       vty_show_ipv6_route (vty, rn, rib);
     }
+  }
   return CMD_SUCCESS;
 }

@@ -1812,9 +1833,10 @@ DEFUN (show_ipv6_route_protocol,
       return CMD_WARNING;
     }

-  table = vrf_table (AFI_IP6, SAFI_UNICAST, 0);
+  VRF_FOREACH_TABLE(AFI_IP6, SAFI_UNICAST, table)
+  {
   if (! table)
-    return CMD_SUCCESS;
+    continue;

   /* Show matched type IPv6 routes. */
   for (rn = route_top (table); rn; rn = route_next (rn))
@@ -1828,6 +1850,7 @@ DEFUN (show_ipv6_route_protocol,
         }
       vty_show_ipv6_route (vty, rn, rib);
     }
+  }
   return CMD_SUCCESS;
 }

@@ -1851,20 +1874,22 @@ DEFUN (show_ipv6_route_addr,
       return CMD_WARNING;
     }

-  table = vrf_table (AFI_IP6, SAFI_UNICAST, 0);
+  VRF_FOREACH_TABLE(AFI_IP6, SAFI_UNICAST, table)
+  {
   if (! table)
-    return CMD_SUCCESS;
+    continue;

   rn = route_node_match (table, (struct prefix *) &p);
   if (! rn)
     {
       vty_out (vty, "%% Network not in table%s", VTY_NEWLINE);
-      return CMD_WARNING;
+      continue;
     }

   vty_show_ipv6_route_detail (vty, rn);

   route_unlock_node (rn);
+  }

   return CMD_SUCCESS;
 }
@@ -1889,21 +1914,22 @@ DEFUN (show_ipv6_route_prefix,
       return CMD_WARNING;
     }

-  table = vrf_table (AFI_IP6, SAFI_UNICAST, 0);
+  VRF_FOREACH_TABLE(AFI_IP6, SAFI_UNICAST, table)
+  {
   if (! table)
-    return CMD_SUCCESS;
+    continue;

   rn = route_node_match (table, (struct prefix *) &p);
   if (! rn || rn->p.prefixlen != p.prefixlen)
     {
       vty_out (vty, "%% Network not in table%s", VTY_NEWLINE);
-      return CMD_WARNING;
+      continue;
     }

   vty_show_ipv6_route_detail (vty, rn);

   route_unlock_node (rn);
-
+  }
   return CMD_SUCCESS;
 }

@@ -1918,12 +1944,14 @@ DEFUN (show_ipv6_route_summary,
 {
   struct route_table *table;

-  table = vrf_table (AFI_IP6, SAFI_UNICAST, 0);
+  VRF_FOREACH_TABLE(AFI_IP6, SAFI_UNICAST, table)
+  {
   if (! table)
-    return CMD_SUCCESS;
+    continue;

   vty_show_ip_route_summary (vty, table);

+  }
   return CMD_SUCCESS;
 }

@@ -1944,9 +1972,10 @@ DEFUN (show_ipv6_mroute,
   struct rib *rib;
   int first = 1;

-  table = vrf_table (AFI_IP6, SAFI_MULTICAST, 0);
+  VRF_FOREACH_TABLE(AFI_IP6, SAFI_MULTICAST, table)
+  {
   if (! table)
-    return CMD_SUCCESS;
+    continue;

   /* Show all IPv6 route. */
   for (rn = route_top (table); rn; rn = route_next (rn))
@@ -1959,6 +1988,7 @@ DEFUN (show_ipv6_mroute,
          }
        vty_show_ipv6_route (vty, rn, rib);
       }
+  }
   return CMD_SUCCESS;
 }

diff --git a/zebra/zserv.c b/zebra/zserv.c
index ca17c2c..97048b1 100644
--- a/zebra/zserv.c
+++ b/zebra/zserv.c
@@ -1577,7 +1577,12 @@ DEFUN (config_table,
        "Configure target kernel routing table\n"
        "TABLE integer\n")
 {
-  zebrad.rtm_table_default = strtol (argv[0], (char**)0, 10);
+  int tableno;
+  tableno = strtol (argv[0], (char**)0, 10);
+  zebrad.rtm_table_default = tableno;
+  if (!vrf_tableno_exists(tableno)){
+    vrf_create(tableno);
+  }
   return CMD_SUCCESS;
 }



2015-12-31 17:56 GMT+08:00 林守磊 <linxiu...@gmail.com>:

Hi All
   I use zebra in my production environment, but found that
command table was not good as I thounght..And I found someone got the same
problem just like me.
http://www.gossamer-threads.com/lists/quagga/users/23301

At last, I had to fix problems in below by myself

1. At first, it can not inject a route to non-default route
table which is already in default route

2. It can not define multiple route tables

The patch(perfect_cmd_table.patch) is tested.

Example zebra.conf like

table 100
ip route 11.0.0.0/8 10.97.215.247
ip route 172.16.0.0/12 10.97.215.247
!
table 101
ip route 11.0.0.0/8 10.97.215.247
ip route 172.16.0.0/12 10.97.215.247
ip route 10.0.0.0/8 10.97.215.247
ip route 100.64.0.0/10 10.97.215.247
!

Forwarding Your Reply.

Regards



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













--
Paul Jakma      p...@jakma.org  @pjakma Key ID: 64A2FF6A
Fortune:
Those who can't write, write manuals.
_______________________________________________
Quagga-dev mailing list
Quagga-dev@lists.quagga.net
https://lists.quagga.net/mailman/listinfo/quagga-dev

Reply via email to