Commit 56c8f2f0 authored by Maria Matejka's avatar Maria Matejka
Browse files

Nest: Route generations and explicit tracking route propagion through pipes

parent 1c2f66f2
Loading
Loading
Loading
Loading
+1 −0
Original line number Original line Diff line number Diff line
@@ -45,6 +45,7 @@ struct config {


  int cli_debug;			/* Tracing of CLI connections and commands */
  int cli_debug;			/* Tracing of CLI connections and commands */
  int latency_debug;			/* I/O loop tracks duration of each event */
  int latency_debug;			/* I/O loop tracks duration of each event */
  int pipe_debug;			/* Track route propagation through pipes */
  u32 latency_limit;			/* Events with longer duration are logged (us) */
  u32 latency_limit;			/* Events with longer duration are logged (us) */
  u32 watchdog_warning;			/* I/O loop watchdog limit for warning (us) */
  u32 watchdog_warning;			/* I/O loop watchdog limit for warning (us) */
  u32 watchdog_timeout;			/* Watchdog timeout (in seconds, 0 = disabled) */
  u32 watchdog_timeout;			/* Watchdog timeout (in seconds, 0 = disabled) */
+8 −0
Original line number Original line Diff line number Diff line
@@ -4124,6 +4124,14 @@ include standard channel config options; see the example below.
	<tag><label id="pipe-peer-table">peer table <m/table/</tag>
	<tag><label id="pipe-peer-table">peer table <m/table/</tag>
	Defines secondary routing table to connect to. The primary one is
	Defines secondary routing table to connect to. The primary one is
	selected by the <cf/table/ keyword.
	selected by the <cf/table/ keyword.

	<tag><label id="pipe-max-generation">max generation <m/expr/</tag>
	Sets maximal generation of route that may pass through this pipe.
	The generation value is increased by one by each pipe on its path.
	Not meeting this requirement causes an error message complaining about
	an overpiped route. If you have long chains of pipes, you probably want
	to raise this value; anyway the default of 16 should be enough for even
	most strange uses. Maximum is 254.
</descrip>
</descrip>


<sect1>Attributes
<sect1>Attributes
+2 −1
Original line number Original line Diff line number Diff line
@@ -111,7 +111,7 @@ proto_postconfig(void)


CF_DECLS
CF_DECLS


CF_KEYWORDS(ROUTER, ID, HOSTNAME, PROTOCOL, TEMPLATE, PREFERENCE, DISABLED, DEBUG, ALL, OFF, DIRECT)
CF_KEYWORDS(ROUTER, ID, HOSTNAME, PROTOCOL, TEMPLATE, PREFERENCE, DISABLED, DEBUG, ALL, OFF, DIRECT, PIPE)
CF_KEYWORDS(INTERFACE, IMPORT, EXPORT, FILTER, NONE, VRF, DEFAULT, TABLE, STATES, ROUTES, FILTERS)
CF_KEYWORDS(INTERFACE, IMPORT, EXPORT, FILTER, NONE, VRF, DEFAULT, TABLE, STATES, ROUTES, FILTERS)
CF_KEYWORDS(IPV4, IPV6, VPN4, VPN6, ROA4, ROA6, FLOW4, FLOW6, SADR, MPLS)
CF_KEYWORDS(IPV4, IPV6, VPN4, VPN6, ROA4, ROA6, FLOW4, FLOW6, SADR, MPLS)
CF_KEYWORDS(RECEIVE, LIMIT, ACTION, WARN, BLOCK, RESTART, DISABLE, KEEP, FILTERED, RPKI)
CF_KEYWORDS(RECEIVE, LIMIT, ACTION, WARN, BLOCK, RESTART, DISABLE, KEEP, FILTERED, RPKI)
@@ -348,6 +348,7 @@ debug_default:
   DEBUG PROTOCOLS debug_mask { new_config->proto_default_debug = $3; }
   DEBUG PROTOCOLS debug_mask { new_config->proto_default_debug = $3; }
 | DEBUG CHANNELS debug_mask { new_config->channel_default_debug = $3; }
 | DEBUG CHANNELS debug_mask { new_config->channel_default_debug = $3; }
 | DEBUG COMMANDS expr { new_config->cli_debug = $3; }
 | DEBUG COMMANDS expr { new_config->cli_debug = $3; }
 | DEBUG PIPE bool { new_config->pipe_debug = $3; }
 ;
 ;


/* MRTDUMP PROTOCOLS is in systep/unix/config.Y */
/* MRTDUMP PROTOCOLS is in systep/unix/config.Y */
+4 −1
Original line number Original line Diff line number Diff line
@@ -162,7 +162,6 @@ typedef struct rtable {
  char *name;				/* Name of this table */
  char *name;				/* Name of this table */
  list channels;			/* List of attached channels (struct channel) */
  list channels;			/* List of attached channels (struct channel) */
  uint addr_type;			/* Type of address data stored in table (NET_*) */
  uint addr_type;			/* Type of address data stored in table (NET_*) */
  int pipe_busy;			/* Pipe loop detection */
  int use_count;			/* Number of protocols using this table */
  int use_count;			/* Number of protocols using this table */
  u32 rt_count;				/* Number of routes in the table */
  u32 rt_count;				/* Number of routes in the table */


@@ -185,6 +184,7 @@ typedef struct rtable {
  byte nhu_state;			/* Next Hop Update state */
  byte nhu_state;			/* Next Hop Update state */
  struct fib_iterator prune_fit;	/* Rtable prune FIB iterator */
  struct fib_iterator prune_fit;	/* Rtable prune FIB iterator */
  struct fib_iterator nhu_fit;		/* Next Hop Update FIB iterator */
  struct fib_iterator nhu_fit;		/* Next Hop Update FIB iterator */
  struct tbf rl_pipe;			/* Rate limiting token buffer for pipe collisions */


  list subscribers;			/* Subscribers for notifications */
  list subscribers;			/* Subscribers for notifications */
  struct timer *settle_timer;		/* Settle time for notifications */
  struct timer *settle_timer;		/* Settle time for notifications */
@@ -243,6 +243,9 @@ typedef struct rte {
  u32 id;				/* Table specific route id */
  u32 id;				/* Table specific route id */
  byte flags;				/* Table-specific flags */
  byte flags;				/* Table-specific flags */
  byte pflags;				/* Protocol-specific flags */
  byte pflags;				/* Protocol-specific flags */
  u8 generation;			/* If this route import is based on other previously exported route,
					   this value should be 1 + MAX(generation of the parent routes).
					   Otherwise the route is independent and this value is zero. */
} rte;
} rte;


struct rte_storage {
struct rte_storage {
+24 −23
Original line number Original line Diff line number Diff line
@@ -837,7 +837,6 @@ rte_recalculate(struct channel *c, net *net, rte *new, struct rte_src *src)
  struct proto *p = c->proto;
  struct proto *p = c->proto;
  struct rtable *table = c->table;
  struct rtable *table = c->table;
  struct proto_stats *stats = &c->stats;
  struct proto_stats *stats = &c->stats;
  static struct tbf rl_pipe = TBF_DEFAULT_LOG_LIMITS;
  struct rte_storage *old_best_stored = net->routes, *old_stored = NULL;
  struct rte_storage *old_best_stored = net->routes, *old_stored = NULL;
  rte *old_best = old_best_stored ? &old_best_stored->rte : NULL;
  rte *old_best = old_best_stored ? &old_best_stored->rte : NULL;
  rte *old = NULL;
  rte *old = NULL;
@@ -853,16 +852,16 @@ rte_recalculate(struct channel *c, net *net, rte *new, struct rte_src *src)
       * a different sender, then there are two paths from the
       * a different sender, then there are two paths from the
       * source protocol to this routing table through transparent
       * source protocol to this routing table through transparent
       * pipes, which is not allowed.
       * pipes, which is not allowed.
	   *
       * We log that and ignore the route. */
	   * We log that and ignore the route. If it is withdraw, we
	   * ignore it completely (there might be 'spurious withdraws',
	   * see FIXME in do_rte_announce())
	   */
      if (old->sender->proto != p)
      if (old->sender->proto != p)
	{
	{
	      if (new)
	  if (!old->generation && !new->generation)
		  log_rl(&rl_pipe, L_ERR "Pipe collision detected when sending %N to table %s",
	    bug("Two protocols claim to author a route with the same rte_src in table %s: %N %s/%u:%u",
		      net->n.addr, table->name);
		c->table->name, net->n.addr, old->src->proto->name, old->src->private_id, old->src->global_id);

	  log_rl(&table->rl_pipe, L_ERR "Route source collision in table %s: %N %s/%u:%u",
		c->table->name, net->n.addr, old->src->proto->name, old->src->private_id, old->src->global_id);

	  return;
	  return;
	}
	}


@@ -881,6 +880,7 @@ rte_recalculate(struct channel *c, net *net, rte *new, struct rte_src *src)
	    return;
	    return;
	  }
	  }



	*before_old = (*before_old)->next;
	*before_old = (*before_old)->next;
	table->rt_count--;
	table->rt_count--;
    }
    }
@@ -1128,7 +1128,6 @@ rte_update(struct channel *c, const net_addr *n, rte *new, struct rte_src *src)
  if (c->in_table && !rte_update_in(c, n, new, src))
  if (c->in_table && !rte_update_in(c, n, new, src))
    return;
    return;


  // struct proto *p = c->proto;
  struct proto_stats *stats = &c->stats;
  struct proto_stats *stats = &c->stats;
  const struct filter *filter = c->in_filter;
  const struct filter *filter = c->in_filter;
  net *nn;
  net *nn;
@@ -1595,6 +1594,8 @@ rt_setup(pool *pp, struct rtable_config *cf)


    t->rt_event = ev_new_init(p, rt_event, t);
    t->rt_event = ev_new_init(p, rt_event, t);
    t->last_rt_change = t->gc_time = current_time();
    t->last_rt_change = t->gc_time = current_time();

    t->rl_pipe = (struct tbf) TBF_DEFAULT_LOG_LIMITS;
  }
  }


  return t;
  return t;
Loading