2005-10-01 Andrew J. Schorr <ajschorr@alumni.princeton.edu>

	* zebra.h: Declare new functions zebra_route_string() and
	  zebra_route_char().
	* log.c: (zroute_lookup,zebra_route_string,zebra_route_char) New
	  functions to map zebra route numbers to strings.
	* zebra_vty.c: (route_type_str) Remove obsolete function: use new
	  library function zebra_route_string() instead.  Note that there
	  are a few differences: for IPv6 routes, we now get "ripng" and
	  "ospf6" instead of the old behavior ("rip" and "ospf").
	  (route_type_char) Remove obsolete function: ues new library function
	  zebra_route_char() instead.  Note that there is one difference:
	  the old function returned 'S' for a ZEBRA_ROUTE_SYSTEM route,
	  whereas the new one returns 'X'.
	  (vty_show_ip_route_detail,vty_show_ipv6_route_detail) Replace
	  route_type_str() with zebra_route_string().
	  (vty_show_ip_route,vty_show_ipv6_route) Replace route_type_char()
	  with zebra_route_char().
	* bgp_vty.c: (bgp_config_write_redistribute) Use new library function
	  zebra_route_string instead of a local hard-coded table.
	* ospf6_asbr.c: Remove local hard-coded tables zroute_name and
	  zroute_abname. Change the ZROUTE_NAME macro to use new library
	  function zebra_route_string().  Remove the ZROUTE_ABNAME macro.
	  (ospf6_asbr_external_route_show): Replace ZROUTE_ABNAME() with
	  a call to zebra_route_char(), and be sure to fix the format string,
	  since we now have a char instead of a char *.
	* ospf6_zebra.c: Remove local hard-coded tables zebra_route_name and
	  zebra_route_abname.  Note that the zebra_route_name[] table
	  contained mixed-case strings, whereas the zebra_route_string()
	  function returns lower-case strings.
	  (ospf6_zebra_read_ipv6): Change debug message to use new library
	  function zebra_route_string() instead of zebra_route_name[].
	  (show_zebra): Use new library function zebra_route_string() instead
	  of zebra_route_name[].
	* ospf_dump.c: Remove local hard-coded table ospf_redistributed_proto.
	  (ospf_redist_string) New function implemented using new library
	  function zebra_route_string().  Note that there are a few differences
	  in the output that will result: the new function returns strings
	  that are lower-case, whereas the old table was mixed case.  Also,
	  the old table mapped ZEBRA_ROUTE_OSPF6 to "OSPFv3", whereas the
	  new function returns "ospf6".
	* ospfd.h: Remove extern struct message ospf_redistributed_proto[],
	  and add extern const char *ospf_redist_string(u_int route_type)
	  instead.
	* ospf_asbr.c: (ospf_external_info_add) In two messages, use
	  ospf_redist_string instead of LOOKUP(ospf_redistributed_proto).
	* ospf_vty.c: Remove local hard-coded table distribute_str.
	  (config_write_ospf_redistribute,config_write_ospf_distribute): Use
	  new library function zebra_route_string() instead of distribute_str[].
	* ospf_zebra.c: (ospf_redistribute_set,ospf_redistribute_unset,
	  ospf_redistribute_default_set,ospf_redistribute_check)
	  In debug messages, use ospf_redist_string() instead of
	  LOOKUP(ospf_redistributed_proto).
	* rip_zebra.c: (config_write_rip_redistribute): Remove local hard-coded
	  table str[]. Replace str[] with calls to new library function
	  zebra_route_string().
	* ripd.c: Remove local hard-coded table route_info[].
	  (show_ip_rip) Replace uses of str[] with calls to new library
	  functions zebra_route_char and zebra_route_string.
	* ripng_zebra.c: (ripng_redistribute_write) Remove local hard-coded
	  table str[].  Replace str[i] with new library function
	  zebra_route_string(i).
	* ripngd.c: Remove local hard-coded table route_info[].
	  (show_ipv6_ripng) Use new library function zebra_route_char() instead
	  of table route_info[].
diff --git a/bgpd/ChangeLog b/bgpd/ChangeLog
index 9dc1adc..d83c345 100644
--- a/bgpd/ChangeLog
+++ b/bgpd/ChangeLog
@@ -1,3 +1,8 @@
+2005-10-01 Andrew J. Schorr <ajschorr@alumni.princeton.edu>
+
+	* bgp_vty.c: (bgp_config_write_redistribute) Use new library function
+	  zebra_route_string instead of a local hard-coded table.
+
 2005-09-30 Vincent Jardin <vincent.jardin@6wind.com>
 
 	* bgp_packet.c: fix compilation when DEBUG is used.
