From de255f240b2b6abdbc0bac5ac905f839f24e8dca Mon Sep 17 00:00:00 2001 From: Dmitrijs Goloscapovs Date: Thu, 18 Jan 2024 13:02:14 +0200 Subject: [PATCH] .......PS. [ZBX-16927] added verbose debug for snmp --- src/zabbix_server/poller/checks_snmp.c | 74 +++++++++++++++++++++++++- 1 file changed, 72 insertions(+), 2 deletions(-) diff --git a/src/zabbix_server/poller/checks_snmp.c b/src/zabbix_server/poller/checks_snmp.c index 66d12c3f837..4bf4ed5b877 100644 --- a/src/zabbix_server/poller/checks_snmp.c +++ b/src/zabbix_server/poller/checks_snmp.c @@ -1010,16 +1010,25 @@ static int zbx_oid_is_new(zbx_hashset_t *hs, size_t root_len, const oid *p_oid, var_len = oid_len - root_len; if (ZBX_OIDS_MAX_NUM == hs->num_data) + { + zabbix_log(LOG_LEVEL_DEBUG, "%s:[%i] cache of seen oids is full", __func__, __LINE__); return FAIL; + } oid_k[0] = var_len; memcpy(oid_k + 1, var_oid, var_len * sizeof(oid)); if (NULL != zbx_hashset_search(hs, oid_k)) + { + zabbix_log(LOG_LEVEL_DEBUG, "%s:[%i] oid was already seen", __func__, __LINE__); return FAIL; /* OID already seen */ + } if (NULL != zbx_hashset_insert(hs, oid_k, (var_len + 1) * sizeof(oid))) + { + zabbix_log(LOG_LEVEL_DEBUG, "%s:[%i] oid is new", __func__, __LINE__); return SUCCEED; /* new OID */ + } THIS_SHOULD_NEVER_HAPPEN; return FAIL; /* hashset fail */ @@ -1097,6 +1106,7 @@ static int zbx_snmp_walk(struct snmp_session *ss, const DC_ITEM *item, const cha root_numeric_len = strlen(oid_index); zbx_strlcpy(root_oid, oid_index, sizeof(root_oid)); + zabbix_log(LOG_LEVEL_DEBUG, "%s():[%i] root oid = '%s'", __func__, __LINE__, root_oid); /* copy rootOID to anOID */ memcpy(anOID, rootOID, rootOID_len * sizeof(oid)); @@ -1108,6 +1118,8 @@ static int zbx_snmp_walk(struct snmp_session *ss, const DC_ITEM *item, const cha while (1 == running) { + char oid_buffer[MAX_STRING_LEN]; + /* create PDU */ if (NULL == (pdu = snmp_pdu_create(SNMP_BULK_ENABLED == bulk ? SNMP_MSG_GETBULK : SNMP_MSG_GETNEXT))) { @@ -1116,6 +1128,11 @@ static int zbx_snmp_walk(struct snmp_session *ss, const DC_ITEM *item, const cha break; } + if (-1 == snprint_objid(oid_buffer, sizeof(oid_buffer), anOID, anOID_len)) + zabbix_log(LOG_LEVEL_DEBUG, "%s():[%i] failed to print oid at %i", __func__, __LINE__, num_vars); + else + zabbix_log(LOG_LEVEL_DEBUG, "%s():[%i] added '%s' to PDU", __func__, __LINE__, oid_buffer); + if (NULL == snmp_add_null_var(pdu, anOID, anOID_len)) /* add OID as variable to PDU */ { zbx_strlcpy(error, "snmp_add_null_var(): cannot add null variable.", max_error_len); @@ -1132,6 +1149,9 @@ static int zbx_snmp_walk(struct snmp_session *ss, const DC_ITEM *item, const cha ss->retries = (0 == bulk || (1 == max_vars && 0 == level) ? 1 : 0); + zabbix_log(LOG_LEVEL_DEBUG, "%s():[%i] set number of retries before session timeout to %i", + __func__, __LINE__, ss->retries); + /* communicate with agent */ status = snmp_synch_response(ss, pdu, &response); @@ -1145,6 +1165,9 @@ static int zbx_snmp_walk(struct snmp_session *ss, const DC_ITEM *item, const cha /* The logic of iteratively reducing request size here is the same as in function */ /* zbx_snmp_get_values(). Please refer to the description there for explanation. */ reduce_max_vars: + zabbix_log(LOG_LEVEL_DEBUG, "%s():[%i] reducing max vars, min_fail = %i, max_vars = %i, level = %i", + __func__, __LINE__, *min_fail, max_vars, level); + if (*min_fail > max_vars) *min_fail = max_vars; @@ -1159,12 +1182,22 @@ reduce_max_vars: level++; + zabbix_log(LOG_LEVEL_DEBUG, "%s():[%i] reduced max vars, min_fail = %i, max_vars = %i, level = %i", + __func__, __LINE__, *min_fail, max_vars, level); + goto next; } else if (STAT_SUCCESS != status || SNMP_ERR_NOERROR != response->errstat) { if (1 >= level && 1 < max_vars) + { + zabbix_log(LOG_LEVEL_DEBUG, "%s():[%i] going to reduce max vars", __func__, __LINE__); goto reduce_max_vars; + } + else + { + zabbix_log(LOG_LEVEL_DEBUG, "%s():[%i] not going to reduce max vars", __func__, __LINE__); + } ret = zbx_get_snmp_response_error(ss, &item->interface, status, response, error, max_error_len); running = 0; @@ -1174,7 +1207,10 @@ reduce_max_vars: if (NULL == response->variables) { if (1 >= level && 1 < max_vars) + { + zabbix_log(LOG_LEVEL_DEBUG, "%s():[%i] going to reduce max vars", __func__, __LINE__); goto reduce_max_vars; + } zbx_strlcpy(error, "No values received.", max_error_len); ret = NOTSUPPORTED; @@ -1183,32 +1219,53 @@ reduce_max_vars: } /* process response */ + zabbix_log(LOG_LEVEL_DEBUG, "%s():[%i] processing response", __func__, __LINE__); for (num_vars = 0, var = response->variables; NULL != var; num_vars++, var = var->next_variable) { char **str_res; unsigned char val_type; + char oid_str[MAX_STRING_LEN], an_oid_str[MAX_STRING_LEN]; /* verify if we are in the same subtree */ if (SNMP_ENDOFMIBVIEW == var->type || var->name_length < rootOID_len || 0 != memcmp(rootOID, var->name, rootOID_len * sizeof(oid))) { /* reached the end or past this subtree */ + zabbix_log(LOG_LEVEL_DEBUG, "%s():[%i] reached end of subtree", __func__, __LINE__); running = 0; break; } else if (SNMP_NOSUCHOBJECT != var->type && SNMP_NOSUCHINSTANCE != var->type) { /* not an exception value */ + zabbix_log(LOG_LEVEL_DEBUG, "%s():[%i] not an exception value", __func__, __LINE__); + + if (-1 == snprint_objid(oid_str, sizeof(oid_str), var->name, var->name_length)) + zabbix_log(LOG_LEVEL_DEBUG, "%s():[%i] failed to print oid at %i", __func__, __LINE__, num_vars); + else + zabbix_log(LOG_LEVEL_DEBUG, "%s():[%i] num_vars = %i, oid = '%s'", __func__, __LINE__, num_vars, oid_str); if (1 == check_oid_increase) /* typical case */ { int res; + zabbix_log(LOG_LEVEL_DEBUG, "%s():[%i] checking for oid increase", __func__, __LINE__); /* normally devices return OIDs in increasing order, */ /* snmp_oid_compare() will return -1 in this case */ - if (-1 != (res = snmp_oid_compare(anOID, anOID_len, var->name, - var->name_length))) + if (-1 == snprint_objid(an_oid_str, sizeof(an_oid_str), anOID, anOID_len)) + zabbix_log(LOG_LEVEL_DEBUG, "%s():[%i] failed to print anOID at %i", __func__, __LINE__, num_vars); + else + zabbix_log(LOG_LEVEL_DEBUG, "%s():[%i] num_vars = %i, anOID = '%s'", __func__, __LINE__, num_vars, an_oid_str); + + res = snmp_oid_compare(anOID, anOID_len, var->name, var->name_length); + + zabbix_log(LOG_LEVEL_DEBUG, "%s():[%i] comparing '%s' (raw length %lu) with '%s' (raw length %lu)", + __func__, __LINE__, oid_str, var->name_length, an_oid_str, anOID_len); + + zabbix_log(LOG_LEVEL_DEBUG, "%s():[%i] snmp_oid_compare returned %i", __func__, __LINE__, res); + + if (-1 != res) { if (0 == res) /* got the same OID */ { @@ -1222,12 +1279,15 @@ reduce_max_vars: /* OID decreased. Disable further checks of increasing */ /* and set up a protection against endless looping. */ + zabbix_log(LOG_LEVEL_DEBUG, "%s():[%i] oid decreased %i", __func__, __LINE__, res); check_oid_increase = 0; zbx_detect_loop_init(&oids_seen); } } } + zabbix_log(LOG_LEVEL_DEBUG, "%s():[%i] check_oid_increase = %i", __func__, __LINE__, check_oid_increase); + if (0 == check_oid_increase && FAIL == zbx_oid_is_new(&oids_seen, rootOID_len, var->name, var->name_length)) { @@ -1277,6 +1337,11 @@ reduce_max_vars: /* go to next variable */ memcpy((char *)anOID, (char *)var->name, var->name_length * sizeof(oid)); anOID_len = var->name_length; + + if (-1 == snprint_objid(oid_str, sizeof(oid_str), anOID, anOID_len)) + zabbix_log(LOG_LEVEL_DEBUG, "%s():[%i] failed to print oid at %i", __func__, __LINE__, num_vars); + else + zabbix_log(LOG_LEVEL_DEBUG, "%s():[%i] anOID set to '%s'", __func__, __LINE__, oid_str); } else { @@ -1292,8 +1357,13 @@ reduce_max_vars: } } + zabbix_log(LOG_LEVEL_DEBUG, "%s():[%i] max_succeed = %i, num_vars = %i", __func__, __LINE__, *max_succeed, num_vars); if (*max_succeed < num_vars) + { *max_succeed = num_vars; + + zabbix_log(LOG_LEVEL_DEBUG, "%s():[%i] set max_succeed to %i", __func__, __LINE__, *max_succeed); + } next: if (NULL != response) snmp_free_pdu(response); -- 2.39.2