mirror of
https://git.proxmox.com/git/mirror_frr
synced 2025-04-28 15:36:25 +00:00
isisd: delay lsp regeneration while events are still coming in
When there is a stream of events coming in, where IS-IS learns about a lot of updates, IS-IS would regenerate its LSPs before the updates have been processed completely. This causes suboptimal convergence because the intermediate state will be flooded. Only after the configured `lsp_gen_interval`, a new update with the correct and final state will be generated. Resolve this by holding off LSP generation while there are still events coming in. Signed-off-by: Christian Franke <chris@opensourcerouting.org>
This commit is contained in:
parent
9196731f9d
commit
f93025e1a6
@ -1361,6 +1361,14 @@ static int lsp_refresh(struct thread *thread)
|
||||
if ((area->is_type & level) == 0)
|
||||
return ISIS_ERROR;
|
||||
|
||||
if (monotime_since(&area->last_lsp_refresh_event[level - 1], NULL) < 50000L) {
|
||||
sched_debug("ISIS (%s): Still unstable, postpone LSP L%d refresh",
|
||||
area->area_tag, level);
|
||||
_lsp_regenerate_schedule(area, level, 0, false,
|
||||
__func__, __FILE__, __LINE__);
|
||||
return 0;
|
||||
}
|
||||
|
||||
sched_debug(
|
||||
"ISIS (%s): LSP L%d refresh timer expired. Refreshing LSP...",
|
||||
area->area_tag, level);
|
||||
@ -1368,8 +1376,9 @@ static int lsp_refresh(struct thread *thread)
|
||||
}
|
||||
|
||||
int _lsp_regenerate_schedule(struct isis_area *area, int level,
|
||||
int all_pseudo, const char *func,
|
||||
const char *file, int line)
|
||||
int all_pseudo, bool postpone,
|
||||
const char *func, const char *file,
|
||||
int line)
|
||||
{
|
||||
struct isis_lsp *lsp;
|
||||
uint8_t id[ISIS_SYS_ID_LEN + 2];
|
||||
@ -1397,6 +1406,10 @@ int _lsp_regenerate_schedule(struct isis_area *area, int level,
|
||||
if (!((level & lvl) && (area->is_type & lvl)))
|
||||
continue;
|
||||
|
||||
if (postpone) {
|
||||
monotime(&area->last_lsp_refresh_event[lvl - 1]);
|
||||
}
|
||||
|
||||
sched_debug(
|
||||
"ISIS (%s): Checking whether L%d needs to be scheduled",
|
||||
area->area_tag, lvl);
|
||||
|
@ -55,11 +55,11 @@ int lsp_tick(struct thread *thread);
|
||||
|
||||
int lsp_generate(struct isis_area *area, int level);
|
||||
#define lsp_regenerate_schedule(area, level, all_pseudo) \
|
||||
_lsp_regenerate_schedule((area), (level), (all_pseudo), \
|
||||
_lsp_regenerate_schedule((area), (level), (all_pseudo), true, \
|
||||
__func__, __FILE__, __LINE__)
|
||||
int _lsp_regenerate_schedule(struct isis_area *area, int level,
|
||||
int all_pseudo, const char *func,
|
||||
const char *file, int line);
|
||||
int all_pseudo, bool postpone,
|
||||
const char *func, const char *file, int line);
|
||||
int lsp_generate_pseudo(struct isis_circuit *circuit, int level);
|
||||
int lsp_regenerate_schedule_pseudo(struct isis_circuit *circuit, int level);
|
||||
|
||||
|
@ -105,6 +105,7 @@ struct isis_area {
|
||||
struct flags flags;
|
||||
struct thread *t_tick; /* LSP walker */
|
||||
struct thread *t_lsp_refresh[ISIS_LEVELS];
|
||||
struct timeval last_lsp_refresh_event[ISIS_LEVELS];
|
||||
/* t_lsp_refresh is used in two ways:
|
||||
* a) regular refresh of LSPs
|
||||
* b) (possibly throttled) updates to LSPs
|
||||
|
Loading…
Reference in New Issue
Block a user