diff --git a/bgpd/bgp_vty.c b/bgpd/bgp_vty.c
index 685ea28..c8d5b2a 100644
--- a/bgpd/bgp_vty.c
+++ b/bgpd/bgp_vty.c
@@ -8510,8 +8510,6 @@
 			       safi_t safi, int *write)
 {
   int i;
-  const char *str[] = { "system", "kernel", "connected", "static", "rip",
-		  "ripng", "ospf", "ospf6", "isis", "bgp"};
 
   /* Unicast redistribution only.  */
   if (safi != SAFI_UNICAST)
@@ -8526,7 +8524,7 @@
 	  bgp_config_write_family_header (vty, afi, safi, write);
 
 	  /* "redistribute" configuration.  */
-	  vty_out (vty, " redistribute %s", str[i]);
+	  vty_out (vty, " redistribute %s", zebra_route_string(i));
 
 	  if (bgp->redist_metric_flag[afi][i])
 	    vty_out (vty, " metric %d", bgp->redist_metric[afi][i]);
diff --git a/lib/ChangeLog b/lib/ChangeLog
index fd3feff..956b10e 100644
--- a/lib/ChangeLog
+++ b/lib/ChangeLog
@@ -1,3 +1,10 @@
+2005-10-01 Andrew J. Schorr <ajschorr@alumni.princeton.edu>
+
+	* zebra.h: Declare new functions zebra_route_string() and
+	  zebra_route_char().
+	* log.c: (zroute_lookup,zebra_route_string,zebra_route_char) New
+	  functions to map zebra route numbers to strings.
+
 2005-09-29 Alain Ritoux <alain.ritoux@6wind.com>
 
 	* smux.[ch]: allow to retreive global OID (identified by <0
diff --git a/lib/log.c b/lib/log.c
index 2c4b399..6748dbc 100644
--- a/lib/log.c
+++ b/lib/log.c
@@ -1,5 +1,5 @@
 /*
- * $Id: log.c,v 1.25 2005/02/03 19:22:05 ajs Exp $
+ * $Id: log.c,v 1.26 2005/10/01 17:38:07 ajs Exp $
  *
  * Logging of zebra
  * Copyright (C) 1997, 1998, 1999 Kunihiro Ishiguro
@@ -703,3 +703,60 @@
   const char *s = strerror(errnum);
   return (s != NULL) ? s : "Unknown error";
 }
+
+/* Note: this table must match the ordering in lib/zebra.h */
+static const struct zebra_route_desc {
+  u_int zroute;
+  const char *string;
+  char chr;
+} route_types[] = {
+  { ZEBRA_ROUTE_SYSTEM, "system", 'X' },
+  { ZEBRA_ROUTE_KERNEL, "kernel", 'K' },
+  { ZEBRA_ROUTE_CONNECT, "connected", 'C' },
+  { ZEBRA_ROUTE_STATIC, "static", 'S' },
+  { ZEBRA_ROUTE_RIP, "rip", 'R' },
+  { ZEBRA_ROUTE_RIPNG, "ripng", 'R' },
+  { ZEBRA_ROUTE_OSPF, "ospf", 'O' },
+  { ZEBRA_ROUTE_OSPF6, "ospf6", 'O' },
+  { ZEBRA_ROUTE_ISIS, "isis", 'I' },
+  { ZEBRA_ROUTE_BGP, "bgp", 'B' },
+  { ZEBRA_ROUTE_HSLS, "hsls", 'H' },
+};
+
+static const struct zebra_route_desc *
+zroute_lookup(u_int zroute)
+{
+  static const struct zebra_route_desc unknown = { 0, "unknown", '?' };
+  u_int i;
+
+  if (zroute >= sizeof(route_types)/sizeof(route_types[0]))
+    {
+      zlog_err("unknown zebra route type: %u", zroute);
+      return &unknown;
+    }
+  if (zroute == route_types[zroute].zroute)
+    return &route_types[zroute];
+  for (i = 0; i < sizeof(route_types)/sizeof(route_types[0]); i++)
+    {
+      if (zroute == route_types[i].zroute)
+        {
+	  zlog_warn("internal error: route type table out of order "
+		    "while searching for %u, please notify developers", zroute);
+	  return &route_types[i];
+        }
+    }
+  zlog_err("internal error: cannot find route type %u in table!", zroute);
+  return &unknown;
+}
+
+const char *
+zebra_route_string(u_int zroute)
+{
+  return zroute_lookup(zroute)->string;
+}
+
+char
+zebra_route_char(u_int zroute)
+{
+  return zroute_lookup(zroute)->chr;
+}
diff --git a/lib/zebra.h b/lib/zebra.h
index 03af70d..88f1625 100644
--- a/lib/zebra.h
+++ b/lib/zebra.h
@@ -391,6 +391,14 @@
 #define ZEBRA_ROUTE_HSLS		 10
 #define ZEBRA_ROUTE_MAX                  11
 
+/* Note: whenever a new route type is added (or the numbering is changed),
+   the route_types[] table in lib/log.c must be updated! */
+
+/* Map a route type to a string.  For example, ZEBRA_ROUTE_RIPNG -> "ripng". */
+extern const char *zebra_route_string(u_int route_type);
+/* Map a route type to a char.  For example, ZEBRA_ROUTE_RIPNG -> 'R'. */
+extern char zebra_route_char(u_int route_type);
+
 /* Zebra's family types. */
 #define ZEBRA_FAMILY_IPV4                1
 #define ZEBRA_FAMILY_IPV6                2
diff --git a/ospf6d/ChangeLog b/ospf6d/ChangeLog
index e925d80..c6bc39f 100644
--- a/ospf6d/ChangeLog
+++ b/ospf6d/ChangeLog
@@ -1,3 +1,20 @@
+2005-10-01 Andrew J. Schorr <ajschorr@alumni.princeton.edu>
+
+	* ospf6_asbr.c: Remove local hard-coded tables zroute_name and
+	  zroute_abname. Change the ZROUTE_NAME macro to use new library
+	  function zebra_route_string().  Remove the ZROUTE_ABNAME macro.
+	  (ospf6_asbr_external_route_show): Replace ZROUTE_ABNAME() with
+	  a call to zebra_route_char(), and be sure to fix the format string,
+	  since we now have a char instead of a char *.
+	* ospf6_zebra.c: Remove local hard-coded tables zebra_route_name and
+	  zebra_route_abname.  Note that the zebra_route_name[] table
+	  contained mixed-case strings, whereas the zebra_route_string()
+	  function returns lower-case strings.
+	  (ospf6_zebra_read_ipv6): Change debug message to use new library
+	  function zebra_route_string() instead of zebra_route_name[].
+	  (show_zebra): Use new library function zebra_route_string() instead
+	  of zebra_route_name[].
+
 2005-08-09 Paul Jakma <paul.jakma@sun.com>
 
 	* ospf6_asbr.c: (ospf6_asbr_redistribute_add) Fix sense of testing
diff --git a/ospf6d/ospf6_asbr.c b/ospf6d/ospf6_asbr.c
index 379b629..286b5c1 100644
--- a/ospf6d/ospf6_asbr.c
+++ b/ospf6d/ospf6_asbr.c
@@ -50,19 +50,7 @@
 
 unsigned char conf_debug_ospf6_asbr = 0;
 
-const char *zroute_name[] =
-{ "system", "kernel", "connected", "static",
-  "rip", "ripng", "ospf", "ospf6", "isis", "bgp", "hsls", "unknown" };
-
-const char *zroute_abname[] =
-{ "X", "K", "C", "S", "R", "R", "O", "O", "I", "B", "H", "?" };
-
-#define ZROUTE_NAME(x)                                     \
-  (0 < (x) && (x) < ZEBRA_ROUTE_MAX ? zroute_name[(x)] :   \
-   zroute_name[ZEBRA_ROUTE_MAX])
-#define ZROUTE_ABNAME(x)                                   \
-  (0 < (x) && (x) < ZEBRA_ROUTE_MAX ? zroute_abname[(x)] : \
-   zroute_abname[ZEBRA_ROUTE_MAX])
+#define ZROUTE_NAME(x) zebra_route_string(x)
 
 /* AS External LSA origination */
 void
@@ -1198,8 +1186,8 @@
     snprintf (forwarding, sizeof (forwarding), ":: (ifindex %d)",
               route->nexthop[0].ifindex);
 
-  vty_out (vty, "%s %-32s %-15s type-%d %5lu %s%s",
-           ZROUTE_ABNAME (info->type),
+  vty_out (vty, "%c %-32s %-15s type-%d %5lu %s%s",
+           zebra_route_char(info->type),
            prefix, id, route->path.metric_type,
            (u_long) (route->path.metric_type == 2 ?
                      route->path.cost_e2 : route->path.cost),
diff --git a/ospf6d/ospf6_zebra.c b/ospf6d/ospf6_zebra.c
index bb32459..c974005 100644
--- a/ospf6d/ospf6_zebra.c
+++ b/ospf6d/ospf6_zebra.c
@@ -187,15 +187,6 @@
   return 0;
 }
 
-
-
-const char *zebra_route_name[ZEBRA_ROUTE_MAX] =
-  { "System", "Kernel", "Connect", "Static", "RIP", "RIPng", "OSPF",
-    "OSPF6", "ISIS", "BGP" };
-
-const char *zebra_route_abname[ZEBRA_ROUTE_MAX] =
-  { "X", "K", "C", "S", "r", "R", "o", "O", "I", "B" };
-
 int
 ospf6_zebra_read_ipv6 (int command, struct zclient *zclient,
                        zebra_size_t length)
@@ -255,7 +246,7 @@
 
       zlog_debug ("Zebra Receive route %s: %s %s nexthop %s ifindex %ld",
 		  (command == ZEBRA_IPV6_ROUTE_ADD ? "add" : "delete"),
-		  zebra_route_name[api.type], prefixstr, nexthopstr, ifindex);
+		  zebra_route_string(api.type), prefixstr, nexthopstr, ifindex);
     }
  
   if (command == ZEBRA_IPV6_ROUTE_ADD)
@@ -295,7 +286,7 @@
   for (i = 0; i < ZEBRA_ROUTE_MAX; i++)
     {
       if (zclient->redist[i])
-        vty_out (vty, " %s", zebra_route_name[i]);
+        vty_out (vty, " %s", zebra_route_string(i));
     }
   vty_out (vty, "%s", VNL);
   return CMD_SUCCESS;
diff --git a/ospfd/ChangeLog b/ospfd/ChangeLog
index 2e288a7..7d56bfe 100644
--- a/ospfd/ChangeLog
+++ b/ospfd/ChangeLog
@@ -1,3 +1,25 @@
+2005-10-01 Andrew J. Schorr <ajschorr@alumni.princeton.edu>
+
+	* ospf_dump.c: Remove local hard-coded table ospf_redistributed_proto.
+	  (ospf_redist_string) New function implemented using new library
+	  function zebra_route_string().  Note that there are a few differences
+	  in the output that will result: the new function returns strings
+	  that are lower-case, whereas the old table was mixed case.  Also,
+	  the old table mapped ZEBRA_ROUTE_OSPF6 to "OSPFv3", whereas the
+	  new function returns "ospf6".
+	* ospfd.h: Remove extern struct message ospf_redistributed_proto[],
+	  and add extern const char *ospf_redist_string(u_int route_type)
+	  instead.
+	* ospf_asbr.c: (ospf_external_info_add) In two messages, use
+	  ospf_redist_string instead of LOOKUP(ospf_redistributed_proto).
+	* ospf_vty.c: Remove local hard-coded table distribute_str.
+	  (config_write_ospf_redistribute,config_write_ospf_distribute): Use
+	  new library function zebra_route_string() instead of distribute_str[].
+	* ospf_zebra.c: (ospf_redistribute_set,ospf_redistribute_unset,
+	  ospf_redistribute_default_set,ospf_redistribute_check)
+	  In debug messages, use ospf_redist_string() instead of
+	  LOOKUP(ospf_redistributed_proto).
+
 2005-09-30 Vincent Jardin <vincent.jardin@6wind.com>
 
 	* ospf_dump.c, ospf_ia.c, ospf_spf.c, ospf_ase.c:
diff --git a/ospfd/ospf_asbr.c b/ospfd/ospf_asbr.c
index 2eb01d0..426fac4 100644
--- a/ospfd/ospf_asbr.c
+++ b/ospfd/ospf_asbr.c
@@ -152,7 +152,7 @@
       {
 	route_unlock_node (rn);
 	zlog_warn ("Redistribute[%s]: %s/%d already exists, discard.",
-		   LOOKUP (ospf_redistributed_proto, type),
+		   ospf_redist_string(type),
 		   inet_ntoa (p.prefix), p.prefixlen);
 	/* XFREE (MTYPE_OSPF_TMP, rn->info); */
 	return rn->info;
@@ -169,7 +169,7 @@
 
   if (IS_DEBUG_OSPF (lsa, LSA_GENERATE))
     zlog_debug ("Redistribute[%s]: %s/%d external info created.",
-	       LOOKUP (ospf_redistributed_proto, type),
+	       ospf_redist_string(type),
 	       inet_ntoa (p.prefix), p.prefixlen);
   return new;
 }
diff --git a/ospfd/ospf_dump.c b/ospfd/ospf_dump.c
index 4ace02b..ac74269 100644
--- a/ospfd/ospf_dump.c
+++ b/ospfd/ospf_dump.c
@@ -103,21 +103,6 @@
 };
 int ospf_link_state_id_type_msg_max = OSPF_MAX_LSA;
 
