channel_request_reload(c);
}
+static void
+channel_roa_out_reload_done(struct channel_feeding_request *req)
+{
+ rfree(req->trie->lp);
+}
+
static void
channel_roa_out_changed(struct settle *se)
{
CD(c, "Feeding triggered by RPKI change");
- /* TODO feed by trie */
-
- /* Refeed already pending */
- if ((s->cfr[0].state == CFRS_PENDING) || (s->cfr[1].state == CFRS_PENDING))
- return;
+ struct channel_feeding_request *cfr = lp_alloc(s->trie->lp, sizeof *cfr);
+ *cfr = (struct channel_feeding_request) {
+ .type = CFRT_AUXILIARY,
+ .trie = s->trie,
+ .done = channel_roa_out_reload_done,
+ };
+ channel_request_feeding(c, cfr);
- /* First refeed inactive */
- if (s->cfr[0].state == CFRS_INACTIVE)
- {
- s->cfr[0].type = CFRT_AUXILIARY;
- channel_request_feeding(c, &s->cfr[0]);
- }
- else
- {
- /* Second refeed MUST be inactive */
- ASSERT_DIE(s->cfr[1].state == CFRS_INACTIVE);
- s->cfr[1].type = CFRT_AUXILIARY;
- channel_request_feeding(c, &s->cfr[1]);
- }
+ s->trie = f_new_trie(lp_new(c->proto->pool), 0);
}
static void
struct channel_feeding_request {
struct channel_feeding_request *next; /* Next in request chain */
void (*done)(struct channel_feeding_request *); /* Called when refeed finishes */
+ struct f_trie *trie; /* Reload only matching nets */
PACKED enum channel_feeding_request_type {
CFRT_DIRECT = 1, /* Refeed by export restart */
CFRT_AUXILIARY, /* Refeed by auxiliary request */
void channel_request_feeding_dynamic(struct channel *c, enum channel_feeding_request_type);
static inline int channel_net_is_refeeding(struct channel *c, const net_addr *n)
-{ return (c->refeeding && c->refeed_trie && !trie_match_net(c->refeed_trie, n)); }
+{
+ /* Not refeeding if not refeeding at all */
+ if (!c->refeeding || !c->refeed_trie)
+ return 0;
+
+ /* Not refeeding if already refed */
+ if (trie_match_net(c->refeed_trie, n))
+ return 0;
+
+ /* Refeeding if matching any request */
+ for (struct channel_feeding_request *cfr = c->refeeding; cfr; cfr = cfr->next)
+ if (!cfr->trie || trie_match_net(cfr->trie, n))
+ return 1;
+
+ /* Not matching any request */
+ return 0;
+}
static inline void channel_net_mark_refed(struct channel *c, const net_addr *n)
{
ASSERT_DIE(c->refeeding && c->refeed_trie);
trie_add_prefix(c->refeed_trie, n, n->pxlen, n->pxlen);
}
+
void *channel_config_new(const struct channel_class *cc, const char *name, uint net_type, struct proto_config *proto);
void *channel_config_get(const struct channel_class *cc, const char *name, uint net_type, struct proto_config *proto);
int channel_reconfigure(struct channel *c, struct channel_config *cf);