]> git.ipfire.org Git - thirdparty/bird.git/commitdiff
Changed initialization of protocol list -- now we call proto_build() instead
authorMartin Mares <mj@ucw.cz>
Sat, 1 Apr 2000 10:19:47 +0000 (10:19 +0000)
committerMartin Mares <mj@ucw.cz>
Sat, 1 Apr 2000 10:19:47 +0000 (10:19 +0000)
of calling the protocols manually.

Implemented printing of dynamic attributes in `show route all'.

Each protocol can now register its own attribute class (protocol->attr_class,
set to EAP_xxx) and also a callback for naming and formatting of attributes.
The callback can return one of the following results:

GA_UNKNOWN Attribute not recognized.
GA_NAME Attribute name recognized and put to the buffer,
generic code should format the value.
GA_FULL Both attribute name and value put to the buffer.

Please update protocols generating dynamic attributes to provide
the attr_class and formatting hook.

TODO
doc/reply_codes
nest/proto.c
nest/protocol.h
nest/route.h
nest/rt-attr.c
nest/rt-table.c
sysdep/unix/main.c

diff --git a/TODO b/TODO
index d3290e8a43af5bec6ed0d208b76fbcc8a797b113..0a4a48221db4ace39cb18b10fa454643de6f897e 100644 (file)
--- a/TODO
+++ b/TODO
@@ -24,6 +24,8 @@ Documentation
 Globals
 ~~~~~~~
 - right usage of DBG vs. debug
+- kill preconfigs?
+- check dump functions
 - cleanup debugging calls
 - logging and tracing; use appropriate log levels
 - check incoming packets and log errors!!
index 140de95afaa6bee57dedf458905e505708f0f0ed..91466bee46820a78a80599ca512418f45eb7632b 100644 (file)
@@ -35,6 +35,7 @@ Reply codes of BIRD command-line interface
 1009   Static route list
 1010   Symbol list
 1011   Uptime
+1012   Route extended attribute list
 
 8000   Reply too long
 8001   Route not found
index c6a3d7d46a1d05078e2368e7240fd67cc771c861..abf4a3cf6ca85407b6adf680031300eb83408473 100644 (file)
@@ -22,7 +22,7 @@
 
 static pool *proto_pool;
 
-list protocol_list;
+static list protocol_list;
 static list proto_list;
 
 #define WALK_PROTO_LIST(p) do {                                                        \
@@ -343,6 +343,17 @@ protos_dump_all(void)
     debug("  flushing %s\n", p->name);
 }
 
+void
+proto_build(struct protocol *p)
+{
+  add_tail(&protocol_list, &p->n);
+  if (p->attr_class)
+    {
+      ASSERT(!attr_class_to_protocol[p->attr_class]);
+      attr_class_to_protocol[p->attr_class] = p;
+    }
+}
+
 void
 protos_build(void)
 {
@@ -352,21 +363,21 @@ protos_build(void)
   init_list(&inactive_proto_list);
   init_list(&initial_proto_list);
   init_list(&flush_proto_list);
-  add_tail(&protocol_list, &proto_device.n);
+  proto_build(&proto_device);
 #ifdef CONFIG_RIP
-  add_tail(&protocol_list, &proto_rip.n);
+  proto_build(&proto_rip);
 #endif
 #ifdef CONFIG_STATIC
-  add_tail(&protocol_list, &proto_static.n);
+  proto_build(&proto_static);
 #endif
 #ifdef CONFIG_OSPF
-  add_tail(&protocol_list, &proto_ospf.n);
+  proto_build(&proto_ospf);
 #endif
 #ifdef CONFIG_PIPE
-  add_tail(&protocol_list, &proto_pipe.n);
+  proto_build(&proto_pipe);
 #endif
 #ifdef CONFIG_BGP
-  add_tail(&protocol_list, &proto_bgp.n);
+  proto_build(&proto_bgp);
 #endif
   proto_pool = rp_new(&root_pool, "Protocols");
   proto_flush_event = ev_new(proto_pool);
index b02ea0229139f2cb62473cbc8b4413a9b8230ec6..2e64112f4eafc8c99ea7d752f2380d388652c86a 100644 (file)
@@ -24,6 +24,7 @@ struct config;
 struct proto;
 struct event;
 struct ea_list;
+struct eattr;
 struct symbol;
 
 /*
@@ -35,6 +36,7 @@ struct protocol {
   char *name;
   char *template;                      /* Template for automatic generation of names */
   int name_counter;                    /* Counter for automatic name generation */
+  int attr_class;                      /* Attribute class known to this protocol */
 
   void (*preconfig)(struct protocol *, struct config *);       /* Just before configuring */
   void (*postconfig)(struct proto_config *);                   /* After configuring each instance */
@@ -46,16 +48,19 @@ struct protocol {
   int (*shutdown)(struct proto *);             /* Stop the instance */
   void (*get_status)(struct proto *, byte *buf); /* Get instance status (for `show protocols' command) */
   void (*get_route_info)(struct rte *, byte *buf); /* Get route information (for `show route' command) */