-struct message ospf_redistributed_proto[] =
-{
-  { ZEBRA_ROUTE_SYSTEM,   "System" },
-  { ZEBRA_ROUTE_KERNEL,   "Kernel" },
-  { ZEBRA_ROUTE_CONNECT,  "Connected" },
-  { ZEBRA_ROUTE_STATIC,   "Static" },
-  { ZEBRA_ROUTE_RIP,      "RIP" },
-  { ZEBRA_ROUTE_RIPNG,    "RIPng" },
-  { ZEBRA_ROUTE_OSPF,     "OSPF" },
-  { ZEBRA_ROUTE_OSPF6,    "OSPFv3" },
-  { ZEBRA_ROUTE_BGP,      "BGP" },
-  { ZEBRA_ROUTE_MAX,	  "Default" },
-};
-int ospf_redistributed_proto_max = ZEBRA_ROUTE_MAX + 1;
-
 struct message ospf_network_type_msg[] =
 {
   { OSPF_IFTYPE_NONE,		  "NONE" },
@@ -148,6 +133,14 @@
 unsigned long term_debug_ospf_nssa = 0;
 
 
+
+const char *
+ospf_redist_string(u_int route_type)
+{
+  return (route_type == ZEBRA_ROUTE_MAX) ?
+  	 "Default" : zebra_route_string(route_type);
+}
+
 #define OSPF_AREA_STRING_MAXLEN  16
 const char *
 ospf_area_name_string (struct ospf_area *area)
diff --git a/ospfd/ospf_vty.c b/ospfd/ospf_vty.c
index 1a2afac..a47eca1 100644
--- a/ospfd/ospf_vty.c
+++ b/ospfd/ospf_vty.c
@@ -7288,8 +7288,6 @@
 }
 
 
