isisd: support for snmp

Add support for read only mib objects from RFC4444.

Signed-off-by: Lynne Morrison <lynne@voltanet.io>
Signed-off-by: Karen Schoener <karen@voltanet.io>
This commit is contained in:
lynne 2020-09-15 16:46:15 -04:00
parent 9ee2ebdc82
commit 1ee746d990
19 changed files with 3979 additions and 105 deletions

View File

@ -49,13 +49,21 @@
#include "isisd/fabricd.h"
#include "isisd/isis_nb.h"
static struct isis_adjacency *adj_alloc(const uint8_t *id)
static struct isis_adjacency *adj_alloc(struct isis_circuit *circuit,
const uint8_t *id)
{
struct isis_adjacency *adj;
adj = XCALLOC(MTYPE_ISIS_ADJACENCY, sizeof(struct isis_adjacency));
memcpy(adj->sysid, id, ISIS_SYS_ID_LEN);
adj->snmp_idx = ++circuit->snmp_adj_idx_gen;
if (circuit->snmp_adj_list == NULL)
circuit->snmp_adj_list = list_new();
adj->snmp_list_node = listnode_add(circuit->snmp_adj_list, adj);
return adj;
}
@ -65,7 +73,7 @@ struct isis_adjacency *isis_new_adj(const uint8_t *id, const uint8_t *snpa,
struct isis_adjacency *adj;
int i;
adj = adj_alloc(id); /* P2P kludge */
adj = adj_alloc(circuit, id); /* P2P kludge */
if (snpa) {
memcpy(adj->snpa, snpa, ETH_ALEN);
@ -146,6 +154,8 @@ void isis_delete_adj(void *arg)
if (!adj)
return;
/* Remove self from snmp list without walking the list*/
list_delete_node(adj->circuit->snmp_adj_list, adj->snmp_list_node);
thread_cancel(&adj->t_expire);
if (adj->adj_state != ISIS_ADJ_DOWN)
@ -292,7 +302,6 @@ void isis_adj_state_change(struct isis_adjacency **padj,
if (circuit->area->log_adj_changes)
isis_log_adj_change(adj, old_state, new_state, reason);
circuit->adj_state_changes++;
#ifndef FABRICD
/* send northbound notification */
isis_notif_adj_state_change(adj, new_state, reason);
@ -303,12 +312,14 @@ void isis_adj_state_change(struct isis_adjacency **padj,
if ((adj->level & level) == 0)
continue;
if (new_state == ISIS_ADJ_UP) {
circuit->adj_state_changes++;
circuit->upadjcount[level - 1]++;
/* update counter & timers for debugging
* purposes */
adj->last_flap = time(NULL);
adj->flaps++;
} else if (old_state == ISIS_ADJ_UP) {
circuit->adj_state_changes++;
listnode_delete(circuit->u.bc.adjdb[level - 1],
adj);

View File

@ -105,6 +105,8 @@ struct isis_adjacency {
unsigned int mt_count; /* Number of entries in mt_set */
struct bfd_session *bfd_session;
struct list *adj_sids; /* Segment Routing Adj-SIDs. */
uint32_t snmp_idx;
struct listnode *snmp_list_node;
};
struct isis_threeway_adj;

View File

@ -71,6 +71,48 @@ DEFINE_HOOK(isis_if_new_hook, (struct interface *ifp), (ifp))
int isis_if_new_hook(struct interface *);
int isis_if_delete_hook(struct interface *);
static int isis_circuit_smmp_id_gen(struct isis_circuit *circuit)
{
struct vrf *vrf = vrf_lookup_by_id(VRF_DEFAULT);
struct isis *isis = NULL;
uint32_t id;
uint32_t i;
isis = isis_lookup_by_vrfid(vrf->vrf_id);
if (isis == NULL)
return 0;
id = isis->snmp_circuit_id_last;
id++;
/* find next unused entry */
for (i = 0; i < SNMP_CIRCUITS_MAX; i++) {
if (id >= SNMP_CIRCUITS_MAX) {
id = 0;
continue;
}
if (id == 0)
continue;
if (isis->snmp_circuits[id] == NULL)
break;
id++;
}
if (i == SNMP_CIRCUITS_MAX) {
zlog_warn("Could not allocate a smmp-circuit-id");
return 0;
}
isis->snmp_circuits[id] = circuit;
isis->snmp_circuit_id_last = id;
circuit->snmp_id = id;
return 1;
}
struct isis_circuit *isis_circuit_new(struct isis *isis)
{
struct isis_circuit *circuit;
@ -79,6 +121,12 @@ struct isis_circuit *isis_circuit_new(struct isis *isis)
circuit = XCALLOC(MTYPE_ISIS_CIRCUIT, sizeof(struct isis_circuit));
circuit->isis = isis;
/*
* Note: if snmp-id generation failed circuit will fail
* up operation
*/
isis_circuit_smmp_id_gen(circuit);
/*
* Default values
*/
@ -150,11 +198,18 @@ struct isis_circuit *isis_circuit_new(struct isis *isis)
void isis_circuit_del(struct isis_circuit *circuit)
{
struct isis *isis = NULL;
if (!circuit)
return;
QOBJ_UNREG(circuit);
if (circuit->interface) {
isis = isis_lookup_by_vrfid(circuit->interface->vrf_id);
isis->snmp_circuits[circuit->snmp_id] = NULL;
}
isis_circuit_if_unbind(circuit, circuit->interface);
circuit_mt_finish(circuit);
@ -609,6 +664,7 @@ int isis_circuit_up(struct isis_circuit *circuit)
return ISIS_OK;
if (circuit->is_passive) {
circuit->last_uptime = time(NULL);
/* make sure the union fields are initialized, else we
* could end with garbage values from a previous circuit
* type, which would then cause a segfault when building
@ -623,6 +679,13 @@ int isis_circuit_up(struct isis_circuit *circuit)
return ISIS_OK;
}
if (circuit->snmp_id == 0) {
/* We cannot bring circuit up if does not have snmp-id */
flog_err(EC_ISIS_CONFIG,
"No snnmp-id: there are too many circuits:");
return ISIS_ERROR;
}
if (circuit->area->lsp_mtu > isis_circuit_pdu_size(circuit)) {
flog_err(
EC_ISIS_CONFIG,
@ -722,6 +785,8 @@ int isis_circuit_up(struct isis_circuit *circuit)
circuit->tx_queue = isis_tx_queue_new(circuit, send_lsp);
circuit->last_uptime = time(NULL);
#ifndef FABRICD
/* send northbound notification */
isis_notif_if_state_change(circuit, false);
@ -828,6 +893,15 @@ void isis_circuit_down(struct isis_circuit *circuit)
thread_cancel(&circuit->u.p2p.t_send_p2p_hello);
}
/*
* All adjacencies have to be gone, delete snmp list
* and reset snmpd idx generator
*/
if (circuit->snmp_adj_list != NULL)
list_delete(&circuit->snmp_adj_list);
circuit->snmp_adj_idx_gen = 0;
/* Cancel all active threads */
thread_cancel(&circuit->t_send_csnp[0]);
thread_cancel(&circuit->t_send_csnp[1]);

View File

@ -79,6 +79,7 @@ struct isis_circuit_arg {
struct isis_circuit {
int state;
uint8_t circuit_id; /* l1/l2 bcast CircuitID */
time_t last_uptime;
struct isis *isis;
struct isis_area *area; /* back pointer to the area */
struct interface *interface; /* interface info from z */
@ -115,6 +116,8 @@ struct isis_circuit {
int pad_hellos; /* add padding to Hello PDUs ? */
char ext_domain; /* externalDomain (boolean) */
int lsp_regenerate_pending[ISIS_LEVELS];
uint64_t lsp_error_counter;
/*
* Configurables
*/
@ -165,6 +168,12 @@ struct isis_circuit {
uint32_t auth_type_failures; /*authentication-type-fails */
uint32_t auth_failures; /* authentication-fails */
uint32_t snmp_id; /* Circuit id in snmp */
uint32_t snmp_adj_idx_gen; /* Create unique id for adjacency on creation
*/
struct list *snmp_adj_list; /* List in id order */
QOBJ_FIELDS
};
DECLARE_QOBJ_TYPE(isis_circuit)

View File

@ -97,6 +97,7 @@ static int isis_check_dr_change(struct isis_adjacency *adj, int level)
/* was there a DIS state transition ? */
{
adj->dischanges[level - 1]++;
adj->circuit->desig_changes[level - 1]++;
/* ok rotate the history list through */
for (i = DIS_RECORDS - 1; i > 0; i--) {
adj->dis_record[(i * ISIS_LEVELS) + level - 1].dis =

View File

@ -166,3 +166,38 @@ void dynhn_print_all(struct vty *vty, struct isis *isis)
cmd_hostname_get());
return;
}
struct isis_dynhn *dynhn_snmp_next(const uint8_t *id, int level)
{
struct listnode *node = NULL;
struct isis_dynhn *dyn = NULL;
struct isis_dynhn *found_dyn = NULL;
int res;
for (ALL_LIST_ELEMENTS_RO(dyn_cache, node, dyn)) {
res = memcmp(dyn->id, id, ISIS_SYS_ID_LEN);
if (res < 0)
continue;
if (res == 0 && dyn->level <= level)
continue;
if (res == 0) {
/*
* This is the best match, we can stop
* searching
*/
found_dyn = dyn;
break;
}
if (found_dyn == NULL
|| memcmp(dyn->id, found_dyn->id, ISIS_SYS_ID_LEN) < 0) {
found_dyn = dyn;
}
}
return found_dyn;
}

View File

@ -38,4 +38,7 @@ struct isis_dynhn *dynhn_find_by_id(const uint8_t *id);
struct isis_dynhn *dynhn_find_by_name(const char *hostname);
void dynhn_print_all(struct vty *vty, struct isis *isis);
/* Snmp support */
struct isis_dynhn *dynhn_snmp_next(const uint8_t *id, int level);
#endif /* _ZEBRA_ISIS_DYNHN_H */

View File

@ -324,8 +324,8 @@ void lsp_inc_seqno(struct isis_lsp *lsp, uint32_t seqno)
/* check for overflow */
if (newseq < lsp->hdr.seqno) {
/* send northbound notification */
isis_notif_lsp_exceed_max(lsp->area,
rawlspid_print(lsp->hdr.lsp_id));
lsp->area->lsp_exceeded_max_counter++;
isis_notif_lsp_exceed_max(lsp->area, lsp->hdr.lsp_id);
}
#endif /* ifndef FABRICD */
@ -1357,8 +1357,8 @@ int lsp_generate(struct isis_area *area, int level)
#ifndef FABRICD
/* send northbound notification */
isis_notif_lsp_gen(area, rawlspid_print(newlsp->hdr.lsp_id),
newlsp->hdr.seqno, newlsp->last_generated);
isis_notif_lsp_gen(area, newlsp->hdr.lsp_id, newlsp->hdr.seqno,
newlsp->last_generated);
#endif /* ifndef FABRICD */
return ISIS_OK;

View File

@ -553,40 +553,97 @@ void cli_show_isis_mpls_if_ldp_sync_holddown(struct vty *vty,
/* Notifications. */
void isis_notif_db_overload(const struct isis_area *area, bool overload);
void isis_notif_lsp_too_large(const struct isis_circuit *circuit,
uint32_t pdu_size, const char *lsp_id);
uint32_t pdu_size, const uint8_t *lsp_id);
void isis_notif_if_state_change(const struct isis_circuit *circuit, bool down);
void isis_notif_corrupted_lsp(const struct isis_area *area,
const char *lsp_id); /* currently unused */
const uint8_t *lsp_id); /* currently unused */
void isis_notif_lsp_exceed_max(const struct isis_area *area,
const char *lsp_id);
const uint8_t *lsp_id);
void isis_notif_max_area_addr_mismatch(const struct isis_circuit *circuit,
uint8_t max_area_addrs,
const char *raw_pdu);
const char *raw_pdu, size_t raw_pdu_len);
void isis_notif_authentication_type_failure(const struct isis_circuit *circuit,
const char *raw_pdu);
const char *raw_pdu,
size_t raw_pdu_len);
void isis_notif_authentication_failure(const struct isis_circuit *circuit,
const char *raw_pdu);
const char *raw_pdu, size_t raw_pdu_len);
void isis_notif_adj_state_change(const struct isis_adjacency *adj,
int new_state, const char *reason);
void isis_notif_reject_adjacency(const struct isis_circuit *circuit,
const char *reason, const char *raw_pdu);
const char *reason, const char *raw_pdu,
size_t raw_pdu_len);
void isis_notif_area_mismatch(const struct isis_circuit *circuit,
const char *raw_pdu);
const char *raw_pdu, size_t raw_pdu_len);
void isis_notif_lsp_received(const struct isis_circuit *circuit,
const char *lsp_id, uint32_t seqno,
const uint8_t *lsp_id, uint32_t seqno,
uint32_t timestamp, const char *sys_id);
void isis_notif_lsp_gen(const struct isis_area *area, const char *lsp_id,
void isis_notif_lsp_gen(const struct isis_area *area, const uint8_t *lsp_id,
uint32_t seqno, uint32_t timestamp);
void isis_notif_id_len_mismatch(const struct isis_circuit *circuit,
uint8_t rcv_id_len, const char *raw_pdu);
uint8_t rcv_id_len, const char *raw_pdu,
size_t raw_pdu_len);
void isis_notif_version_skew(const struct isis_circuit *circuit,
uint8_t version, const char *raw_pdu);
uint8_t version, const char *raw_pdu,
size_t raw_pdu_len);
void isis_notif_lsp_error(const struct isis_circuit *circuit,
const char *lsp_id, const char *raw_pdu,
uint32_t offset, uint8_t tlv_type);
const uint8_t *lsp_id, const char *raw_pdu,
size_t raw_pdu_len, uint32_t offset,
uint8_t tlv_type);
void isis_notif_seqno_skipped(const struct isis_circuit *circuit,
const char *lsp_id);
const uint8_t *lsp_id);
void isis_notif_own_lsp_purge(const struct isis_circuit *circuit,
const char *lsp_id);
const uint8_t *lsp_id);
/* We also declare hook for every notification */
DECLARE_HOOK(isis_hook_db_overload, (const struct isis_area *area), (area));
DECLARE_HOOK(isis_hook_lsp_too_large,
(const struct isis_circuit *circuit, uint32_t pdu_size,
const uint8_t *lsp_id),
(circuit, pdu_size, lsp_id));
/* Note: no isis_hook_corrupted_lsp - because this notificaiton is not used */
DECLARE_HOOK(isis_hook_lsp_exceed_max,
(const struct isis_area *area, const uint8_t *lsp_id),
(area, lsp_id));
DECLARE_HOOK(isis_hook_max_area_addr_mismatch,
(const struct isis_circuit *circuit, uint8_t max_addrs,
const char *raw_pdu, size_t raw_pdu_len),
(circuit, max_addrs, raw_pdu, raw_pdu_len));
DECLARE_HOOK(isis_hook_authentication_type_failure,
(const struct isis_circuit *circuit, const char *raw_pdu,
size_t raw_pdu_len),
(circuit, raw_pdu, raw_pdu_len));
DECLARE_HOOK(isis_hook_authentication_failure,
(const struct isis_circuit *circuit, const char *raw_pdu,
size_t raw_pdu_len),
(circuit, raw_pdu, raw_pdu_len));
DECLARE_HOOK(isis_hook_adj_state_change, (const struct isis_adjacency *adj),
(adj));
DECLARE_HOOK(isis_hook_reject_adjacency,
(const struct isis_circuit *circuit, const char *pdu,
size_t pdu_len),
(circuit, pdu, pdu_len));
DECLARE_HOOK(isis_hook_area_mismatch,
(const struct isis_circuit *circuit, const char *raw_pdu,
size_t raw_pdu_len),
(circuit));
DECLARE_HOOK(isis_hook_id_len_mismatch,
(const struct isis_circuit *circuit, uint8_t rcv_id_len,
const char *raw_pdu, size_t raw_pdu_len),
(circuit, rcv_id_len, raw_pdu, raw_pdu_len));
DECLARE_HOOK(isis_hook_version_skew,
(const struct isis_circuit *circuit, uint8_t version,
const char *raw_pdu, size_t raw_pdu_len),
(circuit));
DECLARE_HOOK(isis_hook_lsp_error,
(const struct isis_circuit *circuit, const uint8_t *lsp_id,
const char *raw_pdu, size_t raw_pdu_len),
(circuit));
DECLARE_HOOK(isis_hook_seqno_skipped,
(const struct isis_circuit *circuit, const uint8_t *lsp_id),
(circuit, lsp_id));
DECLARE_HOOK(isis_hook_own_lsp_purge,
(const struct isis_circuit *circuit, const uint8_t *lsp_id),
(circuit, lsp_id));
#endif /* ISISD_ISIS_NB_H_ */