-  void (*show_route_data)(struct rte *);       /* Print verbose route information (`show route' again) */
+  int (*get_attr)(struct eattr *, byte *buf);  /* ASCIIfy dynamic attribute (returns GA_*) */
 };
 
 void protos_build(void);
+void proto_build(struct protocol *);
 void protos_preconfig(struct config *);
 void protos_postconfig(struct config *);
 void protos_commit(struct config *new, struct config *old, int force_restart);
 void protos_dump_all(void);
 
-extern list protocol_list;
+#define GA_UNKNOWN     0               /* Attribute not recognized */
+#define GA_NAME                1               /* Result = name */
+#define GA_FULL                2               /* Result = both name and value */
 
 /*
  *     Known protocols
@@ -146,7 +151,6 @@ struct proto {
   /* Hic sunt protocol-specific data */
 };
 
-void proto_build(struct proto_config *);
 void *proto_new(struct proto_config *, unsigned size);
 void *proto_config_new(struct protocol *, unsigned size);
 
index f180d5e3a6adb0aa78733f1cc25d502e8841912d..96ee580bb14b6c7237bad71124d32b0a1a573230 100644 (file)
@@ -283,6 +283,7 @@ typedef struct eattr {
 #define EAP_GENERIC 0                  /* Generic attributes */
 #define EAP_BGP 1                      /* BGP attributes */
 #define EAP_RIP 2                      /* RIP */
+#define EAP_MAX 3
 
 #define EA_CODE(proto,id) (((proto) << 8) | (id))
 #define EA_PROTO(ea) ((ea) >> 8)
@@ -336,6 +337,8 @@ void rta_dump_all(void);
 static inline eattr * rta_find(rta *a, unsigned ea) { return ea_find(a->eattrs, ea); }
 void rta_show(struct cli *, rta *);
 
+extern struct protocol *attr_class_to_protocol[EAP_MAX];
+
 /*
  *     Default protocol preferences
  */
index 63f596ef73f04ab77724e4c4f9818498c94dc50f..57c98b2d44157e1881ccc91266738fb7f05f3dc7 100644 (file)
@@ -19,6 +19,8 @@
 static slab *rta_slab;
 static pool *rta_pool;
 
+struct protocol *attr_class_to_protocol[EAP_MAX];
+
 /*
  *     Extended Attributes
  */
@@ -233,6 +235,60 @@ ea_list_copy(ea_list *o)
   return n;
 }
 