-const char *distribute_str[] = { "system", "kernel", "connected", "static",
-				"rip", "ripng", "ospf", "ospf6", "isis", "bgp"};
 static int
 config_write_ospf_redistribute (struct vty *vty, struct ospf *ospf)
 {
@@ -7299,7 +7297,7 @@
   for (type = 0; type < ZEBRA_ROUTE_MAX; type++)
     if (type != zclient->redist_default && zclient->redist[type])
       {
-        vty_out (vty, " redistribute %s", distribute_str[type]);
+        vty_out (vty, " redistribute %s", zebra_route_string(type));
 	if (ospf->dmetric[type].value >= 0)
 	  vty_out (vty, " metric %d", ospf->dmetric[type].value);
 	
@@ -7336,7 +7334,7 @@
 	if (ospf->dlist[type].name)
 	  vty_out (vty, " distribute-list %s out %s%s", 
 		   ospf->dlist[type].name,
-		   distribute_str[type], VTY_NEWLINE);
+		   zebra_route_string(type), VTY_NEWLINE);
 
       /* default-information print. */
       if (ospf->default_originate != DEFAULT_ORIGINATE_NONE)
diff --git a/ospfd/ospf_zebra.c b/ospfd/ospf_zebra.c
index 2072b17..0d98008 100644
--- a/ospfd/ospf_zebra.c
+++ b/ospfd/ospf_zebra.c
@@ -527,7 +527,7 @@
 
       if (IS_DEBUG_OSPF (zebra, ZEBRA_REDISTRIBUTE))
         zlog_debug ("Redistribute[%s]: Refresh  Type[%d], Metric[%d]",
-                   LOOKUP (ospf_redistributed_proto, type),
+                   ospf_redist_string(type),
                    metric_type (ospf, type), metric_value (ospf, type));
 
       return CMD_SUCCESS;
@@ -540,7 +540,7 @@
 
   if (IS_DEBUG_OSPF (zebra, ZEBRA_REDISTRIBUTE))
     zlog_debug ("Redistribute[%s]: Start  Type[%d], Metric[%d]",
-               LOOKUP (ospf_redistributed_proto, type),
+               ospf_redist_string(type),
                metric_type (ospf, type), metric_value (ospf, type));
 
   ospf_asbr_status_update (ospf, ++ospf->redistribute);
@@ -561,7 +561,7 @@
 
   if (IS_DEBUG_OSPF (zebra, ZEBRA_REDISTRIBUTE))
     zlog_debug ("Redistribute[%s]: Stop",
-               LOOKUP (ospf_redistributed_proto, type));
+               ospf_redist_string(type));
 
   ospf->dmetric[type].type = -1;
   ospf->dmetric[type].value = -1;
