#include "isis_constants.h"
#include "isis_common.h"
#include "isis_flags.h"
-#include "dict.h"
#include "isisd.h"
#include "isis_misc.h"
#include "isis_adjacency.h"
return NULL; /* Not reached */
}
-#define VID2STR_BUFFER SRCDEST2STR_BUFFER
-static const char *vid2string(struct isis_vertex *vertex, char *buff, int size)
+const char *vid2string(struct isis_vertex *vertex, char *buff, int size)
{
if (VTYPE_IS(vertex->type) || VTYPE_ES(vertex->type)) {
return print_sys_hostname(vertex->N.id);
return "UNKNOWN";
}
-static struct isis_vertex *isis_vertex_new(union isis_N *n,
+static struct isis_vertex *isis_vertex_new(struct isis_spftree *spftree,
+ void *id,
enum vertextype vtype)
{
struct isis_vertex *vertex;
vertex = XCALLOC(MTYPE_ISIS_VERTEX, sizeof(struct isis_vertex));
- isis_vertex_id_init(vertex, n, vtype);
+ isis_vertex_id_init(vertex, id, vtype);
vertex->Adj_N = list_new();
vertex->parents = list_new();
+ if (spftree->hopcount_metric) {
+ vertex->firsthops = hash_create(isis_vertex_queue_hash_key,
+ isis_vertex_queue_hash_cmp,
+ NULL);
+ }
+
return vertex;
}
memcpy(lspid, sysid, ISIS_SYS_ID_LEN);
LSP_PSEUDO_ID(lspid) = 0;
LSP_FRAGMENT(lspid) = 0;
- lsp = lsp_search(lspid, area->lspdb[level - 1]);
+ lsp = lsp_search(&area->lspdb[level - 1], lspid);
if (lsp && lsp->hdr.rem_lifetime != 0)
return lsp;
return NULL;
#ifdef EXTREME_DEBUG
char buff[VID2STR_BUFFER];
#endif /* EXTREME_DEBUG */
- union isis_N n;
-
- memcpy(n.id, sysid, ISIS_SYS_ID_LEN);
- LSP_PSEUDO_ID(n.id) = 0;
lsp = isis_root_system_lsp(spftree->area, spftree->level, sysid);
if (lsp == NULL)
zlog_warn("ISIS-Spf: could not find own l%d LSP!",
spftree->level);
- vertex = isis_vertex_new(&n,
+ vertex = isis_vertex_new(spftree, sysid,
spftree->area->oldmetric
? VTYPE_NONPSEUDO_IS
: VTYPE_NONPSEUDO_TE_IS);
return vertex;
}
+static void vertex_add_parent_firsthop(struct hash_bucket *bucket, void *arg)
+{
+ struct isis_vertex *vertex = arg;
+ struct isis_vertex *hop = bucket->data;
+
+ hash_get(vertex->firsthops, hop, hash_alloc_intern);
+}
+
+static void vertex_update_firsthops(struct isis_vertex *vertex,
+ struct isis_vertex *parent)
+{
+ if (vertex->d_N <= 2)
+ hash_get(vertex->firsthops, vertex, hash_alloc_intern);
+
+ if (vertex->d_N < 2 || !parent)
+ return;
+
+ hash_iterate(parent->firsthops, vertex_add_parent_firsthop, vertex);
+}
+
/*
* Add a vertex to TENT sorted by cost and by vertextype on tie break situation
*/
assert(isis_find_vertex(&spftree->paths, id, vtype) == NULL);
assert(isis_find_vertex(&spftree->tents, id, vtype) == NULL);
- vertex = isis_vertex_new(id, vtype);
+ vertex = isis_vertex_new(spftree, id, vtype);
vertex->d_N = cost;
vertex->depth = depth;
listnode_add(vertex->parents, parent);
}
+ if (spftree->hopcount_metric)
+ vertex_update_firsthops(vertex, parent);
+
if (parent && parent->Adj_N && listcount(parent->Adj_N) > 0) {
for (ALL_LIST_ELEMENTS_RO(parent->Adj_N, node, parent_adj))
listnode_add(vertex->Adj_N, parent_adj);
if (listnode_lookup(vertex->Adj_N, parent_adj)
== NULL)
listnode_add(vertex->Adj_N, parent_adj);
+ if (spftree->hopcount_metric)
+ vertex_update_firsthops(vertex, parent);
/* 2) */
if (listcount(vertex->Adj_N) > ISIS_MAX_PATH_SPLITS)
remove_excess_adjs(vertex->Adj_N);
for (r = (struct isis_oldstyle_reach *)
lsp->tlvs->oldstyle_reach.head;
r; r = r->next) {
+ if (fabricd)
+ continue;
+
/* C.2.6 a) */
/* Two way connectivity */
if (!memcmp(r->id, root_sysid, ISIS_SYS_ID_LEN))
}
}
- if (!pseudo_lsp && spftree->family == AF_INET
+ if (!fabricd && !pseudo_lsp && spftree->family == AF_INET
&& spftree->mtid == ISIS_MT_IPV4_UNICAST) {
struct isis_item_list *reachs[] = {
&lsp->tlvs->oldstyle_ip_reach,
adjdb = circuit->u.bc.adjdb[spftree->level - 1];
isis_adj_build_up_list(adjdb, adj_list);
if (listcount(adj_list) == 0) {
- list_delete_and_null(&adj_list);
+ list_delete(&adj_list);
if (isis->debugs & DEBUG_SPF_EVENTS)
zlog_debug(
"ISIS-Spf: no L%d adjacencies on circuit %s",
[spftree->level - 1],
parent);
lsp = lsp_search(
- lsp_id,
- spftree->area
- ->lspdb[spftree->level
- - 1]);
+ &spftree->area->lspdb[spftree->level- 1],
+ lsp_id);
if (lsp == NULL
|| lsp->hdr.rem_lifetime == 0)
zlog_warn(
case ISIS_SYSTYPE_UNKNOWN:
default:
zlog_warn(
- "isis_spf_preload_tent unknow adj type");
+ "isis_spf_preload_tent unknown adj type");
}
}
- list_delete_and_null(&adj_list);
+ list_delete(&adj_list);
/*
* Add the pseudonode
*/
continue;
}
lsp = lsp_search(
- lsp_id,
- spftree->area->lspdb[spftree->level - 1]);
+ &spftree->area->lspdb[spftree->level - 1],
+ lsp_id);
if (lsp == NULL || lsp->hdr.rem_lifetime == 0) {
zlog_warn(
"ISIS-Spf: No lsp (%p) found from root "
lsp = lsp_for_vertex(spftree, vertex);
if (!lsp) {
zlog_warn("ISIS-Spf: No LSP found for %s",
- rawlspid_print(vertex->N.id)); /* FIXME */
+ isis_format_id(vertex->N.id,
+ sizeof(vertex->N.id)));
continue;
}
isis_spf_preload_tent(spftree, sysid, root);
} else {
isis_vertex_queue_insert(&spftree->tents, isis_vertex_new(
- sysid, VTYPE_NONPSEUDO_TE_IS));
+ spftree, sysid,
+ VTYPE_NONPSEUDO_TE_IS));
}
isis_spf_loop(spftree, sysid);
return run;
}
-int isis_spf_schedule(struct isis_area *area, int level)
+int _isis_spf_schedule(struct isis_area *area, int level,
+ const char *func, const char *file, int line)
{
struct isis_spftree *spftree = area->spftree[SPFTREE_IPV4][level - 1];
time_t now = monotime(NULL);
assert(diff >= 0);
assert(area->is_type & level);
- if (isis->debugs & DEBUG_SPF_EVENTS)
+ if (isis->debugs & DEBUG_SPF_EVENTS) {
zlog_debug(
- "ISIS-Spf (%s) L%d SPF schedule called, lastrun %d sec ago",
- area->area_tag, level, diff);
+ "ISIS-Spf (%s) L%d SPF schedule called, lastrun %d sec ago"
+ " Caller: %s %s:%d",
+ area->area_tag, level, diff, func, file, line);
+ }
if (area->spf_delay_ietf[level - 1]) {
/* Need to call schedule function also if spf delay is running
return CMD_SUCCESS;
}
-void isis_spf_cmds_init()
+void isis_spf_cmds_init(void)
{
install_element(VIEW_NODE, &show_isis_topology_cmd);
}