+void
+ea_format(eattr *e, byte *buf)
+{
+  struct protocol *p;
+  int status = GA_UNKNOWN;
+  unsigned int i, l;
+  struct adata *ad = (e->type & EAF_EMBEDDED) ? NULL : e->u.ptr;
+
+  if (p = attr_class_to_protocol[EA_PROTO(e->id)])
+    {
+      buf += bsprintf(buf, "%s.", p->name);
+      if (p->get_attr)
+       status = p->get_attr(e, buf);
+      buf += strlen(buf);
+    }
+  else if (EA_PROTO(e->id))
+    buf += bsprintf(buf, "%02x.", EA_PROTO(e->id));
+  if (status < GA_NAME)
+    buf += bsprintf(buf, "%02x", EA_ID(e->id));
+  if (status < GA_FULL)
+    {
+      *buf++ = ':';
+      *buf++ = ' ';
+      switch (e->type & EAF_TYPE_MASK)
+       {
+       case EAF_TYPE_INT:
+         bsprintf(buf, "%d", e->u.data);
+         break;
+       case EAF_TYPE_OPAQUE:
+         l = (ad->length < 16) ? ad->length : 16;
+         for(i=0; i<l; i++)
+           {
+             buf += bsprintf(buf, "%02x", ad->data[i]);
+             if (i < l)
+               *buf++ = ' ';
+           }
+         if (l < ad->length)
+           strcpy(buf, "...");
+         break;
+       case EAF_TYPE_IP_ADDRESS:
+         bsprintf(buf, "%I", *(ip_addr *) ad->data);
+         break;
+       case EAF_TYPE_ROUTER_ID:
+         bsprintf(buf, "%08x", e->u.data); /* FIXME: Better printing of router ID's */
+         break;
+       case EAF_TYPE_AS_PATH:          /* FIXME */
+       case EAF_TYPE_INT_SET:          /* FIXME */
+       case EAF_TYPE_UNDEF:
+       default:
+         bsprintf(buf, "<type %02x>", e->type);
+       }
+    }
+}
+
 void
 ea_dump(ea_list *e)
 {
@@ -484,9 +540,17 @@ rta_show(struct cli *c, rta *a)
                               "RIP", "RIP-ext", "OSPF", "OSPF-ext", "OSPF-IA", "OSPF-boundary",
                               "BGP" };
   static char *cast_names[] = { "unicast", "broadcast", "multicast", "anycast" };
+  ea_list *eal;
+  int i;
+  byte buf[256];
 
   cli_printf(c, -1008, "\tType: %s %s %s", src_names[a->source], cast_names[a->cast], ip_scope_text(a->scope));
-  /* FIXME: Here we probably should print the dynamic attributes... */
+  for(eal=a->eattrs; eal; eal=eal->next)
+    for(i=0; i<eal->count; i++)
+      {
+       ea_format(&eal->attrs[i], buf);
+       cli_printf(c, -1012, "\t%s", buf);
+      }
 }
 
 void
index 3daa836cfdadd87f789e47d74b6498ddb6ef89b9..6ad5b06f385970b2965024c81d479e884505b9ee 100644 (file)
@@ -675,11 +675,7 @@ rt_show_rte(struct cli *c, byte *ia, rte *e, struct rt_show_data *d)
     bsprintf(info, " (%d)", e->pref);
   cli_printf(c, -1007, "%-18s %s [%s %s%s]%s", ia, via, a->proto->name, tm, from, info);
   if (d->verbose)
-    {
-      rta_show(c, a);
-      if (a->proto->proto->show_route_data)
-       a->proto->proto->show_route_data(e);
-    }
+    rta_show(c, a);
 }
 
 static void
index 121ec9dcc0deb93877813fc01cdf7915a7a41e94..39ac3521b96f42f67bfd6ebdd056561c659e044a 100644 (file)
@@ -400,8 +400,8 @@ main(int argc, char **argv)
   if_init();
 
   protos_build();
-  add_tail(&protocol_list, &proto_unix_kernel.n);
-  add_tail(&protocol_list, &proto_unix_iface.n);
+  proto_build(&proto_unix_kernel);
+  proto_build(&proto_unix_iface);
 
   read_config();