@@ -597,7 +597,7 @@
 
       if (IS_DEBUG_OSPF (zebra, ZEBRA_REDISTRIBUTE))
         zlog_debug ("Redistribute[%s]: Refresh  Type[%d], Metric[%d]",
-                   LOOKUP (ospf_redistributed_proto, DEFAULT_ROUTE),
+                   ospf_redist_string(DEFAULT_ROUTE),
                    metric_type (ospf, DEFAULT_ROUTE),
                    metric_value (ospf, DEFAULT_ROUTE));
       return CMD_SUCCESS;
@@ -713,7 +713,7 @@
         {
           if (IS_DEBUG_OSPF (zebra, ZEBRA_REDISTRIBUTE))
             zlog_debug ("Redistribute[%s]: %s/%d filtered by ditribute-list.",
-                       LOOKUP (ospf_redistributed_proto, type),
+                       ospf_redist_string(type),
                        inet_ntoa (p->prefix), p->prefixlen);
           return 0;
         }
@@ -734,7 +734,7 @@
           ei->route_map_set = save_values;
           if (IS_DEBUG_OSPF (zebra, ZEBRA_REDISTRIBUTE))
             zlog_debug ("Redistribute[%s]: %s/%d filtered by route-map.",
-                       LOOKUP (ospf_redistributed_proto, type),
+                       ospf_redist_string(type),
                        inet_ntoa (p->prefix), p->prefixlen);
           return 0;
         }
diff --git a/ospfd/ospfd.h b/ospfd/ospfd.h
index 95e4751..7a2649f 100644
--- a/ospfd/ospfd.h
+++ b/ospfd/ospfd.h
@@ -516,7 +516,6 @@
 extern struct message ospf_nsm_state_msg[];
 extern struct message ospf_lsa_type_msg[];
 extern struct message ospf_link_state_id_type_msg[];
-extern struct message ospf_redistributed_proto[];
 extern struct message ospf_network_type_msg[];
 extern int ospf_ism_state_msg_max;
 extern int ospf_nsm_state_msg_max;
@@ -529,6 +528,7 @@
 extern int ospf_zlog;
 
 /* Prototypes. */
+extern const char *ospf_redist_string(u_int route_type);
 extern struct ospf *ospf_lookup (void);
 extern struct ospf *ospf_get (void);
 extern void ospf_finish (struct ospf *);
diff --git a/ripd/ChangeLog b/ripd/ChangeLog
index 6aecebd..0e19ef3 100644
--- a/ripd/ChangeLog
+++ b/ripd/ChangeLog
@@ -1,3 +1,12 @@
+2005-10-01 Andrew J. Schorr <ajschorr@alumni.princeton.edu>
+
+	* rip_zebra.c: (config_write_rip_redistribute): Remove local hard-coded
+	  table str[]. Replace str[] with calls to new library function
+	  zebra_route_string().
+	* ripd.c: Remove local hard-coded table route_info[].
+	  (show_ip_rip) Replace uses of str[] with calls to new library
+	  functions zebra_route_char and zebra_route_string.
+
 2005-09-29 Alain Ritoux <alain.ritoux@6wind.com>
 
 	* rip_snmp.c: rip2IfConfReceive() sends values in conformance