View File

@ -28,6 +28,56 @@
#include "isisd/isis_dynhn.h"
#include "isisd/isis_misc.h"
DEFINE_HOOK(isis_hook_lsp_too_large,
(const struct isis_circuit *circuit, uint32_t pdu_size,
const uint8_t *lsp_id),
(circuit, pdu_size, lsp_id));
DEFINE_HOOK(isis_hook_corrupted_lsp, (const struct isis_area *area), (area));
DEFINE_HOOK(isis_hook_lsp_exceed_max,
(const struct isis_area *area, const uint8_t *lsp_id),
(area, lsp_id));
DEFINE_HOOK(isis_hook_max_area_addr_mismatch,
(const struct isis_circuit *circuit, uint8_t max_addrs,
const char *raw_pdu, size_t raw_pdu_len),
(circuit, max_addrs, raw_pdu, raw_pdu_len));
DEFINE_HOOK(isis_hook_authentication_type_failure,
(const struct isis_circuit *circuit, const char *raw_pdu,
size_t raw_pdu_len),
(circuit, raw_pdu, raw_pdu_len));
DEFINE_HOOK(isis_hook_authentication_failure,
(const struct isis_circuit *circuit, const char *raw_pdu,
size_t raw_pdu_len),
(circuit, raw_pdu, raw_pdu_len));
DEFINE_HOOK(isis_hook_adj_state_change, (const struct isis_adjacency *adj),
(adj));
DEFINE_HOOK(isis_hook_reject_adjacency,
(const struct isis_circuit *circuit, const char *raw_pdu,
size_t raw_pdu_len),
(circuit, raw_pdu, raw_pdu_len));
DEFINE_HOOK(isis_hook_area_mismatch,
(const struct isis_circuit *circuit, const char *raw_pdu,
size_t raw_pdu_len),
(circuit, raw_pdu, raw_pdu_len));
DEFINE_HOOK(isis_hook_id_len_mismatch,
(const struct isis_circuit *circuit, uint8_t rcv_id_len,
const char *raw_pdu, size_t raw_pdu_len),
(circuit, rcv_id_len, raw_pdu, raw_pdu_len));
DEFINE_HOOK(isis_hook_version_skew,
(const struct isis_circuit *circuit, uint8_t version,
const char *raw_pdu, size_t raw_pdu_len),
(circuit, version, raw_pdu, raw_pdu_len));
DEFINE_HOOK(isis_hook_lsp_error,
(const struct isis_circuit *circuit, const uint8_t *lsp_id,
const char *raw_pdu, size_t raw_pdu_len),
(circuit, lsp_id, raw_pdu, raw_pdu_len));
DEFINE_HOOK(isis_hook_seqno_skipped,
(const struct isis_circuit *circuit, const uint8_t *lsp_id),
(circuit, lsp_id));
DEFINE_HOOK(isis_hook_own_lsp_purge,
(const struct isis_circuit *circuit, const uint8_t *lsp_id),
(circuit, lsp_id));
/*
* Helper functions.
*/
@ -92,7 +142,7 @@ void isis_notif_db_overload(const struct isis_area *area, bool overload)
* XPath: /frr-isisd:lsp-too-large
*/
void isis_notif_lsp_too_large(const struct isis_circuit *circuit,
uint32_t pdu_size, const char *lsp_id)
uint32_t pdu_size, const uint8_t *lsp_id)
{
const char *xpath = "/frr-isisd:lsp-too-large";
struct list *arguments = yang_data_list_new();
@ -106,9 +156,11 @@ void isis_notif_lsp_too_large(const struct isis_circuit *circuit,
data = yang_data_new_uint32(xpath_arg, pdu_size);
listnode_add(arguments, data);
snprintf(xpath_arg, sizeof(xpath_arg), "%s/lsp-id", xpath);
data = yang_data_new_string(xpath_arg, lsp_id);
data = yang_data_new_string(xpath_arg, rawlspid_print(lsp_id));
listnode_add(arguments, data);
hook_call(isis_hook_lsp_too_large, circuit, pdu_size, lsp_id);
nb_notification_send(xpath, arguments);
}
@ -135,7 +187,8 @@ void isis_notif_if_state_change(const struct isis_circuit *circuit, bool down)
/*
* XPath: /frr-isisd:corrupted-lsp-detected
*/
void isis_notif_corrupted_lsp(const struct isis_area *area, const char *lsp_id)
void isis_notif_corrupted_lsp(const struct isis_area *area,
const uint8_t *lsp_id)
{
const char *xpath = "/frr-isisd:corrupted-lsp-detected";
struct list *arguments = yang_data_list_new();
@ -144,16 +197,19 @@ void isis_notif_corrupted_lsp(const struct isis_area *area, const char *lsp_id)
notif_prep_instance_hdr(xpath, area, "default", arguments);
snprintf(xpath_arg, sizeof(xpath_arg), "%s/lsp-id", xpath);
data = yang_data_new_string(xpath_arg, lsp_id);
data = yang_data_new_string(xpath_arg, rawlspid_print(lsp_id));
listnode_add(arguments, data);
hook_call(isis_hook_corrupted_lsp, area);
nb_notification_send(xpath, arguments);
}
/*
* XPath: /frr-isisd:attempt-to-exceed-max-sequence
*/
void isis_notif_lsp_exceed_max(const struct isis_area *area, const char *lsp_id)
void isis_notif_lsp_exceed_max(const struct isis_area *area,
const uint8_t *lsp_id)
{
const char *xpath = "/frr-isisd:attempt-to-exceed-max-sequence";
struct list *arguments = yang_data_list_new();
@ -162,9 +218,11 @@ void isis_notif_lsp_exceed_max(const struct isis_area *area, const char *lsp_id)
notif_prep_instance_hdr(xpath, area, "default", arguments);
snprintf(xpath_arg, sizeof(xpath_arg), "%s/lsp-id", xpath);
data = yang_data_new_string(xpath_arg, lsp_id);
data = yang_data_new_string(xpath_arg, rawlspid_print(lsp_id));
listnode_add(arguments, data);
hook_call(isis_hook_lsp_exceed_max, area, lsp_id);
nb_notification_send(xpath, arguments);
}
@ -173,7 +231,7 @@ void isis_notif_lsp_exceed_max(const struct isis_area *area, const char *lsp_id)
*/
void isis_notif_max_area_addr_mismatch(const struct isis_circuit *circuit,
uint8_t max_area_addrs,
const char *raw_pdu)
const char *raw_pdu, size_t raw_pdu_len)
{
const char *xpath = "/frr-isisd:max-area-addresses-mismatch";
struct list *arguments = yang_data_list_new();
@ -190,6 +248,9 @@ void isis_notif_max_area_addr_mismatch(const struct isis_circuit *circuit,
data = yang_data_new(xpath_arg, raw_pdu);
listnode_add(arguments, data);
hook_call(isis_hook_max_area_addr_mismatch, circuit, max_area_addrs,
raw_pdu, raw_pdu_len);
nb_notification_send(xpath, arguments);
}
@ -197,7 +258,8 @@ void isis_notif_max_area_addr_mismatch(const struct isis_circuit *circuit,
* XPath: /frr-isisd:authentication-type-failure
*/
void isis_notif_authentication_type_failure(const struct isis_circuit *circuit,
const char *raw_pdu)
const char *raw_pdu,
size_t raw_pdu_len)
{
const char *xpath = "/frr-isisd:authentication-type-failure";
struct list *arguments = yang_data_list_new();
@ -211,6 +273,9 @@ void isis_notif_authentication_type_failure(const struct isis_circuit *circuit,
data = yang_data_new(xpath_arg, raw_pdu);
listnode_add(arguments, data);
hook_call(isis_hook_authentication_type_failure, circuit, raw_pdu,
raw_pdu_len);
nb_notification_send(xpath, arguments);
}
@ -218,7 +283,7 @@ void isis_notif_authentication_type_failure(const struct isis_circuit *circuit,
* XPath: /frr-isisd:authentication-failure
*/
void isis_notif_authentication_failure(const struct isis_circuit *circuit,
const char *raw_pdu)
const char *raw_pdu, size_t raw_pdu_len)
{
const char *xpath = "/frr-isisd:authentication-failure";
struct list *arguments = yang_data_list_new();
@ -232,6 +297,9 @@ void isis_notif_authentication_failure(const struct isis_circuit *circuit,
data = yang_data_new(xpath_arg, raw_pdu);
listnode_add(arguments, data);
hook_call(isis_hook_authentication_failure, circuit, raw_pdu,
raw_pdu_len);
nb_notification_send(xpath, arguments);
}
@ -269,6 +337,8 @@ void isis_notif_adj_state_change(const struct isis_adjacency *adj,
listnode_add(arguments, data);
}
hook_call(isis_hook_adj_state_change, adj);
nb_notification_send(xpath, arguments);
}
@ -276,7 +346,8 @@ void isis_notif_adj_state_change(const struct isis_adjacency *adj,
* XPath: /frr-isisd:rejected-adjacency
*/
void isis_notif_reject_adjacency(const struct isis_circuit *circuit,
const char *reason, const char *raw_pdu)
const char *reason, const char *raw_pdu,
size_t raw_pdu_len)
{
const char *xpath = "/frr-isisd:rejected-adjacency";
struct list *arguments = yang_data_list_new();
@ -293,6 +364,8 @@ void isis_notif_reject_adjacency(const struct isis_circuit *circuit,
data = yang_data_new(xpath_arg, raw_pdu);
listnode_add(arguments, data);
hook_call(isis_hook_reject_adjacency, circuit, raw_pdu, raw_pdu_len);
nb_notification_send(xpath, arguments);
}
@ -300,7 +373,7 @@ void isis_notif_reject_adjacency(const struct isis_circuit *circuit,
* XPath: /frr-isisd:area-mismatch
*/
void isis_notif_area_mismatch(const struct isis_circuit *circuit,
const char *raw_pdu)
const char *raw_pdu, size_t raw_pdu_len)
{
const char *xpath = "/frr-isisd:area-mismatch";
struct list *arguments = yang_data_list_new();
@ -314,6 +387,8 @@ void isis_notif_area_mismatch(const struct isis_circuit *circuit,
data = yang_data_new(xpath_arg, raw_pdu);
listnode_add(arguments, data);
hook_call(isis_hook_area_mismatch, circuit, raw_pdu, raw_pdu_len);
nb_notification_send(xpath, arguments);
}
@ -321,7 +396,7 @@ void isis_notif_area_mismatch(const struct isis_circuit *circuit,
* XPath: /frr-isisd:lsp-received
*/
void isis_notif_lsp_received(const struct isis_circuit *circuit,
const char *lsp_id, uint32_t seqno,
const uint8_t *lsp_id, uint32_t seqno,
uint32_t timestamp, const char *sys_id)
{
const char *xpath = "/frr-isisd:lsp-received";
@ -333,7 +408,7 @@ void isis_notif_lsp_received(const struct isis_circuit *circuit,
notif_prep_instance_hdr(xpath, area, "default", arguments);
notif_prepr_iface_hdr(xpath, circuit, arguments);
snprintf(xpath_arg, sizeof(xpath_arg), "%s/lsp-id", xpath);
data = yang_data_new_string(xpath_arg, lsp_id);
data = yang_data_new_string(xpath_arg, rawlspid_print(lsp_id));
listnode_add(arguments, data);
snprintf(xpath_arg, sizeof(xpath_arg), "%s/sequence", xpath);
data = yang_data_new_uint32(xpath_arg, seqno);
@ -351,7 +426,7 @@ void isis_notif_lsp_received(const struct isis_circuit *circuit,
/*
* XPath: /frr-isisd:lsp-generation
*/
void isis_notif_lsp_gen(const struct isis_area *area, const char *lsp_id,
void isis_notif_lsp_gen(const struct isis_area *area, const uint8_t *lsp_id,
uint32_t seqno, uint32_t timestamp)
{
const char *xpath = "/frr-isisd:lsp-generation";
@ -361,7 +436,7 @@ void isis_notif_lsp_gen(const struct isis_area *area, const char *lsp_id,
notif_prep_instance_hdr(xpath, area, "default", arguments);
snprintf(xpath_arg, sizeof(xpath_arg), "%s/lsp-id", xpath);
data = yang_data_new_string(xpath_arg, lsp_id);
data = yang_data_new_string(xpath_arg, rawlspid_print(lsp_id));
listnode_add(arguments, data);
snprintf(xpath_arg, sizeof(xpath_arg), "%s/sequence", xpath);
data = yang_data_new_uint32(xpath_arg, seqno);
@ -377,7 +452,8 @@ void isis_notif_lsp_gen(const struct isis_area *area, const char *lsp_id,
* XPath: /frr-isisd:id-len-mismatch
*/
void isis_notif_id_len_mismatch(const struct isis_circuit *circuit,
uint8_t rcv_id_len, const char *raw_pdu)
uint8_t rcv_id_len, const char *raw_pdu,
size_t raw_pdu_len)
{
const char *xpath = "/frr-isisd:id-len-mismatch";
struct list *arguments = yang_data_list_new();
@ -394,6 +470,9 @@ void isis_notif_id_len_mismatch(const struct isis_circuit *circuit,
data = yang_data_new(xpath_arg, raw_pdu);
listnode_add(arguments, data);
hook_call(isis_hook_id_len_mismatch, circuit, rcv_id_len, raw_pdu,
raw_pdu_len);
nb_notification_send(xpath, arguments);
}
@ -401,7 +480,8 @@ void isis_notif_id_len_mismatch(const struct isis_circuit *circuit,
* XPath: /frr-isisd:version-skew
*/
void isis_notif_version_skew(const struct isis_circuit *circuit,
uint8_t version, const char *raw_pdu)
uint8_t version, const char *raw_pdu,
size_t raw_pdu_len)
{
const char *xpath = "/frr-isisd:version-skew";
struct list *arguments = yang_data_list_new();
@ -418,6 +498,9 @@ void isis_notif_version_skew(const struct isis_circuit *circuit,
data = yang_data_new(xpath_arg, raw_pdu);
listnode_add(arguments, data);
hook_call(isis_hook_version_skew, circuit, version, raw_pdu,
raw_pdu_len);
nb_notification_send(xpath, arguments);
}
@ -425,7 +508,8 @@ void isis_notif_version_skew(const struct isis_circuit *circuit,
* XPath: /frr-isisd:lsp-error-detected
*/
void isis_notif_lsp_error(const struct isis_circuit *circuit,
const char *lsp_id, const char *raw_pdu,
const uint8_t *lsp_id, const char *raw_pdu,
size_t raw_pdu_len,
__attribute__((unused)) uint32_t offset,
__attribute__((unused)) uint8_t tlv_type)
{
@ -438,13 +522,15 @@ void isis_notif_lsp_error(const struct isis_circuit *circuit,
notif_prep_instance_hdr(xpath, area, "default", arguments);
notif_prepr_iface_hdr(xpath, circuit, arguments);
snprintf(xpath_arg, sizeof(xpath_arg), "%s/lsp-id", xpath);
data = yang_data_new_string(xpath_arg, lsp_id);
data = yang_data_new_string(xpath_arg, rawlspid_print(lsp_id));
listnode_add(arguments, data);
snprintf(xpath_arg, sizeof(xpath_arg), "%s/raw-pdu", xpath);
data = yang_data_new(xpath_arg, raw_pdu);
listnode_add(arguments, data);
/* ignore offset and tlv_type which cannot be set properly */
hook_call(isis_hook_lsp_error, circuit, lsp_id, raw_pdu, raw_pdu_len);
nb_notification_send(xpath, arguments);
}
@ -452,7 +538,7 @@ void isis_notif_lsp_error(const struct isis_circuit *circuit,
* XPath: /frr-isisd:sequence-number-skipped
*/
void isis_notif_seqno_skipped(const struct isis_circuit *circuit,
const char *lsp_id)
const uint8_t *lsp_id)
{
const char *xpath = "/frr-isisd:sequence-number-skipped";
struct list *arguments = yang_data_list_new();
@ -463,9 +549,11 @@ void isis_notif_seqno_skipped(const struct isis_circuit *circuit,
notif_prep_instance_hdr(xpath, area, "default", arguments);
notif_prepr_iface_hdr(xpath, circuit, arguments);
snprintf(xpath_arg, sizeof(xpath_arg), "%s/lsp-id", xpath);
data = yang_data_new_string(xpath_arg, lsp_id);
data = yang_data_new_string(xpath_arg, rawlspid_print(lsp_id));
listnode_add(arguments, data);
hook_call(isis_hook_seqno_skipped, circuit, lsp_id);
nb_notification_send(xpath, arguments);
}
@ -473,7 +561,7 @@ void isis_notif_seqno_skipped(const struct isis_circuit *circuit,
* XPath: /frr-isisd:own-lsp-purge
*/
void isis_notif_own_lsp_purge(const struct isis_circuit *circuit,
const char *lsp_id)
const uint8_t *lsp_id)
{
const char *xpath = "/frr-isisd:own-lsp-purge";
struct list *arguments = yang_data_list_new();
@ -484,8 +572,10 @@ void isis_notif_own_lsp_purge(const struct isis_circuit *circuit,
notif_prep_instance_hdr(xpath, area, "default", arguments);
notif_prepr_iface_hdr(xpath, circuit, arguments);
snprintf(xpath_arg, sizeof(xpath_arg), "%s/lsp-id", xpath);
data = yang_data_new_string(xpath_arg, lsp_id);
data = yang_data_new_string(xpath_arg, rawlspid_print(lsp_id));
listnode_add(arguments, data);
hook_call(isis_hook_own_lsp_purge, circuit, lsp_id);
nb_notification_send(xpath, arguments);
}

View File

@ -549,6 +549,19 @@ static int pdu_len_validate(uint16_t pdu_len, struct isis_circuit *circuit)
return 0;
}
static void update_rej_adj_count(struct isis_circuit *circuit)
{
circuit->rej_adjacencies++;
if (circuit->is_type == IS_LEVEL_1)
circuit->area->rej_adjacencies[0]++;
else if (circuit->is_type == IS_LEVEL_2)
circuit->area->rej_adjacencies[1]++;
else {
circuit->area->rej_adjacencies[0]++;
circuit->area->rej_adjacencies[1]++;
}
}
static int process_hello(uint8_t pdu_type, struct isis_circuit *circuit,
uint8_t *ssnpa)
{
@ -581,22 +594,22 @@ static int process_hello(uint8_t pdu_type, struct isis_circuit *circuit,
if (p2p_hello) {
if (circuit->circ_type != CIRCUIT_T_P2P) {
zlog_warn("p2p hello on non p2p circuit");
circuit->rej_adjacencies++;
update_rej_adj_count(circuit);
#ifndef FABRICD
isis_notif_reject_adjacency(
circuit, "p2p hello on non p2p circuit",
raw_pdu);
raw_pdu, sizeof(raw_pdu));
#endif /* ifndef FABRICD */
return ISIS_WARNING;
}
} else {
if (circuit->circ_type != CIRCUIT_T_BROADCAST) {
zlog_warn("lan hello on non broadcast circuit");
circuit->rej_adjacencies++;
update_rej_adj_count(circuit);
#ifndef FABRICD
isis_notif_reject_adjacency(
circuit, "lan hello on non broadcast circuit",
raw_pdu);
raw_pdu, sizeof(raw_pdu));
#endif /* ifndef FABRICD */
return ISIS_WARNING;
}
@ -605,12 +618,12 @@ static int process_hello(uint8_t pdu_type, struct isis_circuit *circuit,
zlog_debug(
"level %d LAN Hello received over circuit with externalDomain = true",
level);
circuit->rej_adjacencies++;
update_rej_adj_count(circuit);
#ifndef FABRICD
isis_notif_reject_adjacency(
circuit,
"LAN Hello received over circuit with externalDomain = true",
raw_pdu);
raw_pdu, sizeof(raw_pdu));
#endif /* ifndef FABRICD */
return ISIS_WARNING;
}
@ -622,10 +635,11 @@ static int process_hello(uint8_t pdu_type, struct isis_circuit *circuit,
circuit->area->area_tag,
circuit->interface->name);
}
circuit->rej_adjacencies++;
update_rej_adj_count(circuit);
#ifndef FABRICD
isis_notif_reject_adjacency(
circuit, "Interface level mismatch", raw_pdu);
isis_notif_reject_adjacency(circuit,
"Interface level mismatch",
raw_pdu, sizeof(raw_pdu));
#endif /* ifndef FABRICD */
return ISIS_WARNING;
}
@ -652,10 +666,10 @@ static int process_hello(uint8_t pdu_type, struct isis_circuit *circuit,
"ISIS-Adj (%s): Rcvd %s from (%s) with invalid pdu length %hu",
circuit->area->area_tag, pdu_name,
circuit->interface->name, iih.pdu_len);
circuit->rej_adjacencies++;
update_rej_adj_count(circuit);
#ifndef FABRICD
isis_notif_reject_adjacency(circuit, "Invalid PDU length",
raw_pdu);
raw_pdu, sizeof(raw_pdu));
#endif /* ifndef FABRICD */
return ISIS_WARNING;
}
@ -664,10 +678,11 @@ static int process_hello(uint8_t pdu_type, struct isis_circuit *circuit,
flog_err(EC_ISIS_PACKET,
"Level %d LAN Hello with Circuit Type %d", level,
iih.circ_type);
circuit->rej_adjacencies++;
update_rej_adj_count(circuit);
#ifndef FABRICD
isis_notif_reject_adjacency(
circuit, "LAN Hello with wrong IS-level", raw_pdu);
isis_notif_reject_adjacency(circuit,
"LAN Hello with wrong IS-level",
raw_pdu, sizeof(raw_pdu));
#endif /* ifndef FABRICD */
return ISIS_ERROR;
}
@ -678,10 +693,10 @@ static int process_hello(uint8_t pdu_type, struct isis_circuit *circuit,
if (isis_unpack_tlvs(STREAM_READABLE(circuit->rcv_stream),
circuit->rcv_stream, &iih.tlvs, &error_log)) {
zlog_warn("isis_unpack_tlvs() failed: %s", error_log);
circuit->rej_adjacencies++;
update_rej_adj_count(circuit);
#ifndef FABRICD
isis_notif_reject_adjacency(circuit, "Failed to unpack TLVs",
raw_pdu);
raw_pdu, sizeof(raw_pdu));
#endif /* ifndef FABRICD */
goto out;
}
@ -690,17 +705,18 @@ static int process_hello(uint8_t pdu_type, struct isis_circuit *circuit,
zlog_warn("No Area addresses TLV in %s", pdu_name);
#ifndef FABRICD
/* send northbound notification */
isis_notif_area_mismatch(circuit, raw_pdu);
isis_notif_area_mismatch(circuit, raw_pdu, sizeof(raw_pdu));
#endif /* ifndef FABRICD */
goto out;
}
if (!iih.tlvs->protocols_supported.count) {
zlog_warn("No supported protocols TLV in %s", pdu_name);
circuit->rej_adjacencies++;
update_rej_adj_count(circuit);
#ifndef FABRICD
isis_notif_reject_adjacency(
circuit, "No supported protocols TLV", raw_pdu);
isis_notif_reject_adjacency(circuit,
"No supported protocols TLV",
raw_pdu, sizeof(raw_pdu));
#endif /* ifndef FABRICD */
goto out;
}
@ -716,12 +732,13 @@ static int process_hello(uint8_t pdu_type, struct isis_circuit *circuit,
stream_get_from(raw_pdu, circuit->rcv_stream, pdu_start,
pdu_end - pdu_start);
if (auth_code == ISIS_AUTH_FAILURE) {
circuit->auth_failures++;
isis_notif_authentication_failure(circuit, raw_pdu);
update_rej_adj_count(circuit);
isis_notif_authentication_failure(circuit, raw_pdu,
sizeof(raw_pdu));
} else { /* AUTH_TYPE_FAILURE or NO_VALIDATOR */
circuit->auth_type_failures++;
isis_notif_authentication_type_failure(circuit,
raw_pdu);
update_rej_adj_count(circuit);
isis_notif_authentication_type_failure(circuit, raw_pdu,
sizeof(raw_pdu));
}
#endif /* ifndef FABRICD */
goto out;
@ -731,10 +748,11 @@ static int process_hello(uint8_t pdu_type, struct isis_circuit *circuit,
zlog_warn(
"ISIS-Adj (%s): Received IIH with own sysid on %s - discard",
circuit->area->area_tag, circuit->interface->name);
circuit->rej_adjacencies++;
update_rej_adj_count(circuit);
#ifndef FABRICD
isis_notif_reject_adjacency(
circuit, "Received IIH with our own sysid", raw_pdu);
isis_notif_reject_adjacency(circuit,
"Received IIH with our own sysid",
raw_pdu, sizeof(raw_pdu));
#endif /* ifndef FABRICD */
goto out;
}
@ -752,7 +770,7 @@ static int process_hello(uint8_t pdu_type, struct isis_circuit *circuit,
}
#ifndef FABRICD
/* send northbound notification */
isis_notif_area_mismatch(circuit, raw_pdu);
isis_notif_area_mismatch(circuit, raw_pdu, sizeof(raw_pdu));
#endif /* ifndef FABRICD */
goto out;
}
@ -769,11 +787,11 @@ static int process_hello(uint8_t pdu_type, struct isis_circuit *circuit,
"ISIS-Adj (%s): Neither IPv4 nor IPv6 considered usable. Ignoring IIH",
circuit->area->area_tag);
}
circuit->rej_adjacencies++;
update_rej_adj_count(circuit);
#ifndef FABRICD
isis_notif_reject_adjacency(
circuit, "Neither IPv4 not IPv6 considered usable",
raw_pdu);
raw_pdu, sizeof(raw_pdu));
#endif /* ifndef FABRICD */
goto out;
}
@ -857,8 +875,8 @@ static int process_lsp(uint8_t pdu_type, struct isis_circuit *circuit,
#ifndef FABRICD
/* send northbound notification */
isis_notif_lsp_received(circuit, rawlspid_print(hdr.lsp_id), hdr.seqno,
time(NULL), sysid_print(hdr.lsp_id));
isis_notif_lsp_received(circuit, hdr.lsp_id, hdr.seqno, time(NULL),
sysid_print(hdr.lsp_id));
#endif /* ifndef FABRICD */
if (pdu_len_validate(hdr.pdu_len, circuit)) {
@ -931,8 +949,18 @@ static int process_lsp(uint8_t pdu_type, struct isis_circuit *circuit,
* we change the code above to return those extra fields, we
* will send dummy values which are ignored in the callback
*/
isis_notif_lsp_error(circuit, rawlspid_print(hdr.lsp_id),
raw_pdu, 0, 0);
circuit->lsp_error_counter++;
if (circuit->is_type == IS_LEVEL_1) {
circuit->area->lsp_error_counter[0]++;
} else if (circuit->is_type == IS_LEVEL_2) {
circuit->area->lsp_error_counter[1]++;
} else {
circuit->area->lsp_error_counter[0]++;
circuit->area->lsp_error_counter[1]++;
}
isis_notif_lsp_error(circuit, hdr.lsp_id, raw_pdu,
sizeof(raw_pdu), 0, 0);
#endif /* ifndef FABRICD */
goto out;
}
@ -956,11 +984,28 @@ static int process_lsp(uint8_t pdu_type, struct isis_circuit *circuit,
/* send northbound notification */
if (auth_code == ISIS_AUTH_FAILURE) {
circuit->auth_failures++;
isis_notif_authentication_failure(circuit, raw_pdu);
if (circuit->is_type == IS_LEVEL_1) {
circuit->area->auth_failures[0]++;
} else if (circuit->is_type == IS_LEVEL_2) {
circuit->area->auth_failures[1]++;
} else {
circuit->area->auth_failures[0]++;
circuit->area->auth_failures[1]++;
}
isis_notif_authentication_failure(circuit, raw_pdu,
sizeof(raw_pdu));
} else { /* AUTH_TYPE_FAILURE or NO_VALIDATOR */
circuit->auth_type_failures++;
isis_notif_authentication_type_failure(circuit,
raw_pdu);
if (circuit->is_type == IS_LEVEL_1) {
circuit->area->auth_type_failures[0]++;
} else if (circuit->is_type == IS_LEVEL_2) {
circuit->area->auth_type_failures[1]++;
} else {
circuit->area->auth_type_failures[0]++;
circuit->area->auth_type_failures[1]++;
}
isis_notif_authentication_type_failure(circuit, raw_pdu,
sizeof(raw_pdu));
}
#endif /* ifndef FABRICD */
goto out;
@ -1105,10 +1150,10 @@ dontcheckadj:
if (lsp->hdr.seqno < hdr.seqno) {
/* send northbound
* notification */
circuit->area
->lsp_seqno_skipped_counter++;
isis_notif_seqno_skipped(
circuit,
rawlspid_print(
hdr.lsp_id));
circuit, hdr.lsp_id);
}
#endif /* ifndef FABRICD */
lsp_inc_seqno(lsp, hdr.seqno);
@ -1129,8 +1174,7 @@ dontcheckadj:
/* our own LSP with 0 remaining life time */
#ifndef FABRICD
/* send northbound notification */
isis_notif_own_lsp_purge(
circuit, rawlspid_print(hdr.lsp_id));
isis_notif_own_lsp_purge(circuit, hdr.lsp_id);
#endif /* ifndef FABRICD */
}
}
@ -1158,8 +1202,8 @@ dontcheckadj:
lsp_inc_seqno(lsp, hdr.seqno);
#ifndef FABRICD
/* send northbound notification */
isis_notif_seqno_skipped(circuit,
rawlspid_print(hdr.lsp_id));
circuit->area->lsp_seqno_skipped_counter++;
isis_notif_seqno_skipped(circuit, hdr.lsp_id);
#endif /* ifndef FABRICD */
if (IS_DEBUG_UPDATE_PACKETS) {
zlog_debug(
@ -1388,12 +1432,28 @@ static int process_snp(uint8_t pdu_type, struct isis_circuit *circuit,
pdu_end - pdu_start);
if (auth_code == ISIS_AUTH_FAILURE) {
circuit->auth_failures++;
isis_notif_authentication_failure(circuit,
raw_pdu);
if (circuit->is_type == IS_LEVEL_1) {
circuit->area->auth_failures[0]++;
} else if (circuit->is_type == IS_LEVEL_2) {
circuit->area->auth_failures[1]++;
} else {
circuit->area->auth_failures[0]++;
circuit->area->auth_failures[1]++;
}
isis_notif_authentication_failure(
circuit, raw_pdu, sizeof(raw_pdu));
} else { /* AUTH_TYPE_FAILURE or NO_VALIDATOR */
circuit->auth_type_failures++;
isis_notif_authentication_type_failure(circuit,
raw_pdu);
if (circuit->is_type == IS_LEVEL_1) {
circuit->area->auth_type_failures[0]++;
} else if (circuit->is_type == IS_LEVEL_2) {
circuit->area->auth_type_failures[1]++;
} else {
circuit->area->auth_type_failures[0]++;
circuit->area->auth_type_failures[1]++;
}
isis_notif_authentication_type_failure(
circuit, raw_pdu, sizeof(raw_pdu));
}
#endif /* ifndef FABRICD */
goto out;
@ -1620,7 +1680,8 @@ int isis_handle_pdu(struct isis_circuit *circuit, uint8_t *ssnpa)
zlog_warn("Unsupported ISIS version %hhu", version1);
#ifndef FABRICD
/* send northbound notification */
isis_notif_version_skew(circuit, version1, raw_pdu);
isis_notif_version_skew(circuit, version1, raw_pdu,
sizeof(raw_pdu));
#endif /* ifndef FABRICD */
return ISIS_WARNING;
}
@ -1631,9 +1692,19 @@ int isis_handle_pdu(struct isis_circuit *circuit, uint8_t *ssnpa)
"IDFieldLengthMismatch: ID Length field in a received PDU %hhu, while the parameter for this IS is %u",
id_len, ISIS_SYS_ID_LEN);
circuit->id_len_mismatches++;
if (circuit->is_type == IS_LEVEL_1) {
circuit->area->id_len_mismatches[0]++;
} else if (circuit->is_type == IS_LEVEL_2) {
circuit->area->id_len_mismatches[1]++;
} else {
circuit->area->id_len_mismatches[0]++;
circuit->area->id_len_mismatches[1]++;
}
#ifndef FABRICD
/* send northbound notification */
isis_notif_id_len_mismatch(circuit, id_len, raw_pdu);
isis_notif_id_len_mismatch(circuit, id_len, raw_pdu,
sizeof(raw_pdu));
#endif /* ifndef FABRICD */
return ISIS_ERROR;
}
@ -1662,7 +1733,8 @@ int isis_handle_pdu(struct isis_circuit *circuit, uint8_t *ssnpa)
zlog_warn("Unsupported ISIS PDU version %hhu", version2);
#ifndef FABRICD
/* send northbound notification */
isis_notif_version_skew(circuit, version2, raw_pdu);
isis_notif_version_skew(circuit, version2, raw_pdu,
sizeof(raw_pdu));
#endif /* ifndef FABRICD */
return ISIS_WARNING;
}
@ -1686,7 +1758,7 @@ int isis_handle_pdu(struct isis_circuit *circuit, uint8_t *ssnpa)
#ifndef FABRICD
/* send northbound notification */
isis_notif_max_area_addr_mismatch(circuit, max_area_addrs,
raw_pdu);
raw_pdu, sizeof(raw_pdu));
#endif /* ifndef FABRICD */
return ISIS_ERROR;
}
@ -2409,7 +2481,7 @@ void send_lsp(struct isis_circuit *circuit, struct isis_lsp *lsp,
#ifndef FABRICD
/* send a northbound notification */
isis_notif_lsp_too_large(circuit, stream_get_endp(lsp->pdu),
rawlspid_print(lsp->hdr.lsp_id));
lsp->hdr.lsp_id);
#endif /* ifndef FABRICD */
if (IS_DEBUG_PACKET_DUMP)
zlog_dump_data(STREAM_DATA(lsp->pdu),

3457
isisd/isis_snmp.c Normal file

File diff suppressed because it is too large Load Diff

View File

@ -1821,6 +1821,7 @@ static int isis_run_spf_cb(struct thread *thread)
struct isis_spf_run *run = THREAD_ARG(thread);
struct isis_area *area = run->area;
int level = run->level;
int have_run = 0;
XFREE(MTYPE_ISIS_SPF_RUN, run);
area->spf_timer[level - 1] = NULL;
@ -1839,15 +1840,24 @@ static int isis_run_spf_cb(struct thread *thread)
zlog_debug("ISIS-SPF (%s) L%d SPF needed, periodic SPF",
area->area_tag, level);
if (area->ip_circuits)
if (area->ip_circuits) {
isis_run_spf_with_protection(
area, area->spftree[SPFTREE_IPV4][level - 1]);
if (area->ipv6_circuits)
have_run = 1;
}
if (area->ipv6_circuits) {
isis_run_spf_with_protection(
area, area->spftree[SPFTREE_IPV6][level - 1]);
if (area->ipv6_circuits && isis_area_ipv6_dstsrc_enabled(area))
have_run = 1;
}
if (area->ipv6_circuits && isis_area_ipv6_dstsrc_enabled(area)) {
isis_run_spf_with_protection(
area, area->spftree[SPFTREE_DSTSRC][level - 1]);
have_run = 1;
}
if (have_run)
area->spf_run_count[level]++;
isis_area_verify_routes(area);

View File

@ -89,6 +89,10 @@ static struct isis_master isis_master;
/* ISIS process wide configuration pointer to export. */
struct isis_master *im;
#ifndef FABRICD
DEFINE_HOOK(isis_hook_db_overload, (const struct isis_area *area), (area));
#endif /* ifndef FABRICD */
/*
* Prototypes.
*/
@ -214,6 +218,7 @@ struct isis *isis_new(const char *vrf_name)
isis->area_list = list_new();
isis->init_circ_list = list_new();
isis->uptime = time(NULL);
isis->snmp_notifications = 1;
dyn_cache_init(isis);
return isis;
@ -2563,6 +2568,14 @@ void isis_area_overload_bit_set(struct isis_area *area, bool overload_bit)
if (new_overload_bit != area->overload_bit) {
area->overload_bit = new_overload_bit;
if (new_overload_bit)
area->overload_counter++;
#ifndef FABRICD
hook_call(isis_hook_db_overload, area);
#endif /* ifndef FABRICD */
lsp_regenerate_schedule(area, IS_LEVEL_1 | IS_LEVEL_2, 1);
}
#ifndef FABRICD

View File

@ -63,6 +63,8 @@ extern void isis_cli_init(void);
all_vrf = strmatch(vrf_name, "all"); \
}
#define SNMP_CIRCUITS_MAX (512)
extern struct zebra_privs_t isisd_privs;
/* uncomment if you are a developer in bug hunt */
@ -93,6 +95,9 @@ struct isis {
time_t uptime; /* when did we start */
struct thread *t_dync_clean; /* dynamic hostname cache cleanup thread */
uint32_t circuit_ids_used[8]; /* 256 bits to track circuit ids 1 through 255 */
struct isis_circuit *snmp_circuits[SNMP_CIRCUITS_MAX];
uint32_t snmp_circuit_id_last;
int snmp_notifications;
struct route_table *ext_info[REDIST_PROTOCOL_COUNT];
struct ldp_sync_info_cmd ldp_sync_cmd; /* MPLS LDP-IGP Sync */
@ -168,6 +173,7 @@ struct isis_area {
char is_type; /* level-1 level-1-2 or level-2-only */
/* are we overloaded? */
char overload_bit;
uint32_t overload_counter;
/* L1/L2 router identifier for inter-area traffic */
char attached_bit_send;
char attached_bit_rcv_ignore;
@ -180,6 +186,9 @@ struct isis_area {
int lsp_frag_threshold;
uint64_t lsp_gen_count[ISIS_LEVELS];
uint64_t lsp_purge_count[ISIS_LEVELS];
uint32_t lsp_exceeded_max_counter;
uint32_t lsp_seqno_skipped_counter;
uint64_t spf_run_count[ISIS_LEVELS];
int ip_circuits;
/* logging adjacency changes? */
uint8_t log_adj_changes;
@ -220,10 +229,19 @@ struct isis_area {
pdu_counter_t pdu_rx_counters;
uint64_t lsp_rxmt_count;
/* Area counters */
uint64_t rej_adjacencies[2];
uint64_t auth_type_failures[2];
uint64_t auth_failures[2];
uint64_t id_len_mismatches[2];
uint64_t lsp_error_counter[2];
QOBJ_FIELDS
};
DECLARE_QOBJ_TYPE(isis_area)
DECLARE_HOOK(isis_area_overload_bit_update, (struct isis_area * area), (area))
void isis_terminate(void);
void isis_finish(struct isis *isis);
void isis_master_init(struct thread_master *master);

View File

@ -17,6 +17,9 @@ vtysh_scan += \
isisd/isisd.c \
# end
vtysh_daemons += isisd
if SNMP
module_LTLIBRARIES += isisd/isisd_snmp.la
endif
man8 += $(MANBUILD)/frr-isisd.8
endif
@ -137,7 +140,12 @@ isisd_isisd_SOURCES = $(ISIS_SOURCES)
nodist_isisd_isisd_SOURCES = \
yang/frr-isisd.yang.c \
# end
isisd_isisd_snmp_la_SOURCES = isisd/isis_snmp.c
isisd_isisd_snmp_la_CFLAGS = $(WERROR) $(SNMP_CFLAGS) -std=gnu99
isisd_isisd_snmp_la_LDFLAGS = -avoid-version -module -shared -export-dynamic
isisd_isisd_snmp_la_LIBADD = lib/libfrrsnmp.la
# Building fabricd
FABRICD_CPPFLAGS = -DFABRICD=1 $(AM_CPPFLAGS)

View File

@ -243,6 +243,11 @@ DEFUN (no_agentx,
return CMD_WARNING_CONFIG_FAILED;
}
int smux_enabled(void)
{
return agentx_enabled;
}
void smux_init(struct thread_master *tm)
{
agentx_tm = tm;
@ -379,4 +384,9 @@ int smux_trap_multi_index(struct variable *vp, size_t vp_len, const oid *ename,
return 1;
}
void smux_events_update(void)
{
agentx_events_update();
}
#endif /* SNMP_AGENTX */

View File

@ -102,6 +102,8 @@ struct index_oid {
#define SNMP_IP6ADDRESS(V) (*var_len = sizeof(struct in6_addr), (uint8_t *)&V)
extern int smux_enabled(void);
extern void smux_init(struct thread_master *tm);
extern void smux_register_mib(const char *, struct variable *, size_t, int,
oid[], size_t);
@ -141,6 +143,8 @@ extern int smux_trap_multi_index(struct variable *vp, size_t vp_len,
struct index_oid *iname, size_t index_len,
const struct trap_object *trapobj,
size_t trapobjlen, uint8_t sptrap);
extern void smux_events_update(void);
extern int oid_compare(const oid *, int, const oid *, int);
extern void oid2in_addr(oid[], int, struct in_addr *);
extern void oid2int(oid oid[], int *dest);

View File

@ -107,7 +107,7 @@ sub scan_file {
$protocol = "VTYSH_ALL";
}
elsif ($file =~ /lib\/agentx\.c$/) {
$protocol = "VTYSH_RIPD|VTYSH_OSPFD|VTYSH_OSPF6D|VTYSH_BGPD|VTYSH_ZEBRA";
$protocol = "VTYSH_ISISD|VTYSH_RIPD|VTYSH_OSPFD|VTYSH_OSPF6D|VTYSH_BGPD|VTYSH_ZEBRA";
}
elsif ($file =~ /lib\/nexthop_group\.c$/) {
$protocol = "VTYSH_NH_GROUP";