/****************************************************************************** * * * Function: proxy_add_history * * * * Purpose: add new value to history * * * * Parameters: item - item data * * value - new value of the item * * now - new value of the item * * * * Author: Alexei Vladishev * * * * Comments: * * * ******************************************************************************/ static void proxy_add_history(DB_ITEM *item, AGENT_RESULT *value, int now) { if (value->type & AR_UINT64) zabbix_log(LOG_LEVEL_DEBUG, "In proxy_add_history(itemid:" ZBX_FS_UI64 ",key:\"%s\",value_type:%d,UINT64:"ZBX_FS_UI64")", item->itemid, item->key, item->value_type, value->ui64); if (value->type & AR_STRING) zabbix_log(LOG_LEVEL_DEBUG, "In proxy_add_history(itemid:" ZBX_FS_UI64 ",key:\"%s\",value_type:%d,STRING:%s)", item->itemid, item->key, item->value_type, value->str); if (value->type & AR_DOUBLE) zabbix_log(LOG_LEVEL_DEBUG, "In proxy_add_history(itemid:" ZBX_FS_UI64 ",key:\"%s\",value_type:%d,DOUBLE:"ZBX_FS_DBL")", item->itemid, item->key, item->value_type, value->dbl); if (value->type & AR_TEXT) zabbix_log(LOG_LEVEL_DEBUG, "In proxy_add_history(itemid: "ZBX_FS_UI64 ",key:\"%s\",value_type:%d,TEXT:[%s])", item->itemid, item->key, item->value_type, value->text); switch (item->value_type) { case ITEM_VALUE_TYPE_FLOAT: if (GET_DBL_RESULT(value)) DBproxy_add_history(item->itemid, value->dbl, now); break; case ITEM_VALUE_TYPE_STR: if (GET_STR_RESULT(value)) DBproxy_add_history_str(item->itemid, value->str, now); break; case ITEM_VALUE_TYPE_LOG: if (GET_STR_RESULT(value)) DBproxy_add_history_log(item->itemid, value->str, now, item->timestamp, item->eventlog_source, item->eventlog_severity, item->lastlogsize); break; case ITEM_VALUE_TYPE_UINT64: if (GET_UI64_RESULT(value)) DBproxy_add_history_uint(item->itemid, value->ui64, now); break; case ITEM_VALUE_TYPE_TEXT: if (GET_TEXT_RESULT(value)) DBproxy_add_history_text(item->itemid, value->str, now); break; default: zabbix_log(LOG_LEVEL_ERR, "Unknown value type [%d] for itemid [" ZBX_FS_UI64 "]", item->value_type, item->itemid); } zabbix_log( LOG_LEVEL_DEBUG, "End of proxy_add_history"); }
int check_vcenter_hv_status(AGENT_REQUEST *request, const char *username, const char *password, AGENT_RESULT *result) { int ret; ret = get_vcenter_stat(request, username, password, ZBX_OPT_XPATH, ZBX_XPATH_LN2("val", "overallStatus"), result); if (SYSINFO_RET_OK == ret && NULL != GET_STR_RESULT(result)) { if (0 == strcmp(result->str, "gray")) SET_UI64_RESULT(result, 0); else if (0 == strcmp(result->str, "green")) SET_UI64_RESULT(result, 1); else if (0 == strcmp(result->str, "yellow")) SET_UI64_RESULT(result, 2); else if (0 == strcmp(result->str, "red")) SET_UI64_RESULT(result, 3); else ret = SYSINFO_RET_FAIL; UNSET_STR_RESULT(result); } return ret; }
/****************************************************************************** * * * Function: set_defaults * * * * Purpose: set configuration defaults * * * * Author: Vladimir Levijev, Rudolfs Kreicbergs * * * ******************************************************************************/ static void set_defaults(void) { AGENT_RESULT result; char **value = NULL; if (NULL == CONFIG_HOSTNAME) { if (NULL == CONFIG_HOSTNAME_ITEM) CONFIG_HOSTNAME_ITEM = zbx_strdup(CONFIG_HOSTNAME_ITEM, "system.hostname"); init_result(&result); if (SUCCEED == process(CONFIG_HOSTNAME_ITEM, PROCESS_LOCAL_COMMAND, &result) && NULL != (value = GET_STR_RESULT(&result))) { assert(*value); if (MAX_ZBX_HOSTNAME_LEN < strlen(*value)) { (*value)[MAX_ZBX_HOSTNAME_LEN] = '\0'; zabbix_log(LOG_LEVEL_WARNING, "hostname truncated to [%s])", *value); } CONFIG_HOSTNAME = zbx_strdup(CONFIG_HOSTNAME, *value); } else zabbix_log(LOG_LEVEL_WARNING, "failed to get system hostname from [%s])", CONFIG_HOSTNAME_ITEM); free_result(&result); } else if (NULL != CONFIG_HOSTNAME_ITEM) zabbix_log(LOG_LEVEL_WARNING, "both Hostname and HostnameItem defined, using [%s]", CONFIG_HOSTNAME); if (NULL != CONFIG_HOST_METADATA && NULL != CONFIG_HOST_METADATA_ITEM) { zabbix_log(LOG_LEVEL_WARNING, "both HostMetadata and HostMetadataItem defined, using [%s]", CONFIG_HOST_METADATA); } #ifndef _WINDOWS if (NULL == CONFIG_LOAD_MODULE_PATH) CONFIG_LOAD_MODULE_PATH = zbx_strdup(CONFIG_LOAD_MODULE_PATH, LIBDIR "/modules"); #endif #ifdef USE_PID_FILE if (NULL == CONFIG_PID_FILE) CONFIG_PID_FILE = "/tmp/zabbix_agentd.pid"; #endif }
static int vmware_set_powerstate_result(AGENT_RESULT *result) { int ret = SYSINFO_RET_OK; if (NULL != GET_STR_RESULT(result)) { if (0 == strcmp(result->str, "poweredOff")) SET_UI64_RESULT(result, 0); else if (0 == strcmp(result->str, "poweredOn")) SET_UI64_RESULT(result, 1); else if (0 == strcmp(result->str, "suspended")) SET_UI64_RESULT(result, 2); else ret = SYSINFO_RET_FAIL; UNSET_STR_RESULT(result); } return ret; }
void load_config() { struct cfg_line cfg[]= { /* PARAMETER ,VAR ,FUNC, TYPE(0i,1s), MANDATORY, MIN, MAX */ {"Server", &CONFIG_HOSTS_ALLOWED, 0,TYPE_STRING, PARM_MAND, 0,0}, {"Hostname", &CONFIG_HOSTNAME, 0,TYPE_STRING, PARM_OPT, 0,0}, #ifdef USE_PID_FILE {"PidFile", &APP_PID_FILE, 0,TYPE_STRING, PARM_OPT, 0,0}, #endif /* USE_PID_FILE */ {"LogFile", &CONFIG_LOG_FILE, 0,TYPE_STRING, PARM_OPT, 0,0}, {"LogFileSize", &CONFIG_LOG_FILE_SIZE, 0,TYPE_INT, PARM_OPT, 0,1024}, {"DisableActive", &CONFIG_DISABLE_ACTIVE, 0,TYPE_INT, PARM_OPT, 0,1}, {"Timeout", &CONFIG_TIMEOUT, 0,TYPE_INT, PARM_OPT, 1,30}, {"ListenPort", &CONFIG_LISTEN_PORT, 0,TYPE_INT, PARM_OPT, 1024,32767}, {"ServerPort", &CONFIG_SERVER_PORT, 0,TYPE_INT, PARM_OPT, 1024,32767}, {"ListenIP", &CONFIG_LISTEN_IP, 0,TYPE_STRING, PARM_OPT, 0,0}, {"DebugLevel", &CONFIG_LOG_LEVEL, 0,TYPE_INT, PARM_OPT, 0,5}, {"StartAgents", &CONFIG_ZABBIX_FORKS, 0,TYPE_INT, PARM_OPT, 1,16}, {"RefreshActiveChecks", &CONFIG_REFRESH_ACTIVE_CHECKS, 0,TYPE_INT, PARM_OPT,60,3600}, {"AllowRoot", &CONFIG_ALLOW_ROOT, 0,TYPE_INT, PARM_OPT,0,1}, {"LogUnresolvedSymbols",&CONFIG_LOG_UNRES_SYMB, 0, TYPE_STRING,PARM_OPT,0,1}, {"ActiveChecksBufSize", &CONFIG_ACTIVE_BUF_SIZE_MB, 0, TYPE_INT, PARM_OPT, 0, 10240}, {"ActiveChecksBufFile", &CONFIG_ACTIVE_BUF_FILE, 0, TYPE_STRING, PARM_OPT, 0, 0}, {0} }; AGENT_RESULT result; char **value = NULL; memset(&result, 0, sizeof(AGENT_RESULT)); parse_cfg_file(CONFIG_FILE, cfg); #ifdef USE_PID_FILE if(APP_PID_FILE == NULL) { APP_PID_FILE = DEFAULT_PID_FILE; } #endif /* USE_PID_FILE */ if(CONFIG_HOSTNAME == NULL) { if(SUCCEED == process("system.hostname", 0, &result)) { if( NULL != (value = GET_STR_RESULT(&result)) ) { CONFIG_HOSTNAME = strdup(*value); } } free_result(&result); if(CONFIG_HOSTNAME == NULL) { zabbix_log( LOG_LEVEL_CRIT, "Hostname is not defined"); exit(1); } } }
/****************************************************************************** * * * Function: discover_service * * * * Purpose: check if service is avaiable and update database * * * * Parameters: service typ,e ip address, port number * * * * Return value: * * * * Author: Alexei Vladishev * * * * Comments: * * * ******************************************************************************/ static int discover_service(DB_DCHECK *check, char *ip, int port) { int ret = SUCCEED; char key[MAX_STRING_LEN]; AGENT_RESULT value; DB_ITEM item; struct sigaction phan; assert(check); assert(ip); zabbix_log(LOG_LEVEL_DEBUG, "In discover_service(ip:%s, port:%d, type:%d)", ip, port, check->type); init_result(&value); switch(check->type) { case SVC_SSH: zbx_snprintf(key,sizeof(key),"net.tcp.service[ssh,%s,%d]", ip, port); break; case SVC_LDAP: zbx_snprintf(key,sizeof(key),"net.tcp.service[ldap,%s,%d]", ip, port); break; case SVC_SMTP: zbx_snprintf(key,sizeof(key),"net.tcp.service[smtp,%s,%d]", ip, port); break; case SVC_FTP: zbx_snprintf(key,sizeof(key),"net.tcp.service[ftp,%s,%d]", ip, port); break; case SVC_HTTP: zbx_snprintf(key,sizeof(key),"net.tcp.service[http,%s,%d]", ip, port); break; case SVC_POP: zbx_snprintf(key,sizeof(key),"net.tcp.service[pop,%s,%d]", ip, port); break; case SVC_NNTP: zbx_snprintf(key,sizeof(key),"net.tcp.service[nntp,%s,%d]", ip, port); break; case SVC_IMAP: zbx_snprintf(key,sizeof(key),"net.tcp.service[imap,%s,%d]", ip, port); break; case SVC_TCP: zbx_snprintf(key,sizeof(key),"net.tcp.service[tcp,%s,%d]", ip, port); break; case SVC_AGENT: case SVC_SNMPv1: case SVC_SNMPv2c: break; default: ret = FAIL; break; } if(ret == SUCCEED) { phan.sa_handler = &child_signal_handler; sigemptyset(&phan.sa_mask); phan.sa_flags = 0; sigaction(SIGALRM, &phan, NULL); alarm(10); switch(check->type) { /* Agent and SNMP checks */ case SVC_AGENT: case SVC_SNMPv1: case SVC_SNMPv2c: memset(&item,0,sizeof(DB_ITEM)); strscpy(item.key,check->key_); item.host_name = ip; item.host_ip = ip; item.host_dns = ip; item.useip = 1; item.port = port; item.value_type = ITEM_VALUE_TYPE_STR; if(check->type == SVC_SNMPv1) { item.type = ITEM_TYPE_SNMPv1; } else { item.type = ITEM_TYPE_SNMPv2c; } item.snmp_oid = check->key_; item.snmp_community = check->snmp_community; item.snmp_port = port; if(check->type==SVC_AGENT) { if(SUCCEED == get_value_agent(&item, &value)) { if(GET_STR_RESULT(&value)) { strscpy(check->value, value.str); } else ret = FAIL; } else { ret = FAIL; } } else #ifdef HAVE_SNMP { if(SUCCEED == get_value_snmp(&item, &value)) { if(GET_STR_RESULT(&value)) { strscpy(check->value, value.str); } else ret = FAIL; } else { ret = FAIL; } } #else { ret = FAIL; } #endif break; /* Simple checks */ default: if(process(key, 0, &value) == SUCCEED) { if(GET_UI64_RESULT(&value)) { if(value.ui64 == 0) ret = FAIL; } else ret = FAIL; } else ret = FAIL; break; } alarm(0); } free_result(&value); zabbix_log(LOG_LEVEL_DEBUG, "End discover_service()"); return ret; }
/****************************************************************************** * * * Function: zbx_set_defaults * * * * Purpose: set configuration defaults * * * * Author: Rudolfs Kreicbergs * * * ******************************************************************************/ static void zbx_set_defaults() { AGENT_RESULT result; char **value = NULL; CONFIG_SERVER_STARTUP_TIME = time(NULL); if (NULL == CONFIG_HOSTNAME) { if (NULL == CONFIG_HOSTNAME_ITEM) CONFIG_HOSTNAME_ITEM = zbx_strdup(CONFIG_HOSTNAME_ITEM, "system.hostname"); init_result(&result); if (SUCCEED == process(CONFIG_HOSTNAME_ITEM, PROCESS_LOCAL_COMMAND, &result) && NULL != (value = GET_STR_RESULT(&result))) { assert(*value); if (MAX_ZBX_HOSTNAME_LEN < strlen(*value)) { (*value)[MAX_ZBX_HOSTNAME_LEN] = '\0'; zabbix_log(LOG_LEVEL_WARNING, "proxy name truncated to [%s])", *value); } CONFIG_HOSTNAME = zbx_strdup(CONFIG_HOSTNAME, *value); } else zabbix_log(LOG_LEVEL_WARNING, "failed to get proxy name from [%s])", CONFIG_HOSTNAME_ITEM); free_result(&result); } else if (NULL != CONFIG_HOSTNAME_ITEM) zabbix_log(LOG_LEVEL_WARNING, "both Hostname and HostnameItem defined, using [%s]", CONFIG_HOSTNAME); if (NULL == CONFIG_DBHOST) CONFIG_DBHOST = zbx_strdup(CONFIG_DBHOST, "localhost"); if (NULL == CONFIG_SNMPTRAP_FILE) CONFIG_SNMPTRAP_FILE = zbx_strdup(CONFIG_SNMPTRAP_FILE, "/tmp/zabbix_traps.tmp"); if (NULL == CONFIG_PID_FILE) CONFIG_PID_FILE = zbx_strdup(CONFIG_PID_FILE, "/tmp/zabbix_proxy.pid"); if (NULL == CONFIG_TMPDIR) CONFIG_TMPDIR = zbx_strdup(CONFIG_TMPDIR, "/tmp"); if (NULL == CONFIG_FPING_LOCATION) CONFIG_FPING_LOCATION = zbx_strdup(CONFIG_FPING_LOCATION, "/usr/sbin/fping"); #ifdef HAVE_IPV6 if (NULL == CONFIG_FPING6_LOCATION) CONFIG_FPING6_LOCATION = zbx_strdup(CONFIG_FPING6_LOCATION, "/usr/sbin/fping6"); #endif if (NULL == CONFIG_EXTERNALSCRIPTS) CONFIG_EXTERNALSCRIPTS = zbx_strdup(CONFIG_EXTERNALSCRIPTS, DATADIR "/zabbix/externalscripts"); if (ZBX_PROXYMODE_ACTIVE != CONFIG_PROXYMODE || 0 == CONFIG_HEARTBEAT_FREQUENCY) CONFIG_HEARTBEAT_FORKS = 0; if (ZBX_PROXYMODE_PASSIVE == CONFIG_PROXYMODE) { CONFIG_CONFSYNCER_FORKS = CONFIG_DATASENDER_FORKS = 0; daemon_type = ZBX_DAEMON_TYPE_PROXY_PASSIVE; } }
/****************************************************************************** * * * Function: discover_service * * * * Purpose: check if service is available and update database * * * * Parameters: service type, ip address, port number * * * * Author: Alexei Vladishev * * * ******************************************************************************/ static int discover_service(DB_DCHECK *dcheck, char *ip, int port, char *value) { const char *__function_name = "discover_service"; int ret = SUCCEED; char key[MAX_STRING_LEN], error[ITEM_ERROR_LEN_MAX]; const char *service = NULL; AGENT_RESULT result; DC_ITEM item; ZBX_FPING_HOST host; zabbix_log(LOG_LEVEL_DEBUG, "In %s()", __function_name); init_result(&result); *value = '\0'; switch (dcheck->type) { case SVC_SSH: service = "ssh"; break; case SVC_LDAP: service = "ldap"; break; case SVC_SMTP: service = "smtp"; break; case SVC_FTP: service = "ftp"; break; case SVC_HTTP: service = "http"; break; case SVC_POP: service = "pop"; break; case SVC_NNTP: service = "nntp"; break; case SVC_IMAP: service = "imap"; break; case SVC_TCP: service = "tcp"; break; case SVC_HTTPS: service = "https"; break; case SVC_TELNET: service = "telnet"; break; case SVC_AGENT: case SVC_SNMPv1: case SVC_SNMPv2c: case SVC_SNMPv3: case SVC_ICMPPING: break; default: ret = FAIL; break; } if (SUCCEED == ret) { alarm(CONFIG_TIMEOUT); switch (dcheck->type) { /* simple checks */ case SVC_SSH: case SVC_LDAP: case SVC_SMTP: case SVC_FTP: case SVC_HTTP: case SVC_POP: case SVC_NNTP: case SVC_IMAP: case SVC_TCP: case SVC_HTTPS: case SVC_TELNET: zbx_snprintf(key, sizeof(key), "net.tcp.service[%s,%s,%d]", service, ip, port); if (SUCCEED != process(key, 0, &result) || NULL == GET_UI64_RESULT(&result) || 0 == result.ui64) { ret = FAIL; } break; /* agent and SNMP checks */ case SVC_AGENT: case SVC_SNMPv1: case SVC_SNMPv2c: case SVC_SNMPv3: memset(&item, 0, sizeof(DC_ITEM)); strscpy(item.key_orig, dcheck->key_); item.key = item.key_orig; item.interface.useip = 1; item.interface.addr = ip; item.interface.port = port; item.value_type = ITEM_VALUE_TYPE_STR; switch (dcheck->type) { case SVC_SNMPv1: item.type = ITEM_TYPE_SNMPv1; break; case SVC_SNMPv2c: item.type = ITEM_TYPE_SNMPv2c; break; case SVC_SNMPv3: item.type = ITEM_TYPE_SNMPv3; break; default: item.type = ITEM_TYPE_ZABBIX; break; } if (SVC_AGENT == dcheck->type) { if (SUCCEED == get_value_agent(&item, &result) && NULL != GET_STR_RESULT(&result)) zbx_strlcpy(value, result.str, DSERVICE_VALUE_LEN_MAX); else ret = FAIL; } else #ifdef HAVE_SNMP { item.snmp_community = strdup(dcheck->snmp_community); item.snmp_oid = strdup(dcheck->key_); substitute_simple_macros(NULL, NULL, NULL, NULL, NULL, NULL, &item.snmp_community, MACRO_TYPE_ITEM_FIELD, NULL, 0); substitute_key_macros(&item.snmp_oid, NULL, NULL, NULL, MACRO_TYPE_SNMP_OID, NULL, 0); if (ITEM_TYPE_SNMPv3 == item.type) { item.snmpv3_securityname = strdup(dcheck->snmpv3_securityname); item.snmpv3_securitylevel = dcheck->snmpv3_securitylevel; item.snmpv3_authpassphrase = strdup(dcheck->snmpv3_authpassphrase); item.snmpv3_privpassphrase = strdup(dcheck->snmpv3_privpassphrase); substitute_simple_macros(NULL, NULL, NULL, NULL, NULL, NULL, &item.snmpv3_securityname, MACRO_TYPE_ITEM_FIELD, NULL, 0); substitute_simple_macros(NULL, NULL, NULL, NULL, NULL, NULL, &item.snmpv3_authpassphrase, MACRO_TYPE_ITEM_FIELD, NULL, 0); substitute_simple_macros(NULL, NULL, NULL, NULL, NULL, NULL, &item.snmpv3_privpassphrase, MACRO_TYPE_ITEM_FIELD, NULL, 0); } if (SUCCEED == get_value_snmp(&item, &result) && NULL != GET_STR_RESULT(&result)) zbx_strlcpy(value, result.str, DSERVICE_VALUE_LEN_MAX); else ret = FAIL; zbx_free(item.snmp_community); zbx_free(item.snmp_oid); if (ITEM_TYPE_SNMPv3 == item.type) { zbx_free(item.snmpv3_securityname); zbx_free(item.snmpv3_authpassphrase); zbx_free(item.snmpv3_privpassphrase); } } #else ret = FAIL; #endif /* HAVE_SNMP */ if (FAIL == ret && ISSET_MSG(&result)) { zabbix_log(LOG_LEVEL_DEBUG, "discovery: item [%s] error: %s", item.key, result.msg); } break; case SVC_ICMPPING: memset(&host, 0, sizeof(host)); host.addr = strdup(ip); if (SUCCEED != do_ping(&host, 1, 3, 0, 0, 0, error, sizeof(error)) || 0 == host.rcv) ret = FAIL; zbx_free(host.addr); break; default: break; } alarm(0); } free_result(&result); zabbix_log(LOG_LEVEL_DEBUG, "End of %s():%s", __function_name, zbx_result_string(ret)); return ret; }
/****************************************************************************** * * * Function: refresh_active_checks * * * * Purpose: Retrieve from Zabbix server list of active checks * * * * Parameters: host - IP or Hostname of Zabbix server * * port - port of Zabbix server * * * * Return value: returns SUCCEED on successful parsing, * * FAIL on other cases * * * * Author: Eugene Grigorjev, Alexei Vladishev (new json protocol) * * * * Comments: * * * ******************************************************************************/ static int refresh_active_checks(const char *host, unsigned short port) { const char *__function_name = "refresh_active_checks"; zbx_sock_t s; char *buf; int ret; struct zbx_json json; static int last_ret = SUCCEED; zabbix_log(LOG_LEVEL_DEBUG, "In %s() host:'%s' port:%hu", __function_name, host, port); zbx_json_init(&json, ZBX_JSON_STAT_BUF_LEN); zbx_json_addstring(&json, ZBX_PROTO_TAG_REQUEST, ZBX_PROTO_VALUE_GET_ACTIVE_CHECKS, ZBX_JSON_TYPE_STRING); zbx_json_addstring(&json, ZBX_PROTO_TAG_HOST, CONFIG_HOSTNAME, ZBX_JSON_TYPE_STRING); if (NULL != CONFIG_HOST_METADATA) { zbx_json_addstring(&json, ZBX_PROTO_TAG_HOST_METADATA, CONFIG_HOST_METADATA, ZBX_JSON_TYPE_STRING); } else if (NULL != CONFIG_HOST_METADATA_ITEM) { char **value; AGENT_RESULT result; init_result(&result); if (SUCCEED == process(CONFIG_HOST_METADATA_ITEM, PROCESS_LOCAL_COMMAND, &result) && NULL != (value = GET_STR_RESULT(&result)) && NULL != *value) { if (SUCCEED != zbx_is_utf8(*value)) { zabbix_log(LOG_LEVEL_WARNING, "cannot get host metadata using \"%s\" item specified by" " \"HostMetadataItem\" configuration parameter: returned value is not" " an UTF-8 string", CONFIG_HOST_METADATA_ITEM); } else { if (HOST_METADATA_LEN < zbx_strlen_utf8(*value)) { size_t bytes; zabbix_log(LOG_LEVEL_WARNING, "the returned value of \"%s\" item specified by" " \"HostMetadataItem\" configuration parameter is too long," " using first %d characters", CONFIG_HOST_METADATA_ITEM, HOST_METADATA_LEN); bytes = zbx_strlen_utf8_n(*value, HOST_METADATA_LEN); (*value)[bytes] = '\0'; } zbx_json_addstring(&json, ZBX_PROTO_TAG_HOST_METADATA, *value, ZBX_JSON_TYPE_STRING); } } else zabbix_log(LOG_LEVEL_WARNING, "cannot get host metadata using \"%s\" item specified by" " \"HostMetadataItem\" configuration parameter", CONFIG_HOST_METADATA_ITEM); free_result(&result); } if (NULL != CONFIG_LISTEN_IP) { char *p; if (NULL != (p = strchr(CONFIG_LISTEN_IP, ','))) *p = '\0'; zbx_json_addstring(&json, ZBX_PROTO_TAG_IP, CONFIG_LISTEN_IP, ZBX_JSON_TYPE_STRING); if (NULL != p) *p = ','; } if (ZBX_DEFAULT_AGENT_PORT != CONFIG_LISTEN_PORT) zbx_json_adduint64(&json, ZBX_PROTO_TAG_PORT, CONFIG_LISTEN_PORT); if (SUCCEED == (ret = zbx_tcp_connect(&s, CONFIG_SOURCE_IP, host, port, CONFIG_TIMEOUT))) { zabbix_log(LOG_LEVEL_DEBUG, "sending [%s]", json.buffer); if (SUCCEED == (ret = zbx_tcp_send(&s, json.buffer))) { zabbix_log(LOG_LEVEL_DEBUG, "before read"); if (SUCCEED == (ret = SUCCEED_OR_FAIL(zbx_tcp_recv_ext(&s, &buf, ZBX_TCP_READ_UNTIL_CLOSE, 0)))) { zabbix_log(LOG_LEVEL_DEBUG, "got [%s]", buf); if (SUCCEED != last_ret) { zabbix_log(LOG_LEVEL_WARNING, "active check configuration update from [%s:%hu]" " is working again", host, port); } parse_list_of_checks(buf, host, port); } } zbx_tcp_close(&s); } if (SUCCEED != ret && SUCCEED == last_ret) { zabbix_log(LOG_LEVEL_WARNING, "active check configuration update from [%s:%hu] started to fail (%s)", host, port, zbx_tcp_strerror()); } last_ret = ret; zbx_json_free(&json); zabbix_log(LOG_LEVEL_DEBUG, "End of %s():%s", __function_name, zbx_result_string(ret)); return ret; }
/****************************************************************************** * * * Function: update_item * * * * Purpose: update item info after new value is received * * * * Parameters: item - item data * * value - new value of the item * * now - current timestamp * * * * Author: Alexei Vladishev, Eugene Grigorjev * * * * Comments: * * * ******************************************************************************/ static void update_item(DB_ITEM *item, AGENT_RESULT *value, time_t now) { char *value_esc; zbx_uint64_t value_uint64; double value_double; zabbix_log(LOG_LEVEL_DEBUG, "In update_item()"); item->nextcheck = calculate_item_nextcheck(item->itemid, item->type, item->delay, item->delay_flex, now); switch (item->value_type) { case ITEM_VALUE_TYPE_FLOAT: if (NULL == GET_DBL_RESULT(value)) break; switch (item->delta) { /* Should we store delta or original value? */ case ITEM_STORE_AS_IS: value_double = DBmultiply_value_float(item, value->dbl); DBexecute("update items set nextcheck=%d,prevvalue=lastvalue,prevorgvalue=NULL," "lastvalue='" ZBX_FS_DBL "',lastclock=%d where itemid=" ZBX_FS_UI64, item->nextcheck, value_double, (int)now, item->itemid); SET_DBL_RESULT(value, value_double); break; case ITEM_STORE_SPEED_PER_SECOND: /* Delta as speed of change */ if (0 == item->prevorgvalue_null && item->prevorgvalue_dbl <= value->dbl) { /* In order to continue normal processing, we assume difference 1 second Otherwise function update_functions and update_triggers won't work correctly*/ if (now != item->lastclock) value_double = (value->dbl - item->prevorgvalue_dbl) / (now - item->lastclock); else value_double = value->dbl - item->prevorgvalue_dbl; value_double = DBmultiply_value_float(item, value_double); DBexecute("update items set nextcheck=%d,prevvalue=lastvalue,prevorgvalue='" ZBX_FS_DBL "'," "lastvalue='" ZBX_FS_DBL "',lastclock=%d where itemid=" ZBX_FS_UI64, item->nextcheck, value->dbl, value_double, (int)now, item->itemid); SET_DBL_RESULT(value, value_double); } else { DBexecute("update items set nextcheck=%d,prevorgvalue='" ZBX_FS_DBL "',lastclock=%d where itemid=" ZBX_FS_UI64, item->nextcheck, value->dbl, (int)now, item->itemid); } break; case ITEM_STORE_SIMPLE_CHANGE: /* Real delta: simple difference between values */ if (0 == item->prevorgvalue_null && item->prevorgvalue_dbl <= value->dbl) { value_double = DBmultiply_value_float(item, value->dbl - item->prevorgvalue_dbl); DBexecute("update items set nextcheck=%d,prevvalue=lastvalue,prevorgvalue='" ZBX_FS_DBL "'," "lastvalue='" ZBX_FS_DBL "',lastclock=%d where itemid=" ZBX_FS_UI64, item->nextcheck, value->dbl, value_double, (int)now, item->itemid); SET_DBL_RESULT(value, value_double); } else { DBexecute("update items set nextcheck=%d,prevorgvalue='" ZBX_FS_DBL "',lastclock=%d where itemid=" ZBX_FS_UI64, item->nextcheck, value->dbl, (int)now, item->itemid); } break; } break; case ITEM_VALUE_TYPE_UINT64: if (NULL == GET_UI64_RESULT(value)) break; switch (item->delta) { /* Should we store delta or original value? */ case ITEM_STORE_AS_IS: value_uint64 = DBmultiply_value_uint64(item, value->ui64); DBexecute("update items set nextcheck=%d,prevvalue=lastvalue,prevorgvalue=NULL," "lastvalue='" ZBX_FS_UI64 "',lastclock=%d where itemid=" ZBX_FS_UI64, item->nextcheck, value_uint64, (int)now, item->itemid); SET_UI64_RESULT(value, value_uint64); break; case ITEM_STORE_SPEED_PER_SECOND: /* Delta as speed of change */ if (0 == item->prevorgvalue_null && item->prevorgvalue_uint64 <= value->ui64) { if (now != item->lastclock) value_uint64 = (zbx_uint64_t)(value->ui64 - item->prevorgvalue_uint64) / (now - item->lastclock); else value_uint64 = value->ui64 - item->prevorgvalue_uint64; value_uint64 = DBmultiply_value_uint64(item, value_uint64); DBexecute("update items set nextcheck=%d,prevvalue=lastvalue,prevorgvalue='" ZBX_FS_UI64 "'," "lastvalue='" ZBX_FS_UI64 "',lastclock=%d where itemid=" ZBX_FS_UI64, item->nextcheck, value->ui64, value_uint64, (int)now, item->itemid); SET_UI64_RESULT(value, value_uint64); } else { DBexecute("update items set nextcheck=%d,prevorgvalue='" ZBX_FS_UI64 "',lastclock=%d where itemid=" ZBX_FS_UI64, item->nextcheck, value->ui64, (int)now, item->itemid); } break; case ITEM_STORE_SIMPLE_CHANGE: /* Real delta: simple difference between values */ if (0 == item->prevorgvalue_null && item->prevorgvalue_uint64 <= value->ui64) { value_uint64 = DBmultiply_value_uint64(item, value->ui64 - item->prevorgvalue_uint64); DBexecute("update items set nextcheck=%d,prevvalue=lastvalue,prevorgvalue='" ZBX_FS_UI64 "'," "lastvalue='" ZBX_FS_UI64 "',lastclock=%d where itemid=" ZBX_FS_UI64, item->nextcheck, value->ui64, value_uint64, (int)now, item->itemid); SET_UI64_RESULT(value, value_uint64); } else { DBexecute("update items set nextcheck=%d,prevorgvalue='" ZBX_FS_UI64 "',lastclock=%d where itemid=" ZBX_FS_UI64, item->nextcheck, value->ui64, (int)now, item->itemid); } break; } break; case ITEM_VALUE_TYPE_STR: case ITEM_VALUE_TYPE_TEXT: if (NULL == GET_STR_RESULT(value)) break; value_esc = DBdyn_escape_string_len(value->str, ITEM_LASTVALUE_LEN); DBexecute("update items set nextcheck=%d,prevvalue=lastvalue,lastvalue='%s',lastclock=%d" " where itemid=" ZBX_FS_UI64, item->nextcheck, value_esc, (int)now, item->itemid); zbx_free(value_esc); break; case ITEM_VALUE_TYPE_LOG: if (NULL == GET_STR_RESULT(value)) break; value_esc = DBdyn_escape_string_len(value->str, ITEM_LASTVALUE_LEN); DBexecute("update items set nextcheck=%d,prevvalue=lastvalue,lastvalue='%s',lastclock=%d,lastlogsize=%d" " where itemid=" ZBX_FS_UI64, item->nextcheck, value_esc, (int)now, item->lastlogsize, item->itemid); zbx_free(value_esc); break; } item->prevvalue_str = item->lastvalue_str; item->prevvalue_dbl = item->lastvalue_dbl; item->prevvalue_uint64 = item->lastvalue_uint64; item->prevvalue_null = item->lastvalue_null; item->lastvalue_uint64 = value->ui64; item->lastvalue_dbl = value->dbl; item->lastvalue_str = value->str; item->lastvalue_null = 0; /* Required for nodata() */ item->lastclock = now; /* Update item status if required */ if (item->status == ITEM_STATUS_NOTSUPPORTED) { zabbix_log( LOG_LEVEL_WARNING, "Parameter [%s] became supported by agent on host [%s]", item->key, item->host_name); zabbix_syslog("Parameter [%s] became supported by agent on host [%s]", item->key, item->host_name); item->status = ITEM_STATUS_ACTIVE; DBexecute("update items set status=%d,error='' where itemid=" ZBX_FS_UI64, item->status, item->itemid); } zabbix_log(LOG_LEVEL_DEBUG, "End of update_item()"); }
/****************************************************************************** * * * Function: add_history * * * * Purpose: add new value to history * * * * Parameters: item - item data * * value - new value of the item * * now - new value of the item * * * * Author: Alexei Vladishev * * * * Comments: * * * ******************************************************************************/ static int add_history(DB_ITEM *item, AGENT_RESULT *value, int now) { int ret = FAIL; zbx_uint64_t value_uint64; double value_double; zabbix_log(LOG_LEVEL_DEBUG, "In add_history(key:%s,value_type:%X,type:%X)", item->key, item->value_type, value->type); if (value->type & AR_UINT64) zabbix_log(LOG_LEVEL_DEBUG, "In add_history(itemid:"ZBX_FS_UI64",UINT64:"ZBX_FS_UI64")", item->itemid, value->ui64); if (value->type & AR_STRING) zabbix_log(LOG_LEVEL_DEBUG, "In add_history(itemid:"ZBX_FS_UI64",STRING:%s)", item->itemid, value->str); if (value->type & AR_DOUBLE) zabbix_log(LOG_LEVEL_DEBUG, "In add_history(itemid:"ZBX_FS_UI64",DOUBLE:"ZBX_FS_DBL")", item->itemid, value->dbl); if (value->type & AR_TEXT) zabbix_log(LOG_LEVEL_DEBUG, "In add_history(itemid:"ZBX_FS_UI64",TEXT:[%s])", item->itemid, value->text); switch (item->value_type) { case ITEM_VALUE_TYPE_FLOAT: if (NULL == GET_DBL_RESULT(value)) break; switch (item->delta) { /* Should we store delta or original value? */ case ITEM_STORE_AS_IS: if (item->history > 0) DBadd_history(item->itemid, DBmultiply_value_float(item, value->dbl), now); ret = SUCCEED; break; case ITEM_STORE_SPEED_PER_SECOND: /* Delta as speed of change */ if (0 == item->prevorgvalue_null && item->prevorgvalue_dbl <= value->dbl && item->lastclock < now) { if (item->history > 0) { value_double = (value->dbl - item->prevorgvalue_dbl) / (now - item->lastclock); DBadd_history(item->itemid, DBmultiply_value_float(item, value_double), now); } ret = SUCCEED; } break; case ITEM_STORE_SIMPLE_CHANGE: /* Real delta: simple difference between values */ if (0 == item->prevorgvalue_null && item->prevorgvalue_dbl <= value->dbl) { if (item->history > 0) DBadd_history(item->itemid, DBmultiply_value_float(item, value->dbl - item->prevorgvalue_dbl), now); ret = SUCCEED; } break; default: zabbix_log(LOG_LEVEL_ERR, "Value not stored for itemid [" ZBX_FS_UI64 "]. Unknown delta [%d]", item->itemid, item->delta); zabbix_syslog("Value not stored for itemid [" ZBX_FS_UI64 "]. Unknown delta [%d]", item->itemid, item->delta); } break; case ITEM_VALUE_TYPE_UINT64: if (NULL == GET_UI64_RESULT(value)) break; switch (item->delta) { /* Should we store delta or original value? */ case ITEM_STORE_AS_IS: if (item->history > 0) DBadd_history_uint(item->itemid, DBmultiply_value_uint64(item, value->ui64), now); ret = SUCCEED; break; case ITEM_STORE_SPEED_PER_SECOND: /* Delta as speed of change */ if (0 == item->prevorgvalue_null && item->prevorgvalue_uint64 <= value->ui64 && item->lastclock < now) { if (item->history > 0) { value_uint64 = (zbx_uint64_t)(value->ui64 - item->prevorgvalue_uint64) / (now - item->lastclock); DBadd_history_uint(item->itemid, DBmultiply_value_uint64(item, value_uint64), now); } ret = SUCCEED; } break; case ITEM_STORE_SIMPLE_CHANGE: /* Real delta: simple difference between values */ if (0 == item->prevorgvalue_null && item->prevorgvalue_uint64 <= value->ui64) { if (item->history > 0) DBadd_history_uint(item->itemid, DBmultiply_value_uint64(item, value->ui64 - item->prevorgvalue_uint64), now); ret = SUCCEED; } break; default: zabbix_log(LOG_LEVEL_ERR, "Value not stored for itemid [" ZBX_FS_UI64 "]. Unknown delta [%d]", item->itemid, item->delta); zabbix_syslog("Value not stored for itemid [" ZBX_FS_UI64 "]. Unknown delta [%d]", item->itemid, item->delta); } break; case ITEM_VALUE_TYPE_STR: if (NULL == GET_STR_RESULT(value)) break; if (item->history > 0) DBadd_history_str(item->itemid, value->str, now); ret = SUCCEED; break; case ITEM_VALUE_TYPE_LOG: if (NULL == GET_STR_RESULT(value)) break; if (item->history > 0) DBadd_history_log(item->itemid, value->str, now, item->timestamp, item->eventlog_source, item->eventlog_severity, item->lastlogsize); ret = SUCCEED; break; case ITEM_VALUE_TYPE_TEXT: if (NULL == GET_TEXT_RESULT(value)) break; if (item->history > 0) DBadd_history_text(item->itemid,value->text,now); ret = SUCCEED; break; default: zabbix_log(LOG_LEVEL_ERR, "Unknown value type [%d] for itemid [" ZBX_FS_UI64 "]", item->value_type, item->itemid); zabbix_syslog("Unknown value type [%d] for itemid [" ZBX_FS_UI64 "]", item->value_type, item->itemid); } zabbix_log(LOG_LEVEL_DEBUG, "End of add_history():%s", zbx_result_string(ret)); return ret; }
/****************************************************************************** * * * Function: init_config * * * * Purpose: parse config file and update configuration parameters * * * * Parameters: * * * * Return value: * * * * Author: Alexei Vladishev * * * * Comments: will terminate process if parsing fails * * * ******************************************************************************/ void init_config(void) { AGENT_RESULT result; char **value = NULL; static struct cfg_line cfg[]= { /* PARAMETER ,VAR ,FUNC, TYPE(0i,1s),MANDATORY,MIN,MAX */ {"Server",&CONFIG_SERVER,0,TYPE_STRING,PARM_MAND,0,0}, {"ServerPort",&CONFIG_SERVER_PORT,0,TYPE_INT,PARM_OPT,1024,32768}, {"Hostname",&CONFIG_HOSTNAME,0,TYPE_STRING,PARM_OPT,0,0}, {"StartDBSyncers",&CONFIG_DBSYNCER_FORKS,0,TYPE_INT,PARM_OPT,0,16}, {"StartDiscoverers",&CONFIG_DISCOVERER_FORKS,0,TYPE_INT,PARM_OPT,0,255}, {"StartHTTPPollers",&CONFIG_HTTPPOLLER_FORKS,0,TYPE_INT,PARM_OPT,0,255}, {"StartPingers",&CONFIG_PINGER_FORKS,0,TYPE_INT,PARM_OPT,0,255}, {"StartPollers",&CONFIG_POLLER_FORKS,0,TYPE_INT,PARM_OPT,0,255}, {"StartIPMIPollers",&CONFIG_IPMIPOLLER_FORKS,0,TYPE_INT,PARM_OPT,0,255}, {"StartPollersUnreachable",&CONFIG_UNREACHABLE_POLLER_FORKS,0,TYPE_INT,PARM_OPT,0,255}, {"StartTrappers",&CONFIG_TRAPPERD_FORKS,0,TYPE_INT,PARM_OPT,0,255}, {"HousekeepingFrequency",&CONFIG_HOUSEKEEPING_FREQUENCY,0,TYPE_INT,PARM_OPT,1,24}, {"ProxyLocalBuffer",&CONFIG_PROXY_LOCAL_BUFFER,0,TYPE_INT,PARM_OPT,0,720}, {"ProxyOfflineBuffer",&CONFIG_PROXY_OFFLINE_BUFFER,0,TYPE_INT,PARM_OPT,1,720}, {"HeartbeatFrequency",&CONFIG_HEARTBEAT_FREQUENCY,0,TYPE_INT,PARM_OPT,0,3600}, {"ConfigFrequency",&CONFIG_PROXYCONFIG_FREQUENCY,0,TYPE_INT,PARM_OPT,1,3600*7*24}, {"DataSenderFrequency",&CONFIG_DATASENDER_FREQUENCY,0,TYPE_INT,PARM_OPT,1,3600}, /* {"SenderFrequency",&CONFIG_SENDER_FREQUENCY,0,TYPE_INT,PARM_OPT,5,3600},*/ {"PingerFrequency",&CONFIG_PINGER_FREQUENCY,0,TYPE_INT,PARM_OPT,1,3600}, {"TmpDir",&CONFIG_TMPDIR,0,TYPE_STRING,PARM_OPT,0,0}, {"FpingLocation",&CONFIG_FPING_LOCATION,0,TYPE_STRING,PARM_OPT,0,0}, #ifdef HAVE_IPV6 {"Fping6Location",&CONFIG_FPING6_LOCATION,0,TYPE_STRING,PARM_OPT,0,0}, #endif /* HAVE_IPV6 */ {"Timeout",&CONFIG_TIMEOUT,0,TYPE_INT,PARM_OPT,1,30}, {"TrapperTimeout",&CONFIG_TRAPPER_TIMEOUT,0,TYPE_INT,PARM_OPT,1,300}, {"UnreachablePeriod",&CONFIG_UNREACHABLE_PERIOD,0,TYPE_INT,PARM_OPT,1,3600}, {"UnreachableDelay",&CONFIG_UNREACHABLE_DELAY,0,TYPE_INT,PARM_OPT,1,3600}, {"UnavailableDelay",&CONFIG_UNAVAILABLE_DELAY,0,TYPE_INT,PARM_OPT,1,3600}, {"ListenIP",&CONFIG_LISTEN_IP,0,TYPE_STRING,PARM_OPT,0,0}, {"ListenPort",&CONFIG_LISTEN_PORT,0,TYPE_INT,PARM_OPT,1024,32768}, {"SourceIP",&CONFIG_SOURCE_IP,0,TYPE_STRING,PARM_OPT,0,0}, /* {"NoTimeWait",&CONFIG_NOTIMEWAIT,0,TYPE_INT,PARM_OPT,0,1},*/ /* {"DisablePinger",&CONFIG_DISABLE_PINGER,0,TYPE_INT,PARM_OPT,0,1},*/ {"DebugLevel",&CONFIG_LOG_LEVEL,0,TYPE_INT,PARM_OPT,0,4}, {"PidFile",&APP_PID_FILE,0,TYPE_STRING,PARM_OPT,0,0}, {"LogFile",&CONFIG_LOG_FILE,0,TYPE_STRING,PARM_OPT,0,0}, {"LogFileSize",&CONFIG_LOG_FILE_SIZE,0,TYPE_INT,PARM_OPT,0,1024}, /* {"AlertScriptsPath",&CONFIG_ALERT_SCRIPTS_PATH,0,TYPE_STRING,PARM_OPT,0,0},*/ {"ExternalScripts",&CONFIG_EXTERNALSCRIPTS,0,TYPE_STRING,PARM_OPT,0,0}, {"DBHost",&CONFIG_DBHOST,0,TYPE_STRING,PARM_OPT,0,0}, {"DBName",&CONFIG_DBNAME,0,TYPE_STRING,PARM_MAND,0,0}, {"DBUser",&CONFIG_DBUSER,0,TYPE_STRING,PARM_OPT,0,0}, {"DBPassword",&CONFIG_DBPASSWORD,0,TYPE_STRING,PARM_OPT,0,0}, {"DBSocket",&CONFIG_DBSOCKET,0,TYPE_STRING,PARM_OPT,0,0}, {"DBPort",&CONFIG_DBPORT,0,TYPE_INT,PARM_OPT,1024,65535}, {0} }; CONFIG_SERVER_STARTUP_TIME = time(NULL); parse_cfg_file(CONFIG_FILE,cfg); if(CONFIG_HOSTNAME == NULL) { if(SUCCEED == process("system.hostname", 0, &result)) { if( NULL != (value = GET_STR_RESULT(&result)) ) { CONFIG_HOSTNAME = strdup(*value); } } free_result(&result); if(CONFIG_HOSTNAME == NULL) { zabbix_log( LOG_LEVEL_CRIT, "Hostname is not defined"); exit(1); } } if(CONFIG_DBNAME == NULL) { zabbix_log( LOG_LEVEL_CRIT, "DBName not in config file"); exit(1); } if(APP_PID_FILE == NULL) { APP_PID_FILE=strdup("/tmp/zabbix_server.pid"); } if(CONFIG_ALERT_SCRIPTS_PATH == NULL) { CONFIG_ALERT_SCRIPTS_PATH=strdup("/home/zabbix/bin"); } if(CONFIG_TMPDIR == NULL) { CONFIG_TMPDIR=strdup("/tmp"); } if(CONFIG_FPING_LOCATION == NULL) { CONFIG_FPING_LOCATION=strdup("/usr/sbin/fping"); } #ifdef HAVE_IPV6 if(CONFIG_FPING6_LOCATION == NULL) { CONFIG_FPING6_LOCATION=strdup("/usr/sbin/fping6"); } #endif /* HAVE_IPV6 */ if(CONFIG_EXTERNALSCRIPTS == NULL) { CONFIG_EXTERNALSCRIPTS=strdup("/etc/zabbix/externalscripts"); } #ifndef HAVE_LIBCURL CONFIG_HTTPPOLLER_FORKS = 0; #endif #ifndef HAVE_OPENIPMI CONFIG_IPMIPOLLER_FORKS = 0; #endif }