diff --git a/ripd/rip_zebra.c b/ripd/rip_zebra.c
index 570b528..d810a6b 100644
--- a/ripd/rip_zebra.c
+++ b/ripd/rip_zebra.c
@@ -653,8 +653,6 @@
 config_write_rip_redistribute (struct vty *vty, int config_mode)
 {
   int i;
-  const char *str[] = { "system", "kernel", "connected", "static", "rip",
-			"ripng", "ospf", "ospf6", "isis", "bgp"};
 
   for (i = 0; i < ZEBRA_ROUTE_MAX; i++)
     if (i != zclient->redist_default && zclient->redist[i])
@@ -665,27 +663,27 @@
 	      {
 		if (rip->route_map[i].name)
 		  vty_out (vty, " redistribute %s metric %d route-map %s%s",
-			   str[i], rip->route_map[i].metric,
+			   zebra_route_string(i), rip->route_map[i].metric,
 			   rip->route_map[i].name,
 			   VTY_NEWLINE);
 		else
 		  vty_out (vty, " redistribute %s metric %d%s",
-			   str[i], rip->route_map[i].metric,
+			   zebra_route_string(i), rip->route_map[i].metric,
 			   VTY_NEWLINE);
 	      }
 	    else
 	      {
 		if (rip->route_map[i].name)
 		  vty_out (vty, " redistribute %s route-map %s%s",
-			   str[i], rip->route_map[i].name,
+			   zebra_route_string(i), rip->route_map[i].name,
 			   VTY_NEWLINE);
 		else
-		  vty_out (vty, " redistribute %s%s", str[i],
+		  vty_out (vty, " redistribute %s%s", zebra_route_string(i),
 			   VTY_NEWLINE);
 	      }
 	  }
 	else
-	  vty_out (vty, " %s", str[i]);
+	  vty_out (vty, " %s", zebra_route_string(i));
       }
   return 0;
 }
diff --git a/ripd/ripd.c b/ripd/ripd.c
index 13cf9b9..fd1f2da 100644
--- a/ripd/ripd.c
+++ b/ripd/ripd.c
@@ -85,26 +85,6 @@
   {RIP_POLL_ENTRY, "POLL ENTRY"},
   {0,              NULL}
 };
-
-/* Each route type's strings and default preference. */
-struct
-{  
-  int key;
-  const char *str;
-  const char *str_long;
-} route_info[] =
-{
-  { ZEBRA_ROUTE_SYSTEM,  "X", "system"},
-  { ZEBRA_ROUTE_KERNEL,  "K", "kernel"},
-  { ZEBRA_ROUTE_CONNECT, "C", "connected"},
-  { ZEBRA_ROUTE_STATIC,  "S", "static"},
-  { ZEBRA_ROUTE_RIP,     "R", "rip"},
-  { ZEBRA_ROUTE_RIPNG,   "R", "ripng"},
-  { ZEBRA_ROUTE_OSPF,    "O", "ospf"},
-  { ZEBRA_ROUTE_OSPF6,   "O", "ospf6"},
-  { ZEBRA_ROUTE_ISIS,    "I", "isis"},
-  { ZEBRA_ROUTE_BGP,     "B", "bgp"}
-};
 
 /* Utility function to set boradcast option to the socket. */
 int
@@ -3478,9 +3458,9 @@
       {
 	int len;
 
-	len = vty_out (vty, "%s(%s) %s/%d",
+	len = vty_out (vty, "%c(%s) %s/%d",
 		       /* np->lock, For debugging. */
-		       route_info[rinfo->type].str,
+		       zebra_route_char(rinfo->type),
 		       rip_route_type_print (rinfo->sub_type),
 		       inet_ntoa (np->p.u.prefix4), np->p.prefixlen);
 	
@@ -3514,7 +3494,7 @@
 	    if (rinfo->external_metric)
 	      {
 	        len = vty_out (vty, "self (%s:%d)", 
-	                       route_info[rinfo->type].str_long,
+			       zebra_route_string(rinfo->type),
 	                       rinfo->external_metric);
 	        len = 16 - len;
 	        if (len > 0)
diff --git a/ripngd/ChangeLog b/ripngd/ChangeLog
index 84c3ea0..46d4f9f 100644
--- a/ripngd/ChangeLog
+++ b/ripngd/ChangeLog
@@ -1,3 +1,12 @@
+2005-10-01 Andrew J. Schorr <ajschorr@alumni.princeton.edu>
+
+	* ripng_zebra.c: (ripng_redistribute_write) Remove local hard-coded
+	  table str[].  Replace str[i] with new library function
+	  zebra_route_string(i).
+	* ripngd.c: Remove local hard-coded table route_info[].
+	  (show_ipv6_ripng) Use new library function zebra_route_char() instead
+	  of table route_info[].
+
 2005-08-27 Hasso Tepper <hasso at quagga.net>
 
 	* ripng_zebra.c, ripngd.[ch]: Pass metric info to the zebra daemon.
diff --git a/ripngd/ripng_zebra.c b/ripngd/ripng_zebra.c
index 7744fd5..1f9bee0 100644
--- a/ripngd/ripng_zebra.c
+++ b/ripngd/ripng_zebra.c
@@ -486,8 +486,6 @@
 ripng_redistribute_write (struct vty *vty, int config_mode)
 {
   int i;
-  const char *str[] = { "system", "kernel", "connected", "static", "rip",
-			"ripng", "ospf", "ospf6", "isis", "bgp"};
 
   for (i = 0; i < ZEBRA_ROUTE_MAX; i++)
     if (i != zclient->redist_default && zclient->redist[i])
@@ -498,23 +496,26 @@
 	    {
 	      if (ripng->route_map[i].name)
 		vty_out (vty, " redistribute %s metric %d route-map %s%s",
-			 str[i], ripng->route_map[i].metric,
+			 zebra_route_string(i), ripng->route_map[i].metric,
 			ripng->route_map[i].name, VTY_NEWLINE);
 	      else
 		vty_out (vty, " redistribute %s metric %d%s",
-			str[i], ripng->route_map[i].metric, VTY_NEWLINE);
+			zebra_route_string(i), ripng->route_map[i].metric,
+			VTY_NEWLINE);
 	    }
 	  else
 	    {
 	      if (ripng->route_map[i].name)
 		vty_out (vty, " redistribute %s route-map %s%s",
-			 str[i], ripng->route_map[i].name, VTY_NEWLINE);
+			 zebra_route_string(i), ripng->route_map[i].name,
+			 VTY_NEWLINE);
 	      else
-		vty_out (vty, " redistribute %s%s", str[i], VTY_NEWLINE);
+		vty_out (vty, " redistribute %s%s", zebra_route_string(i),
+			 VTY_NEWLINE);
 	    }
 	}
       else
-	vty_out (vty, "    %s", str[i]);
+	vty_out (vty, "    %s", zebra_route_string(i));
       }
 }
 
diff --git a/ripngd/ripngd.c b/ripngd/ripngd.c
index cf0d578..a5bc28d 100644
--- a/ripngd/ripngd.c
+++ b/ripngd/ripngd.c
@@ -1922,26 +1922,6 @@
     }
 }
 
-/* Each route type's strings and default preference.
- * FIXME: ISIS? What are these distance values? */
-struct
-{  
-  int key;
-  const char *str;
-  const char *str_long;
-  int distance;
-} route_info[] =
-{
-  { ZEBRA_ROUTE_SYSTEM,  "X", "system",    10},
-  { ZEBRA_ROUTE_KERNEL,  "K", "kernel",    20},
-  { ZEBRA_ROUTE_CONNECT, "C", "connected", 30},
-  { ZEBRA_ROUTE_STATIC,  "S", "static",    40},
-  { ZEBRA_ROUTE_RIP,     "R", "rip",       50},
-  { ZEBRA_ROUTE_RIPNG,   "R", "ripng",     50},
-  { ZEBRA_ROUTE_OSPF,    "O", "ospf",      60},
-  { ZEBRA_ROUTE_OSPF6,   "O", "ospf6",     60},
-  { ZEBRA_ROUTE_BGP,     "B", "bgp",       70},
-};
 
 /* Print out routes update time. */
 static void
@@ -2059,14 +2039,14 @@
 	  p = (struct prefix_ipv6 *) &rp->p;
 
 #ifdef DEBUG
-	  len = vty_out (vty, "%s(%s) 0/%d %s/%d ",
-			 route_info[rinfo->type].str,
+	  len = vty_out (vty, "%c(%s) 0/%d %s/%d ",
+			 zebra_route_char(rinfo->type),
 			 ripng_route_subtype_print(rinfo),
 			 rinfo->suppress,
 			 inet6_ntoa (p->prefix), p->prefixlen);
 #else
-	  len = vty_out (vty, "%s(%s) %s/%d ",
-			 route_info[rinfo->type].str,
+	  len = vty_out (vty, "%c(%s) %s/%d ",
+			 zebra_route_char(rinfo->type),
 			 ripng_route_subtype_print(rinfo),
 			 inet6_ntoa (p->prefix), p->prefixlen);
 #endif /* DEBUG */
diff --git a/zebra/ChangeLog b/zebra/ChangeLog
index 9f4bd18..22adfeb 100644
--- a/zebra/ChangeLog
+++ b/zebra/ChangeLog
@@ -1,5 +1,20 @@
 2005-10-01 Andrew J. Schorr <ajschorr@alumni.princeton.edu>
 
+	* zebra_vty.c: (route_type_str) Remove obsolete function: use new
+	  library function zebra_route_string() instead.  Note that there
+	  are a few differences: for IPv6 routes, we now get "ripng" and
+	  "ospf6" instead of the old behavior ("rip" and "ospf").
+	  (route_type_char) Remove obsolete function: ues new library function
+	  zebra_route_char() instead.  Note that there is one difference:
+	  the old function returned 'S' for a ZEBRA_ROUTE_SYSTEM route,
+	  whereas the new one returns 'X'.
+	  (vty_show_ip_route_detail,vty_show_ipv6_route_detail) Replace
+	  route_type_str() with zebra_route_string().
+	  (vty_show_ip_route,vty_show_ipv6_route) Replace route_type_char()
+	  with zebra_route_char().
+
+2005-10-01 Andrew J. Schorr <ajschorr@alumni.princeton.edu>
+
 	* rt_netlink.c: (netlink_request) Use memset to clear structure
 	  before calling sendto (eliminates a valgrind error message about
 	  uninitialized data).
diff --git a/zebra/zebra_vty.c b/zebra/zebra_vty.c
index ad91d95..68e6f92 100644
--- a/zebra/zebra_vty.c
+++ b/zebra/zebra_vty.c
@@ -29,68 +29,6 @@
 
 #include "zebra/zserv.h"
 
-/* Return route type string for VTY output.  */
-static const char *
-route_type_str (u_char type)
-{
-  switch (type)
-    {
-    case ZEBRA_ROUTE_SYSTEM:
-      return "system";
-    case ZEBRA_ROUTE_KERNEL:
-      return "kernel";
-    case ZEBRA_ROUTE_CONNECT:
-      return "connected";
-    case ZEBRA_ROUTE_STATIC:
-      return "static";
-    case ZEBRA_ROUTE_RIP:
-      return "rip";
-    case ZEBRA_ROUTE_RIPNG:
-      return "rip";
-    case ZEBRA_ROUTE_OSPF:
-      return "ospf";
-    case ZEBRA_ROUTE_OSPF6:
-      return "ospf";
-    case ZEBRA_ROUTE_ISIS:
-      return "isis";
-    case ZEBRA_ROUTE_BGP:
-      return "bgp";
-    default:
-      return "unknown";
-    }
-};
-
-/* Return route type string for VTY output.  */
-static const char
-route_type_char (u_char type)
-{
-  switch (type)
-    {
-    case ZEBRA_ROUTE_SYSTEM:
-      return 'S';
-    case ZEBRA_ROUTE_KERNEL:
-      return 'K';
-    case ZEBRA_ROUTE_CONNECT:
-      return 'C';
-    case ZEBRA_ROUTE_STATIC:
-      return 'S';
-    case ZEBRA_ROUTE_RIP:
-      return 'R';
-    case ZEBRA_ROUTE_RIPNG:
-      return 'R';
-    case ZEBRA_ROUTE_OSPF:
-      return 'O';
-    case ZEBRA_ROUTE_OSPF6:
-      return 'O';
-    case ZEBRA_ROUTE_ISIS:
-      return 'I';
-    case ZEBRA_ROUTE_BGP:
-      return 'B';
-    default:
-      return '?';
-    }
-};
-
 /* General fucntion for static route. */
 static int
 zebra_static_ipv4 (struct vty *vty, int add_cmd, const char *dest_str,
@@ -548,7 +486,7 @@
       vty_out (vty, "Routing entry for %s/%d%s", 
 	       inet_ntoa (rn->p.u.prefix4), rn->p.prefixlen,
 	       VTY_NEWLINE);
-      vty_out (vty, "  Known via \"%s\"", route_type_str (rib->type));
+      vty_out (vty, "  Known via \"%s\"", zebra_route_string (rib->type));
       vty_out (vty, ", distance %d, metric %d", rib->distance, rib->metric);
       if (CHECK_FLAG (rib->flags, ZEBRA_FLAG_SELECTED))
 	vty_out (vty, ", best");
@@ -657,7 +595,7 @@
 	{
 	  /* Prefix information. */
 	  len = vty_out (vty, "%c%c%c %s/%d",
-			 route_type_char (rib->type),
+			 zebra_route_char (rib->type),
 			 CHECK_FLAG (rib->flags, ZEBRA_FLAG_SELECTED)
 			 ? '>' : ' ',
 			 CHECK_FLAG (nexthop->flags, NEXTHOP_FLAG_FIB)
@@ -1435,7 +1373,7 @@
 	       inet_ntop (AF_INET6, &rn->p.u.prefix6, buf, BUFSIZ),
 	       rn->p.prefixlen,
 	       VTY_NEWLINE);
-      vty_out (vty, "  Known via \"%s\"", route_type_str (rib->type));
+      vty_out (vty, "  Known via \"%s\"", zebra_route_string (rib->type));
       vty_out (vty, ", distance %d, metric %d", rib->distance, rib->metric);
       if (CHECK_FLAG (rib->flags, ZEBRA_FLAG_SELECTED))
 	vty_out (vty, ", best");
@@ -1552,7 +1490,7 @@
 	{
 	  /* Prefix information. */
 	  len = vty_out (vty, "%c%c%c %s/%d",
-			 route_type_char (rib->type),
+			 zebra_route_char (rib->type),
 			 CHECK_FLAG (rib->flags, ZEBRA_FLAG_SELECTED)
 			 ? '>' : ' ',
 			 CHECK_FLAG (nexthop->flags, NEXTHOP_FLAG_FIB)