int zbx_variant_set_numeric(zbx_variant_t *value, const char *text) { zbx_uint64_t value_ui64; char buffer[MAX_STRING_LEN]; zbx_strlcpy(buffer, text, sizeof(buffer)); zbx_rtrim(buffer, "\n\r"); /* trim newline for historical reasons / backwards compatibility */ zbx_trim_integer(buffer); del_zeros(buffer); if ('+' == buffer[0]) { /* zbx_trim_integer() stripped one '+' sign, so there's more than one '+' sign in the 'text' argument */ return FAIL; } if (SUCCEED == is_uint64(buffer, &value_ui64)) { zbx_variant_set_ui64(value, value_ui64); return SUCCEED; } if (SUCCEED == is_double(buffer)) { zbx_variant_set_dbl(value, atof(buffer)); return SUCCEED; } return FAIL; }
static int variant_to_ui64(zbx_variant_t *value) { zbx_uint64_t value_ui64; char buffer[MAX_STRING_LEN]; switch (value->type) { case ZBX_VARIANT_UI64: return SUCCEED; case ZBX_VARIANT_DBL: if (0 > value->data.dbl) return FAIL; zbx_variant_set_ui64(value, value->data.dbl); return SUCCEED; case ZBX_VARIANT_STR: zbx_strlcpy(buffer, value->data.str, sizeof(buffer)); break; default: return FAIL; } zbx_rtrim(buffer, "\n\r"); /* trim newline for historical reasons / backwards compatibility */ zbx_trim_integer(buffer); del_zeros(buffer); if (SUCCEED != is_uint64(buffer, &value_ui64)) return FAIL; zbx_variant_clear(value); zbx_variant_set_ui64(value, value_ui64); return SUCCEED; }
int NET_TCP_LISTEN(const char *cmd, const char *param, unsigned flags, AGENT_RESULT *result) { /* Declare and initialize variables */ MIB_TCPTABLE *pTcpTable = NULL; DWORD dwSize, dwRetVal; int i, ret = SYSINFO_RET_FAIL; zbx_uint64_t port; char tmp[8]; if (num_param(param) > 1) return SYSINFO_RET_FAIL; if (0 != get_param(param, 1, tmp, sizeof(tmp))) return SYSINFO_RET_FAIL; if (SUCCEED != is_uint64(tmp, &port)) return SYSINFO_RET_FAIL; if (port > 65535) return SYSINFO_RET_FAIL; dwSize = sizeof(MIB_TCPTABLE); pTcpTable = (MIB_TCPTABLE *)zbx_malloc(pTcpTable, dwSize); /* Make an initial call to GetTcpTable to get the necessary size into the dwSize variable */ if (ERROR_INSUFFICIENT_BUFFER == (dwRetVal = GetTcpTable(pTcpTable, &dwSize, TRUE))) pTcpTable = (MIB_TCPTABLE *)zbx_realloc(pTcpTable, dwSize); /* Make a second call to GetTcpTable to get the actual data we require */ if (NO_ERROR == (dwRetVal = GetTcpTable(pTcpTable, &dwSize, TRUE))) { for (i = 0; i < (int) pTcpTable->dwNumEntries; i++) { if (MIB_TCP_STATE_LISTEN == pTcpTable->table[i].dwState && (u_short)port == ntohs((u_short)pTcpTable->table[i].dwLocalPort)) { SET_UI64_RESULT(result, 1); break; } } ret = SYSINFO_RET_OK; } else { zabbix_log(LOG_LEVEL_DEBUG, "GetTcpTable failed with error: %s", strerror_from_system(dwRetVal)); goto clean; } if (!ISSET_UI64(result)) SET_UI64_RESULT(result, 0); clean: zbx_free(pTcpTable); return ret; }
static zbx_uint64_t *get_result_ui64_value(AGENT_RESULT *result) { zbx_uint64_t value; assert(result); if (0 != ISSET_UI64(result)) { /* nothing to do */ } else if (0 != ISSET_DBL(result)) { SET_UI64_RESULT(result, result->dbl); } else if (0 != ISSET_STR(result)) { zbx_rtrim(result->str, " \""); zbx_ltrim(result->str, " \"+"); del_zeroes(result->str); if (SUCCEED != is_uint64(result->str, &value)) return NULL; SET_UI64_RESULT(result, value); } else if (0 != ISSET_TEXT(result)) { zbx_rtrim(result->text, " \""); zbx_ltrim(result->text, " \"+"); del_zeroes(result->text); if (SUCCEED != is_uint64(result->text, &value)) return NULL; SET_UI64_RESULT(result, value); } /* skip AR_MESSAGE - it is information field */ if (0 != ISSET_UI64(result)) return &result->ui64; return NULL; }
static int hv_get_stat(zbx_vmware_hv_t *hv, int opt, const char *xpath, AGENT_RESULT *result) { char *value; zbx_uint64_t value_uint64, value_uint64_sum; int i; switch (opt) { case ZBX_OPT_XPATH: if (NULL == (value = zbx_xml_read_value(hv->details, xpath))) return SYSINFO_RET_FAIL; SET_STR_RESULT(result, value); break; case ZBX_OPT_VM_NUM: SET_UI64_RESULT(result, hv->vms.values_num); break; case ZBX_OPT_MEM_BALLOONED: xpath = ZBX_XPATH_LN2("quickStats", "balloonedMemory"); value_uint64_sum = 0; for (i = 0; i < hv->vms.values_num; i++) { zbx_vmware_vm_t *vm = (zbx_vmware_vm_t *)hv->vms.values[i]; if (NULL == (value = zbx_xml_read_value(vm->details, xpath))) continue; if (SUCCEED == is_uint64(value, &value_uint64)) value_uint64_sum += value_uint64; zbx_free(value); } SET_UI64_RESULT(result, value_uint64_sum); break; } return SYSINFO_RET_OK; }
static int vmware_counter_get(const char *stats, const char *instance, zbx_uint64_t counterid, int coeff, AGENT_RESULT *result) { int ret = SYSINFO_RET_FAIL; char xpath[MAX_STRING_LEN], *value; zbx_uint64_t value_ui64; zbx_snprintf(xpath, sizeof(xpath), ZBX_XPATH_LN3("value", "id", "counterId") "[.='" ZBX_FS_UI64 "']/.." ZBX_XPATH_LN("instance") "[.='%s']/../.." ZBX_XPATH_LN("value"), counterid, instance); if (NULL == (value = zbx_xml_read_value(stats, xpath))) return SYSINFO_RET_FAIL; if (SUCCEED == is_uint64(value, &value_ui64)) { SET_UI64_RESULT(result, value_ui64 * coeff); ret = SYSINFO_RET_OK; } zbx_free(value); return ret; }
void zbx_mock_test_entry(void **state) { AGENT_REQUEST request; AGENT_RESULT param_result; zbx_mock_error_t error; const char *init_param; zbx_mock_handle_t param_handle; const char *expected_param_value_string, *expected_return_string; zbx_uint64_t expected_param_value = 0; int expected_result = FAIL, actual_result = FAIL; ZBX_UNUSED(state); if (ZBX_MOCK_SUCCESS != (error = zbx_mock_out_parameter("return", ¶m_handle)) || ZBX_MOCK_SUCCESS != (error = zbx_mock_string(param_handle,&expected_return_string))) { fail_msg("Cannot get expected 'return' parameter from test case data: %s", zbx_mock_error_string(error)); } else { if (0 == strcmp("SYSINFO_RET_OK", expected_return_string)) expected_result = SYSINFO_RET_OK; else if (0 == strcmp("SYSINFO_RET_FAIL", expected_return_string)) expected_result = SYSINFO_RET_FAIL; else fail_msg("Get unexpected 'return' parameter from test case data: %s", expected_return_string); } if (ZBX_MOCK_SUCCESS != (error = zbx_mock_in_parameter("param", ¶m_handle)) || ZBX_MOCK_SUCCESS != (error = zbx_mock_string(param_handle, &init_param))) { fail_msg("Cannot get input 'param' from test case data: %s", zbx_mock_error_string(error)); } if (ZBX_MOCK_SUCCESS != (error = zbx_mock_out_parameter("result", ¶m_handle)) || ZBX_MOCK_SUCCESS != (error = zbx_mock_string(param_handle, &expected_param_value_string))) { fail_msg("Cannot get expected 'result' parameters from test case data: %s", zbx_mock_error_string(error)); } else { if (FAIL == is_uint64(expected_param_value_string, &expected_param_value) && SYSINFO_RET_OK == expected_result) { fail_msg("Cannot get expected numeric parameter from test case data: %s", expected_param_value_string); } } init_request(&request); init_result(¶m_result); if (SUCCEED != parse_item_key(init_param, &request)) fail_msg("Cannot parse item key: %s", init_param); if (expected_result != (actual_result = NET_IF_IN(&request,¶m_result))) { fail_msg("Got %s instead of %s as a result.", zbx_sysinfo_ret_string(actual_result), zbx_sysinfo_ret_string(expected_result)); } if (SYSINFO_RET_OK == expected_result) { if (NULL == GET_UI64_RESULT(¶m_result) || expected_param_value != *GET_UI64_RESULT(¶m_result)) { if (NULL != GET_UI64_RESULT(¶m_result)) { fail_msg("Got '" ZBX_FS_UI64 "' instead of '%s' as a value.", *GET_UI64_RESULT(¶m_result), expected_param_value_string); } else fail_msg("Got 'NULL' instead of '%s' as a value.", expected_param_value_string); } } else /* SYSINFO_RET_FAIL == expected_result */ { if (NULL == GET_MSG_RESULT(¶m_result) || 0 != strcmp(expected_param_value_string, *GET_MSG_RESULT(¶m_result))) { fail_msg("Got '%s' instead of '%s' as a value.", (NULL != GET_MSG_RESULT(¶m_result) ? *GET_MSG_RESULT(¶m_result) : "NULL"), expected_param_value_string); } } free_request(&request); free_result(¶m_result); }
int check_vcenter_vm_vfs_fs_size(AGENT_REQUEST *request, const char *username, const char *password, AGENT_RESULT *result) { zbx_vmware_service_t *service; zbx_vmware_vm_t *vm; char *url, *uuid, *fsname, *mode, *value = NULL, xpath[MAX_STRING_LEN]; zbx_uint64_t value_total, value_free; int ret = SYSINFO_RET_FAIL; if (3 > request->nparam || request->nparam > 4) return SYSINFO_RET_FAIL; url = get_rparam(request, 0); uuid = get_rparam(request, 1); fsname = get_rparam(request, 2); mode = get_rparam(request, 3); if ('\0' == *uuid) return SYSINFO_RET_FAIL; zbx_vmware_lock(); if (NULL == (service = get_vmware_service(url, username, password, result, &ret))) goto unlock; if (NULL == (vm = service_vm_get(service, uuid))) goto unlock; zbx_snprintf(xpath, sizeof(xpath), ZBX_XPATH_LN2("disk", "diskPath") "[.='%s']/.." ZBX_XPATH_LN("capacity"), fsname); if (NULL == (value = zbx_xml_read_value(vm->details, xpath))) goto unlock; if (SUCCEED != is_uint64(value, &value_total)) goto unlock; zbx_free(value); zbx_snprintf(xpath, sizeof(xpath), ZBX_XPATH_LN2("disk", "diskPath") "[.='%s']/.." ZBX_XPATH_LN("freeSpace"), fsname); if (NULL == (value = zbx_xml_read_value(vm->details, xpath))) goto unlock; if (SUCCEED != is_uint64(value, &value_free)) goto unlock; ret = SYSINFO_RET_OK; if (NULL == mode || '\0' == *mode || 0 == strcmp(mode, "total")) SET_UI64_RESULT(result, value_total); else if (0 == strcmp(mode, "free")) SET_UI64_RESULT(result, value_free); else if (0 == strcmp(mode, "used")) SET_UI64_RESULT(result, value_total - value_free); else if (0 == strcmp(mode, "pfree")) SET_DBL_RESULT(result, (0 != value_total ? (double)(100.0 * value_free) / value_total : 0)); else if (0 == strcmp(mode, "pused")) SET_DBL_RESULT(result, 100.0 - (0 != value_total ? (double)(100.0 * value_free) / value_total : 0)); else ret = SYSINFO_RET_FAIL; unlock: zbx_free(value); zbx_vmware_unlock(); return ret; }
int vmware_get_events(const char *events, zbx_uint64_t lastlogsize, AGENT_RESULT *result) { zbx_vector_str_t keys; zbx_uint64_t key; char *value, xpath[MAX_STRING_LEN]; int i; zbx_log_t *log; struct tm tm; time_t t; zbx_vector_str_create(&keys); if (SUCCEED != zbx_xml_read_values(events, ZBX_XPATH_LN2("Event", "key"), &keys)) { zbx_vector_str_destroy(&keys); return SYSINFO_RET_FAIL; } for (i = keys.values_num - 1; i >= 0; i--) { if (SUCCEED != is_uint64(keys.values[i], &key)) continue; if (key <= lastlogsize) continue; /* value */ zbx_snprintf(xpath, sizeof(xpath), ZBX_XPATH_LN2("Event", "key") "[.='" ZBX_FS_UI64 "']/.." ZBX_XPATH_LN("fullFormattedMessage"), key); if (NULL == (value = zbx_xml_read_value(events, xpath))) continue; zbx_replace_invalid_utf8(value); log = add_log_result(result, value); log->logeventid = key; log->lastlogsize = key; zbx_free(value); /* timestamp */ zbx_snprintf(xpath, sizeof(xpath), ZBX_XPATH_LN2("Event", "key") "[.='" ZBX_FS_UI64 "']/.." ZBX_XPATH_LN("createdTime"), key); if (NULL == (value = zbx_xml_read_value(events, xpath))) continue; /* 2013-06-04T14:19:23.406298Z */ if (6 == sscanf(value, "%d-%d-%dT%d:%d:%d.%*s", &tm.tm_year, &tm.tm_mon, &tm.tm_mday, &tm.tm_hour, &tm.tm_min, &tm.tm_sec)) { int tz_offset; #if defined(HAVE_TM_TM_GMTOFF) struct tm *ptm; time_t now; now = time(NULL); ptm = localtime(&now); tz_offset = ptm->tm_gmtoff; #else tz_offset = -timezone; #endif tm.tm_year -= 1900; tm.tm_mon--; tm.tm_isdst = -1; if (0 < (t = mktime(&tm))) log->timestamp = (int)t + tz_offset; } zbx_free(value); } if (!ISSET_LOG(result)) set_log_result_empty(result); zbx_vector_str_clean(&keys); zbx_vector_str_destroy(&keys); return SYSINFO_RET_OK; }
/****************************************************************************** * * * Function: node_process_command * * * * Purpose: process command received from a master node or php * * * * Return value: SUCCEED - processed successfully * * FAIL - an error occurred * * * ******************************************************************************/ int node_process_command(zbx_sock_t *sock, const char *data, struct zbx_json_parse *jp) { char *result = NULL, *send = NULL, tmp[64]; int nodeid = -1, next_nodeid, ret = FAIL; zbx_uint64_t scriptid, hostid; struct zbx_json j; zabbix_log(LOG_LEVEL_DEBUG, "In node_process_command()"); zbx_json_init(&j, ZBX_JSON_STAT_BUF_LEN); if (SUCCEED != zbx_json_value_by_name(jp, ZBX_PROTO_TAG_NODEID, tmp, sizeof(tmp)) || FAIL == is_uint31(tmp, &nodeid)) { result = zbx_dsprintf(result, "Failed to parse command request tag: %s.", ZBX_PROTO_TAG_NODEID); goto finish; } if (SUCCEED != zbx_json_value_by_name(jp, ZBX_PROTO_TAG_SCRIPTID, tmp, sizeof(tmp)) || FAIL == is_uint64(tmp, &scriptid)) { result = zbx_dsprintf(result, "Failed to parse command request tag: %s.", ZBX_PROTO_TAG_SCRIPTID); goto finish; } if (SUCCEED != zbx_json_value_by_name(jp, ZBX_PROTO_TAG_HOSTID, tmp, sizeof(tmp)) || FAIL == is_uint64(tmp, &hostid)) { result = zbx_dsprintf(result, "Failed to parse command request tag: %s.", ZBX_PROTO_TAG_HOSTID); goto finish; } if (nodeid == CONFIG_NODEID) { if (SUCCEED == (ret = execute_script(scriptid, hostid, &result))) { zbx_json_addstring(&j, ZBX_PROTO_TAG_RESPONSE, ZBX_PROTO_VALUE_SUCCESS, ZBX_JSON_TYPE_STRING); zbx_json_addstring(&j, ZBX_PROTO_TAG_DATA, result, ZBX_JSON_TYPE_STRING); send = j.buffer; } } else if (SUCCEED == get_next_point_to_node(CONFIG_NODEID, nodeid, &next_nodeid)) { zabbix_log(LOG_LEVEL_WARNING, "NODE %d: Sending command for Node %d to Node %d", CONFIG_NODEID, nodeid, next_nodeid); if (SUCCEED == (ret = send_script(next_nodeid, data, &result))) send = result; } else result = zbx_dsprintf(result, "NODE %d: Unknown Node ID [%d].", CONFIG_NODEID, nodeid); finish: if (FAIL == ret) { zbx_json_addstring(&j, ZBX_PROTO_TAG_RESPONSE, ZBX_PROTO_VALUE_FAILED, ZBX_JSON_TYPE_STRING); zbx_json_addstring(&j, ZBX_PROTO_TAG_INFO, (NULL != result ? result : "Unknown error."), ZBX_JSON_TYPE_STRING); send = j.buffer; } alarm(CONFIG_TIMEOUT); if (SUCCEED != zbx_tcp_send_raw(sock, send)) { zabbix_log(LOG_LEVEL_WARNING, "NODE %d: Error sending result of command to node %d", CONFIG_NODEID, nodeid); } else { zabbix_log(LOG_LEVEL_DEBUG, "NODE %d: Sending back command '%s' result '%s'", CONFIG_NODEID, data, send); } alarm(0); zbx_json_free(&j); zbx_free(result); return ret; }
// WARNING: 1.only works for positive number without pre or post spaces // 2.limit not checked, string can exceed the int size // TODO: make it more universal bool UInt64Parser::validate(std::string data_str){ return is_uint64(data_str); }
int set_result_type(AGENT_RESULT *result, int value_type, int data_type, char *c) { int ret = FAIL; zbx_uint64_t value_uint64; double value_double; assert(result); switch (value_type) { case ITEM_VALUE_TYPE_UINT64: zbx_rtrim(c, " \""); zbx_ltrim(c, " \"+"); del_zeroes(c); switch (data_type) { case ITEM_DATA_TYPE_BOOLEAN: if (SUCCEED == is_boolean(c, &value_uint64)) { SET_UI64_RESULT(result, value_uint64); ret = SUCCEED; } break; case ITEM_DATA_TYPE_OCTAL: if (SUCCEED == is_uoct(c)) { ZBX_OCT2UINT64(value_uint64, c); SET_UI64_RESULT(result, value_uint64); ret = SUCCEED; } break; case ITEM_DATA_TYPE_DECIMAL: if (SUCCEED == is_uint64(c, &value_uint64)) { SET_UI64_RESULT(result, value_uint64); ret = SUCCEED; } break; case ITEM_DATA_TYPE_HEXADECIMAL: if (SUCCEED == is_uhex(c)) { ZBX_HEX2UINT64(value_uint64, c); SET_UI64_RESULT(result, value_uint64); ret = SUCCEED; } else if (SUCCEED == is_hex_string(c)) { zbx_remove_whitespace(c); ZBX_HEX2UINT64(value_uint64, c); SET_UI64_RESULT(result, value_uint64); ret = SUCCEED; } break; default: THIS_SHOULD_NEVER_HAPPEN; break; } break; case ITEM_VALUE_TYPE_FLOAT: zbx_rtrim(c, " \""); zbx_ltrim(c, " \"+"); if (SUCCEED != is_double(c)) break; value_double = atof(c); SET_DBL_RESULT(result, value_double); ret = SUCCEED; break; case ITEM_VALUE_TYPE_STR: zbx_replace_invalid_utf8(c); SET_STR_RESULT(result, zbx_strdup(NULL, c)); ret = SUCCEED; break; case ITEM_VALUE_TYPE_TEXT: zbx_replace_invalid_utf8(c); SET_TEXT_RESULT(result, zbx_strdup(NULL, c)); ret = SUCCEED; break; case ITEM_VALUE_TYPE_LOG: zbx_replace_invalid_utf8(c); add_log_result(result, c); ret = SUCCEED; break; } if (SUCCEED != ret) { char *error = NULL; zbx_remove_chars(c, "\r\n"); zbx_replace_invalid_utf8(c); if (ITEM_VALUE_TYPE_UINT64 == value_type) error = zbx_dsprintf(error, "Received value [%s] is not suitable for value type [%s] and data type [%s]", c, zbx_item_value_type_string(value_type), zbx_item_data_type_string(data_type)); else error = zbx_dsprintf(error, "Received value [%s] is not suitable for value type [%s]", c, zbx_item_value_type_string(value_type)); SET_MSG_RESULT(result, error); } return ret; }
static int vm_create(int argc, char* argv[]) { // Default value VMSpec vm = {}; vm.core_size = 1; vm.memory_size = 0x1000000; // 16MB vm.storage_size = 0x1000000; // 16MB // Main options static struct option options[] = { { "core", required_argument, 0, 'c' }, { "memory", required_argument, 0, 'm' }, { "storage", required_argument, 0, 's' }, { "nic", optional_argument, 0, 'n' }, { "args", required_argument, 0, 'a' }, { 0, 0, 0, 0 } }; int opt; int index = 0; while((opt = getopt_long(argc, argv, "c:m:s:n::a:", options, &index)) != -1) { switch(opt) { case 'c' : if(!is_uint32(optarg)) goto failure; vm.core_size = strtol(optarg, NULL, 0); break; case 'm' : if(!is_uint32(optarg)) goto failure; vm.memory_size = strtol(optarg, NULL, 16); break; case 's' : if(!is_uint32(optarg)) goto failure; vm.storage_size = strtol(optarg, NULL, 16); break; case 'n' :; // Suboptions for NIC enum { EMPTY, MAC, DEV, IBUF, OBUF, IBAND, OBAND, HPAD, TPAD, POOL, INHERITMAC, NOARP, PROMISC, BROADCAST, MULTICAST, MULTIQUEUE, }; const char* token[] = { [EMPTY] = "", [MAC] = "mac", [DEV] = "dev", [IBUF] = "ibuf", [OBUF] = "obuf", [IBAND] = "iband", [OBAND] = "oband", [HPAD] = "hpad", [TPAD] = "tpad", [POOL] = "pool", [INHERITMAC] = "inheritmac", [NOARP] = "noarp", [PROMISC] = "promisc", [BROADCAST] = "broadcast", [MULTICAST] = "multicast", [MULTIQUEUE] = "multiqueue", NULL, }; // Default NIC configuration NICSpec* nic = &vm.nics[vm.nic_count++]; nic->mac = 0; nic->parent[0] = '\0'; nic->budget = NICSPEC_DEFAULT_BUDGET_SIZE; nic->flags = NICSPEC_DEFAULT_FLAGS; nic->rx_buffer_size = 1024; nic->tx_buffer_size = 1024; nic->rx_bandwidth = 1000000000; /* 1 GB */ nic->tx_bandwidth = 1000000000; /* 1 GB */ nic->padding_head = 32; nic->padding_tail = 32; nic->pool_size = 0x400000; /* 4 MB */ char* subopts = optarg; while(optarg && *subopts != '\0') { char* value = NULL; int subopt_index = getsubopt(&subopts, (char* const*)token, &value); if(subopt_index == -1) goto failure; switch(subopt_index) { case EMPTY: break; case MAC: if(!is_uint64(value)) goto failure; nic->mac = strtoll(value, NULL, 16); break; case DEV: strncpy(nic->parent, value, MAX_NIC_NAME_LEN); break; case IBUF: if(!is_uint32(value)) goto failure; nic->rx_buffer_size = strtoul(value, NULL, 0); break; case OBUF: if(!is_uint32(value)) goto failure; nic->tx_buffer_size = strtoul(value, NULL, 0); break; case IBAND: if(!is_uint64(value)) goto failure; nic->rx_bandwidth = strtoull(value, NULL, 0); break; case OBAND: if(!is_uint64(value)) goto failure; nic->tx_bandwidth = strtoull(value, NULL, 0); break; case HPAD: if(!is_uint8(value)) goto failure; nic->padding_head = strtoul(value, NULL, 0); break; case TPAD: if(!is_uint8(value)) goto failure; nic->padding_tail = strtoul(value, NULL, 0); break; case POOL: if(!is_uint32(value)) goto failure; nic->pool_size = strtoul(value, NULL, 16); break; case INHERITMAC: if(!strcmp("on", value)) { nic->flags |= NICSPEC_F_INHERITMAC; } else if(!strcmp("off", value)) { nic->flags |= NICSPEC_F_INHERITMAC; nic->flags ^= NICSPEC_F_INHERITMAC; } else goto failure; break; case NOARP: if(!strcmp("on", value)) { nic->flags |= NICSPEC_F_NOARP; } else if(!strcmp("off", value)) { nic->flags |= NICSPEC_F_NOARP; nic->flags ^= NICSPEC_F_NOARP; } else goto failure; break; case PROMISC: if(!strcmp("on", value)) { nic->flags |= NICSPEC_F_PROMISC; } else if(!strcmp("off", value)) { nic->flags |= NICSPEC_F_PROMISC; nic->flags ^= NICSPEC_F_PROMISC; } else goto failure; break; case BROADCAST: if(!strcmp("on", value)) { nic->flags |= NICSPEC_F_BROADCAST; } else if(!strcmp("off", value)) { nic->flags |= NICSPEC_F_BROADCAST; nic->flags ^= NICSPEC_F_BROADCAST; } else goto failure; break; case MULTICAST: if(!strcmp("on", value)) { nic->flags |= NICSPEC_F_MULTICAST; } else if(!strcmp("off", value)) { nic->flags |= NICSPEC_F_MULTICAST; nic->flags ^= NICSPEC_F_MULTICAST; } else goto failure; break; case MULTIQUEUE: if(!strcmp("on", value)) { nic->flags |= NICSPEC_F_MULTIQUEUE; } else if(!strcmp("off", value)) { nic->flags |= NICSPEC_F_MULTIQUEUE; nic->flags ^= NICSPEC_F_MULTIQUEUE; } else goto failure; break; default: goto failure; break; } } break; case 'a' : vm.argv[vm.argc++] = strdup(optarg); if(errno == ENOMEM) goto failure; break; default: goto failure; } } rpc_vm_create(rpc, &vm, callback_vm_create, NULL); return 0; failure: printf("Malformed input were given\n"); help(); exit(EXIT_FAILURE); }
void zbx_mock_test_entry(void **state) { zbx_mock_error_t error; zbx_mock_handle_t handle, parameters, parameter; const char *cfg_file, *validation, *tmp, **multi_string, *string_list; int strict = 42, exit_code, parameter_count = 0, i; struct cfg_line *cfg = NULL; void **expected_values = NULL; ZBX_UNUSED(state); if (ZBX_MOCK_SUCCESS != (error = zbx_mock_in_parameter("configuration file", &handle)) || ZBX_MOCK_SUCCESS != (error = zbx_mock_string(handle, &cfg_file))) { fail_msg("Cannot get configuration file from test case data: %s", zbx_mock_error_string(error)); } if (ZBX_MOCK_SUCCESS != (error = zbx_mock_in_parameter("validation", &handle)) || ZBX_MOCK_SUCCESS != (error = zbx_mock_string(handle, &validation))) { fail_msg("Cannot get validation mode from test case data: %s", zbx_mock_error_string(error)); } if (0 == strcmp(validation, "not strict")) strict = ZBX_CFG_NOT_STRICT; else if (0 == strcmp(validation, "strict")) strict = ZBX_CFG_STRICT; else fail_msg("Invalid validation mode \"%s\".", validation); if (ZBX_MOCK_SUCCESS != (error = zbx_mock_in_parameter("parameters", ¶meters))) fail_msg("Cannot get description of parameters from test case data: %s", zbx_mock_error_string(error)); while (ZBX_MOCK_SUCCESS == (error = zbx_mock_vector_element(parameters, ¶meter))) { cfg = zbx_realloc(cfg, (parameter_count + 1) * sizeof(struct cfg_line)); expected_values = zbx_realloc(expected_values, (parameter_count + 1) * sizeof(void *)); if (ZBX_MOCK_SUCCESS != (error = zbx_mock_object_member(parameter, "name", &handle)) || ZBX_MOCK_SUCCESS != (error = zbx_mock_string(handle, &tmp))) { fail_msg("Cannot get name of parameter #%d: %s", parameter_count + 1, zbx_mock_error_string(error)); } cfg[parameter_count].parameter = tmp; if (ZBX_MOCK_SUCCESS != (error = zbx_mock_object_member(parameter, "type", &handle)) || ZBX_MOCK_SUCCESS != (error = zbx_mock_string(handle, &tmp))) { fail_msg("Cannot get type of parameter #%d: %s", parameter_count + 1, zbx_mock_error_string(error)); } if (0 == strcmp(tmp, "numeric")) { if (ZBX_MOCK_NO_SUCH_MEMBER == (error = zbx_mock_object_member(parameter, "expect", &handle))) { expected_values[parameter_count] = NULL; } else if (ZBX_MOCK_SUCCESS == error && ZBX_MOCK_SUCCESS == (error = zbx_mock_string(handle, &tmp))) { expected_values[parameter_count] = zbx_malloc(NULL, sizeof(zbx_uint64_t)); if (SUCCEED != is_uint64(tmp, expected_values[parameter_count])) { fail_msg("Expected value \"%s\" of parameter #%d is not numeric.", tmp, parameter_count + 1); } } else break; cfg[parameter_count].variable = zbx_malloc(NULL, sizeof(zbx_uint64_t)); *(zbx_uint64_t *)cfg[parameter_count].variable = (zbx_uint64_t)-1; if (ZBX_MOCK_NO_SUCH_MEMBER == (error = zbx_mock_object_member(parameter, "min", &handle))) { cfg[parameter_count].min = 0; } else if (ZBX_MOCK_SUCCESS == error && ZBX_MOCK_SUCCESS == (error = zbx_mock_string(handle, &tmp))) { zbx_uint64_t min; if (SUCCEED != is_uint64(tmp, &min)) { fail_msg("Minimum allowed value \"%s\" of parameter #%d is not numeric.", tmp, parameter_count + 1); } cfg[parameter_count].min = min; } else break; if (ZBX_MOCK_NO_SUCH_MEMBER == (error = zbx_mock_object_member(parameter, "max", &handle))) { cfg[parameter_count].max = 0; } else if (ZBX_MOCK_SUCCESS == error && ZBX_MOCK_SUCCESS == (error = zbx_mock_string(handle, &tmp))) { zbx_uint64_t max; if (SUCCEED != is_uint64(tmp, &max)) { fail_msg("Maximum allowed value \"%s\" of parameter #%d is not numeric.", tmp, parameter_count + 1); } cfg[parameter_count].max = max; } else break; cfg[parameter_count].type = TYPE_UINT64; /* no separate treatment for TYPE_INT */ } else if (0 == strcmp(tmp, "string")) { if (ZBX_MOCK_NO_SUCH_MEMBER == (error = zbx_mock_object_member(parameter, "expect", &handle))) { expected_values[parameter_count] = NULL; } else if (ZBX_MOCK_SUCCESS == error && ZBX_MOCK_SUCCESS == (error = zbx_mock_string(handle, &tmp))) { expected_values[parameter_count] = zbx_malloc(NULL, sizeof(char *)); *(const char **)expected_values[parameter_count] = tmp; } else break; cfg[parameter_count].variable = zbx_malloc(NULL, sizeof(char *)); *(char **)cfg[parameter_count].variable = NULL; cfg[parameter_count].min = 0; cfg[parameter_count].max = 0; cfg[parameter_count].type = TYPE_STRING; } else if (0 == strcmp(tmp, "string list")) { expected_values[parameter_count] = zbx_malloc(NULL, sizeof(zbx_mock_handle_t)); if (ZBX_MOCK_NO_SUCH_MEMBER == (error = zbx_mock_object_member(parameter, "expect", expected_values[parameter_count]))) { fail_msg("Missing expected field for parameter #%d of string list type, use [] instead.", parameter_count + 1); } if (ZBX_MOCK_SUCCESS != error) break; cfg[parameter_count].variable = zbx_malloc(NULL, sizeof(char *)); *(char **)cfg[parameter_count].variable = NULL; cfg[parameter_count].min = 0; cfg[parameter_count].max = 0; cfg[parameter_count].type = TYPE_STRING_LIST; } else if (0 == strcmp(tmp, "multi string")) { expected_values[parameter_count] = zbx_malloc(NULL, sizeof(zbx_mock_handle_t)); if (ZBX_MOCK_NO_SUCH_MEMBER == (error = zbx_mock_object_member(parameter, "expect", expected_values[parameter_count]))) { fail_msg("Missing expected field for parameter #%d of multi string type, use [] instead.", parameter_count + 1); } if (ZBX_MOCK_SUCCESS != error) break; cfg[parameter_count].variable = zbx_malloc(NULL, sizeof(char **)); *(char ***)cfg[parameter_count].variable = NULL; zbx_strarr_init((char ***)cfg[parameter_count].variable); cfg[parameter_count].min = 0; cfg[parameter_count].max = 0; cfg[parameter_count].type = TYPE_MULTISTRING; } else fail_msg("Invalid type \"%s\" of parameter #%d.", tmp, parameter_count + 1); if (ZBX_MOCK_SUCCESS != (error = zbx_mock_object_member(parameter, "mandatory", &handle)) || ZBX_MOCK_SUCCESS != (error = zbx_mock_string(handle, &tmp))) { fail_msg("Cannot get mandatory flag of parameter #%d: %s", parameter_count + 1, zbx_mock_error_string(error)); } if (0 == strcmp(tmp, "yes")) cfg[parameter_count].mandatory = PARM_MAND; else if (0 == strcmp(tmp, "no")) cfg[parameter_count].mandatory = PARM_OPT; else fail_msg("Invalid mandatory flag \"%s\" of parameter #%d.", tmp, parameter_count + 1); parameter_count++; } if (ZBX_MOCK_END_OF_VECTOR != error) { fail_msg("Cannot get description of parameter #%d from test case data: %s", parameter_count + 1, zbx_mock_error_string(error)); } cfg = zbx_realloc(cfg, (parameter_count + 1) * sizeof(struct cfg_line)); cfg[parameter_count].parameter = NULL; parse_cfg_file(cfg_file, cfg, ZBX_CFG_FILE_REQUIRED, strict); if (ZBX_MOCK_NO_EXIT_CODE != (error = zbx_mock_exit_code(&exit_code))) { if (ZBX_MOCK_SUCCESS == error) fail_msg("parse_cfg_file() was expected to call exit(%d), but has not.", exit_code); else fail_msg("Cannot get exit code from test case data: %s", zbx_mock_error_string(error)); } for (i = 0; i < parameter_count; i++) { switch (cfg[i].type) { case TYPE_MULTISTRING: multi_string = *(const char ***)cfg[i].variable; while (ZBX_MOCK_SUCCESS == (error = zbx_mock_vector_element( *(zbx_mock_handle_t *)expected_values[i], &handle)) && ZBX_MOCK_SUCCESS == (error = zbx_mock_string(handle, &tmp))) { if (NULL == *multi_string) { fail_msg("Values of multi string parameter \"%s\" ended while \"%s\"" " was expected.", cfg[i].parameter, tmp); } if (0 != strcmp(*multi_string, tmp)) { fail_msg("Value \"%s\" of multi string parameter \"%s\"" " differs from expected \"%s\".", *multi_string, cfg[i].parameter, tmp); } multi_string++; } if (ZBX_MOCK_END_OF_VECTOR != error) { fail_msg("Cannot get expected values of multi string parameter \"%s\": %s", cfg[i].parameter, zbx_mock_error_string(error)); } if (NULL != *multi_string) { fail_msg("Value of multi string parameter \"%s\" ends with unexpected \"%s\"" " (and maybe more).", cfg[i].parameter, *multi_string); } break; case TYPE_STRING_LIST: string_list = *(const char **)cfg[i].variable; while (ZBX_MOCK_SUCCESS == (error = zbx_mock_vector_element( *(zbx_mock_handle_t *)expected_values[i], &handle)) && ZBX_MOCK_SUCCESS == (error = zbx_mock_string(handle, &tmp))) { if ('\0' == *string_list) { fail_msg("Value of string list parameter \"%s\" ended when \"%s{,...}\"" " was expected.", cfg[i].parameter, tmp); } if (0 != strncmp(string_list, tmp, strlen(tmp))) { fail_msg("Value of string list parameter \"%s\" starting with \"%s\"" " differs from expected \"%s{,...}\".", cfg[i].parameter, string_list, tmp); } string_list += strlen(tmp); if (',' != *string_list) { if ('\0' != *string_list) { fail_msg("Value of string list parameter \"%s\" starting with" " \"%s\" differs from expected.", cfg[i].parameter, string_list); } } else string_list++; } if (ZBX_MOCK_END_OF_VECTOR != error) { fail_msg("Cannot get expected value of string list parameter \"%s\": %s", cfg[i].parameter, zbx_mock_error_string(error)); } if ('\0' != *string_list) { fail_msg("Values of string list parameter \"%s\" ends with unexpected \"%s\".", cfg[i].parameter, string_list); } break; case TYPE_STRING: if (NULL == *(char **)cfg[i].variable && NULL != *(char **)expected_values[i]) { fail_msg("No value of string parameter \"%s\" while expected \"%s\".", cfg[i].parameter, *(char **)expected_values[i]); } else if (NULL != *(char **)cfg[i].variable && NULL == *(char **)expected_values[i]) { fail_msg("Got value \"%s\" of string parameter \"%s\" none was expected.", *(char **)cfg[i].variable, cfg[i].parameter); } else if (NULL != *(char **)cfg[i].variable && NULL != *(char **)expected_values[i] && 0 != strcmp(*(char **)cfg[i].variable, *(char **)expected_values[i])) { fail_msg("Value \"%s\" of string parameter \"%s\" differs from expected \"%s\".", *(char **)cfg[i].variable, cfg[i].parameter, *(char **)expected_values[i]); } break; case TYPE_UINT64: if (*(zbx_uint64_t *)cfg[i].variable != *(zbx_uint64_t *)expected_values[i]) { fail_msg("Value " ZBX_FS_UI64 " of numeric parameter \"%s\"" " differs from expected (" ZBX_FS_UI64 ").", *(zbx_uint64_t *)cfg[i].variable, cfg[i].parameter, *(zbx_uint64_t *)expected_values[i]); } break; default: fail_msg("Invalid type of parameter \"%s\" when doing validation.", cfg[i].parameter); } } for (i = 0; i < parameter_count; i++) { switch (cfg[i].type) { case TYPE_MULTISTRING: zbx_strarr_free(*(char ***)cfg[i].variable); zbx_free(cfg[i].variable); zbx_free(expected_values[i]); break; case TYPE_STRING_LIST: case TYPE_STRING: zbx_free(*(char **)cfg[i].variable); zbx_free(cfg[i].variable); zbx_free(expected_values[i]); break; case TYPE_UINT64: zbx_free(cfg[i].variable); zbx_free(expected_values[i]); break; default: fail_msg("Invalid type of parameter \"%s\" when doing cleanup.", cfg[i].parameter); } } zbx_free(expected_values); zbx_free(cfg); }
/****************************************************************************** * * * Function: byte_value_from_proc_file * * * * Purpose: Read amount of memory in bytes from a string in /proc file. * * For example, reading "VmSize: 176712 kB" from /proc/1/status * * will produce a result 176712*1024 = 180953088 bytes * * * * Parameters: * * f - [IN] file to read from * * label - [IN] label to look for, e.g. "VmData:\t" * * guard - [IN] label before which to stop, e.g. "VmStk:\t" (optional) * * bytes - [OUT] result in bytes * * * * Return value: SUCCEED - successful reading, * * NOTSUPPORTED - the search string was not found. For example, * * /proc/NNN/status files for kernel threads do * * not contain "VmSize:" string. * * FAIL - the search string was found but could not be parsed. * * * ******************************************************************************/ int byte_value_from_proc_file(FILE *f, const char *label, const char *guard, zbx_uint64_t *bytes) { char buf[MAX_STRING_LEN], *p_value, *p_unit; size_t label_len, guard_len; long pos = 0; int ret = NOTSUPPORTED; label_len = strlen(label); p_value = buf + label_len; if (NULL != guard) { guard_len = strlen(guard); pos = ftell(f); } while (NULL != fgets(buf, (int)sizeof(buf), f)) { if (NULL != guard) { if (0 == strncmp(buf, guard, guard_len)) { fseek(f, pos, SEEK_SET); break; } pos = ftell(f); } if (0 != strncmp(buf, label, label_len)) continue; if (NULL == (p_unit = strrchr(p_value, ' '))) { ret = FAIL; break; } *p_unit++ = '\0'; while (' ' == *p_value) p_value++; if (FAIL == is_uint64(p_value, bytes)) { ret = FAIL; break; } zbx_rtrim(p_unit, "\n"); if (0 == strcasecmp(p_unit, "kB")) *bytes <<= 10; else if (0 == strcasecmp(p_unit, "mB")) *bytes <<= 20; else if (0 == strcasecmp(p_unit, "GB")) *bytes <<= 30; else if (0 == strcasecmp(p_unit, "TB")) *bytes <<= 40; ret = SUCCEED; break; } return ret; }
static int process_trap(zbx_socket_t *sock, char *s, zbx_timespec_t *ts) { int ret = SUCCEED; zbx_rtrim(s, " \r\n"); zabbix_log(LOG_LEVEL_DEBUG, "trapper got '%s'", s); if ('{' == *s) /* JSON protocol */ { struct zbx_json_parse jp; char value[MAX_STRING_LEN]; if (SUCCEED != zbx_json_open(s, &jp)) { zbx_send_response(sock, FAIL, zbx_json_strerror(), CONFIG_TIMEOUT); zabbix_log(LOG_LEVEL_WARNING, "received invalid JSON object from %s: %s", sock->peer, zbx_json_strerror()); return FAIL; } if (SUCCEED == zbx_json_value_by_name(&jp, ZBX_PROTO_TAG_REQUEST, value, sizeof(value))) { if (0 == strcmp(value, ZBX_PROTO_VALUE_PROXY_CONFIG)) { if (0 != (program_type & ZBX_PROGRAM_TYPE_SERVER)) { send_proxyconfig(sock, &jp); } else if (0 != (program_type & ZBX_PROGRAM_TYPE_PROXY_PASSIVE)) { zabbix_log(LOG_LEVEL_WARNING, "received configuration data from server" " at \"%s\", datalen " ZBX_FS_SIZE_T, sock->peer, (zbx_fs_size_t)(jp.end - jp.start + 1)); recv_proxyconfig(sock, &jp); } else if (0 != (program_type & ZBX_PROGRAM_TYPE_PROXY_ACTIVE)) { /* This is a misconfiguration: the proxy is configured in active mode */ /* but server sends requests to it as to a proxy in passive mode. To */ /* prevent logging of this problem for every request we report it */ /* only when the server sends configuration to the proxy and ignore */ /* it for other requests. */ active_passive_misconfig(sock); } } else if (0 == strcmp(value, ZBX_PROTO_VALUE_AGENT_DATA) || 0 == strcmp(value, ZBX_PROTO_VALUE_SENDER_DATA)) { recv_agenthistory(sock, &jp, ts); } else if (0 == strcmp(value, ZBX_PROTO_VALUE_HISTORY_DATA)) { if (0 != (program_type & ZBX_PROGRAM_TYPE_SERVER)) recv_proxyhistory(sock, &jp, ts); else if (0 != (program_type & ZBX_PROGRAM_TYPE_PROXY_PASSIVE)) send_proxyhistory(sock, ts); } else if (0 == strcmp(value, ZBX_PROTO_VALUE_DISCOVERY_DATA)) { if (0 != (program_type & ZBX_PROGRAM_TYPE_SERVER)) recv_discovery_data(sock, &jp); else if (0 != (program_type & ZBX_PROGRAM_TYPE_PROXY_PASSIVE)) send_discovery_data(sock); } else if (0 == strcmp(value, ZBX_PROTO_VALUE_AUTO_REGISTRATION_DATA)) { if (0 != (program_type & ZBX_PROGRAM_TYPE_SERVER)) recv_areg_data(sock, &jp); else if (0 != (program_type & ZBX_PROGRAM_TYPE_PROXY_PASSIVE)) send_areg_data(sock); } else if (0 == strcmp(value, ZBX_PROTO_VALUE_PROXY_HEARTBEAT)) { if (0 != (program_type & ZBX_PROGRAM_TYPE_SERVER)) recv_proxy_heartbeat(sock, &jp); } else if (0 == strcmp(value, ZBX_PROTO_VALUE_GET_ACTIVE_CHECKS)) { ret = send_list_of_active_checks_json(sock, &jp); } else if (0 == strcmp(value, ZBX_PROTO_VALUE_HOST_AVAILABILITY)) { if (0 != (program_type & ZBX_PROGRAM_TYPE_SERVER)) recv_host_availability(sock, &jp); else if (0 != (program_type & ZBX_PROGRAM_TYPE_PROXY_PASSIVE)) send_host_availability(sock); } else if (0 == strcmp(value, ZBX_PROTO_VALUE_COMMAND)) { ret = node_process_command(sock, s, &jp); } else if (0 == strcmp(value, ZBX_PROTO_VALUE_GET_QUEUE)) { if (0 != (program_type & ZBX_PROGRAM_TYPE_SERVER)) ret = recv_getqueue(sock, &jp); } else zabbix_log(LOG_LEVEL_WARNING, "unknown request received [%s]", value); } } else if (0 == strncmp(s, "ZBX_GET_ACTIVE_CHECKS", 21)) /* request for list of active checks */ { ret = send_list_of_active_checks(sock, s); } else { char value_dec[MAX_BUFFER_LEN], lastlogsize[ZBX_MAX_UINT64_LEN], timestamp[11], source[HISTORY_LOG_SOURCE_LEN_MAX], severity[11]; AGENT_VALUE av; memset(&av, 0, sizeof(AGENT_VALUE)); if ('<' == *s) /* XML protocol */ { comms_parse_response(s, av.host_name, sizeof(av.host_name), av.key, sizeof(av.key), value_dec, sizeof(value_dec), lastlogsize, sizeof(lastlogsize), timestamp, sizeof(timestamp), source, sizeof(source), severity, sizeof(severity)); av.value = value_dec; if (SUCCEED != is_uint64(lastlogsize, &av.lastlogsize)) av.lastlogsize = 0; av.timestamp = atoi(timestamp); av.source = source; av.severity = atoi(severity); } else { char *pl, *pr; pl = s; if (NULL == (pr = strchr(pl, ':'))) return FAIL; *pr = '\0'; zbx_strlcpy(av.host_name, pl, sizeof(av.host_name)); *pr = ':'; pl = pr + 1; if (NULL == (pr = strchr(pl, ':'))) return FAIL; *pr = '\0'; zbx_strlcpy(av.key, pl, sizeof(av.key)); *pr = ':'; av.value = pr + 1; av.severity = 0; } zbx_timespec(&av.ts); if (0 == strcmp(av.value, ZBX_NOTSUPPORTED)) av.state = ITEM_STATE_NOTSUPPORTED; process_mass_data(sock, 0, &av, 1, NULL); zbx_alarm_on(CONFIG_TIMEOUT); if (SUCCEED != zbx_tcp_send_raw(sock, "OK")) zabbix_log(LOG_LEVEL_WARNING, "Error sending result back"); zbx_alarm_off(); } return ret; }
static int process_trap(zbx_sock_t *sock, char *s, int max_len) { char *pl, *pr, *data, value_dec[MAX_BUFFER_LEN]; char lastlogsize[ZBX_MAX_UINT64_LEN], timestamp[11], source[HISTORY_LOG_SOURCE_LEN_MAX], severity[11]; int sender_nodeid, nodeid; char *answer; int ret = SUCCEED, res; size_t datalen; struct zbx_json_parse jp; char value[MAX_STRING_LEN]; AGENT_VALUE av; memset(&av, 0, sizeof(AGENT_VALUE)); zbx_rtrim(s, " \r\n"); datalen = strlen(s); zabbix_log(LOG_LEVEL_DEBUG, "Trapper got [%s] len " ZBX_FS_SIZE_T, s, (zbx_fs_size_t)datalen); if (0 == strncmp(s, "ZBX_GET_ACTIVE_CHECKS", 21)) /* request for list of active checks */ { ret = send_list_of_active_checks(sock, s); } else if (strncmp(s, "ZBX_GET_HISTORY_LAST_ID", 23) == 0) /* request for last IDs */ { send_history_last_id(sock, s); return ret; } else { if (0 == strncmp(s, "Data", 4)) /* node data exchange */ { node_sync_lock(0); res = node_sync(s, &sender_nodeid, &nodeid); if (FAIL == res) { alarm(CONFIG_TIMEOUT); send_data_to_node(sender_nodeid, sock, "FAIL"); alarm(0); } else { res = calculate_checksums(nodeid, NULL, 0); if (SUCCEED == res && NULL != (data = DMget_config_data(nodeid, ZBX_NODE_SLAVE))) { zabbix_log( LOG_LEVEL_WARNING, "NODE %d: Sending configuration changes" " to slave node %d for node %d datalen " ZBX_FS_SIZE_T, CONFIG_NODEID, sender_nodeid, nodeid, (zbx_fs_size_t)strlen(data)); alarm(CONFIG_TRAPPER_TIMEOUT); res = send_data_to_node(sender_nodeid, sock, data); zbx_free(data); if (SUCCEED == res) res = recv_data_from_node(sender_nodeid, sock, &answer); if (SUCCEED == res && 0 == strcmp(answer, "OK")) res = update_checksums(nodeid, ZBX_NODE_SLAVE, SUCCEED, NULL, 0, NULL); alarm(0); } } node_sync_unlock(0); return ret; } else if (0 == strncmp(s, "History", 7)) /* slave node history */ { const char *reply; reply = (SUCCEED == node_history(s, datalen) ? "OK" : "FAIL"); alarm(CONFIG_TIMEOUT); if (SUCCEED != zbx_tcp_send_raw(sock, reply)) zabbix_log(LOG_LEVEL_WARNING, "Error sending %s to node", reply); alarm(0); return ret; } else if (SUCCEED == zbx_json_open(s, &jp)) /* JSON protocol */ { if (SUCCEED == zbx_json_value_by_name(&jp, ZBX_PROTO_TAG_REQUEST, value, sizeof(value))) { if (0 == strcmp(value, ZBX_PROTO_VALUE_PROXY_CONFIG)) { if (0 != (daemon_type & ZBX_DAEMON_TYPE_SERVER)) send_proxyconfig(sock, &jp); else if (0 != (daemon_type & ZBX_DAEMON_TYPE_PROXY_PASSIVE)) { zabbix_log(LOG_LEVEL_WARNING, "Received configuration data from server." " Datalen " ZBX_FS_SIZE_T, (zbx_fs_size_t)datalen); recv_proxyconfig(sock, &jp); } } else if (0 == strcmp(value, ZBX_PROTO_VALUE_AGENT_DATA) || 0 == strcmp(value, ZBX_PROTO_VALUE_SENDER_DATA)) { recv_agenthistory(sock, &jp); } else if (0 == strcmp(value, ZBX_PROTO_VALUE_HISTORY_DATA)) { if (0 != (daemon_type & ZBX_DAEMON_TYPE_SERVER)) recv_proxyhistory(sock, &jp); else if (0 != (daemon_type & ZBX_DAEMON_TYPE_PROXY_PASSIVE)) send_proxyhistory(sock); } else if (0 == strcmp(value, ZBX_PROTO_VALUE_DISCOVERY_DATA)) { if (0 != (daemon_type & ZBX_DAEMON_TYPE_SERVER)) recv_discovery_data(sock, &jp); else if (0 != (daemon_type & ZBX_DAEMON_TYPE_PROXY_PASSIVE)) send_discovery_data(sock); } else if (0 == strcmp(value, ZBX_PROTO_VALUE_AUTO_REGISTRATION_DATA)) { if (0 != (daemon_type & ZBX_DAEMON_TYPE_SERVER)) recv_areg_data(sock, &jp); else if (0 != (daemon_type & ZBX_DAEMON_TYPE_PROXY_PASSIVE)) send_areg_data(sock); } else if (0 == strcmp(value, ZBX_PROTO_VALUE_PROXY_HEARTBEAT)) { if (0 != (daemon_type & ZBX_DAEMON_TYPE_SERVER)) recv_proxy_heartbeat(sock, &jp); } else if (0 == strcmp(value, ZBX_PROTO_VALUE_GET_ACTIVE_CHECKS)) { ret = send_list_of_active_checks_json(sock, &jp); } else if (0 == strcmp(value, ZBX_PROTO_VALUE_HOST_AVAILABILITY)) { if (0 != (daemon_type & ZBX_DAEMON_TYPE_SERVER)) recv_host_availability(sock, &jp); else if (0 != (daemon_type & ZBX_DAEMON_TYPE_PROXY_PASSIVE)) send_host_availability(sock); } else if (0 == strcmp(value, ZBX_PROTO_VALUE_COMMAND)) { ret = node_process_command(sock, s, &jp); } else zabbix_log(LOG_LEVEL_WARNING, "unknown request received [%s]", value); } return ret; } else if ('<' == *s) /* XML protocol */ { comms_parse_response(s, av.host_name, sizeof(av.host_name), av.key, sizeof(av.key), value_dec, sizeof(value_dec), lastlogsize, sizeof(lastlogsize), timestamp, sizeof(timestamp), source, sizeof(source), severity, sizeof(severity)); av.value = value_dec; if (SUCCEED != is_uint64(lastlogsize, &av.lastlogsize)) av.lastlogsize = 0; av.timestamp = atoi(timestamp); av.source = source; av.severity = atoi(severity); } else { pl = s; if (NULL == (pr = strchr(pl, ':'))) return FAIL; *pr = '\0'; zbx_strlcpy(av.host_name, pl, sizeof(av.host_name)); *pr = ':'; pl = pr + 1; if (NULL == (pr = strchr(pl, ':'))) return FAIL; *pr = '\0'; zbx_strlcpy(av.key, pl, sizeof(av.key)); *pr = ':'; av.value = pr + 1; av.severity = 0; } zbx_timespec(&av.ts); if (0 == strcmp(av.value, ZBX_NOTSUPPORTED)) av.status = ITEM_STATUS_NOTSUPPORTED; process_mass_data(sock, 0, &av, 1, NULL); alarm(CONFIG_TIMEOUT); if (SUCCEED != zbx_tcp_send_raw(sock, SUCCEED == ret ? "OK" : "NOT OK")) zabbix_log(LOG_LEVEL_WARNING, "Error sending result back"); alarm(0); } return ret; }
/****************************************************************************** * * * Function: parse_list_of_checks * * * * Purpose: Parse list of active checks received from server * * * * Parameters: str - NULL terminated string received from server * * host - address of host * * port - port number on host * * * * Return value: returns SUCCEED on successful parsing, * * FAIL on an incorrect format of string * * * * Author: Eugene Grigorjev, Alexei Vladishev (new json protocol) * * * * Comments: * * String represented as "ZBX_EOF" termination list * * With '\n' delimiter between elements. * * Each element represented as: * * <key>:<refresh time>:<last log size>:<modification time> * * * ******************************************************************************/ static int parse_list_of_checks(char *str, const char *host, unsigned short port) { const char *p; char name[MAX_STRING_LEN], key_orig[MAX_STRING_LEN], expression[MAX_STRING_LEN], tmp[MAX_STRING_LEN], exp_delimiter; int delay, mtime, expression_type, case_sensitive; zbx_uint64_t lastlogsize; struct zbx_json_parse jp; struct zbx_json_parse jp_data, jp_row; zabbix_log(LOG_LEVEL_DEBUG, "In parse_list_of_checks()"); disable_all_metrics(); if (SUCCEED != zbx_json_open(str, &jp)) goto json_error; if (SUCCEED != zbx_json_value_by_name(&jp, ZBX_PROTO_TAG_RESPONSE, tmp, sizeof(tmp))) goto json_error; if (0 != strcmp(tmp, ZBX_PROTO_VALUE_SUCCESS)) { if (SUCCEED == zbx_json_value_by_name(&jp, ZBX_PROTO_TAG_INFO, tmp, sizeof(tmp))) zabbix_log(LOG_LEVEL_WARNING, "no active checks on server [%s:%hu]: %s", host, port, tmp); else zabbix_log(LOG_LEVEL_WARNING, "no active checks on server"); return FAIL; } if (SUCCEED != zbx_json_brackets_by_name(&jp, ZBX_PROTO_TAG_DATA, &jp_data)) goto json_error; p = NULL; while (NULL != (p = zbx_json_next(&jp_data, p))) { /* {"data":[{"key":"system.cpu.num",...,...},{...},...]} * ^------------------------------^ */ if (SUCCEED != zbx_json_brackets_open(p, &jp_row)) goto json_error; if (SUCCEED != zbx_json_value_by_name(&jp_row, ZBX_PROTO_TAG_KEY, name, sizeof(name)) || '\0' == *name) { zabbix_log(LOG_LEVEL_WARNING, "cannot retrieve value of tag \"%s\"", ZBX_PROTO_TAG_KEY); continue; } if (SUCCEED != zbx_json_value_by_name(&jp_row, ZBX_PROTO_TAG_KEY_ORIG, key_orig, sizeof(key_orig)) || '\0' == *key_orig) { zbx_strlcpy(key_orig, name, sizeof(key_orig)); } if (SUCCEED != zbx_json_value_by_name(&jp_row, ZBX_PROTO_TAG_DELAY, tmp, sizeof(tmp)) || '\0' == *tmp) { zabbix_log(LOG_LEVEL_WARNING, "cannot retrieve value of tag \"%s\"", ZBX_PROTO_TAG_DELAY); continue; } delay = atoi(tmp); if (SUCCEED != zbx_json_value_by_name(&jp_row, ZBX_PROTO_TAG_LOGLASTSIZE, tmp, sizeof(tmp)) || SUCCEED != is_uint64(tmp, &lastlogsize)) { zabbix_log(LOG_LEVEL_WARNING, "cannot retrieve value of tag \"%s\"", ZBX_PROTO_TAG_LOGLASTSIZE); continue; } if (SUCCEED != zbx_json_value_by_name(&jp_row, ZBX_PROTO_TAG_MTIME, tmp, sizeof(tmp)) || '\0' == *tmp) { zabbix_log(LOG_LEVEL_WARNING, "cannot retrieve value of tag \"%s\"", ZBX_PROTO_TAG_MTIME); mtime = 0; } else mtime = atoi(tmp); add_check(name, key_orig, delay, lastlogsize, mtime); } zbx_regexp_clean_expressions(®exps); if (SUCCEED == zbx_json_brackets_by_name(&jp, ZBX_PROTO_TAG_REGEXP, &jp_data)) { p = NULL; while (NULL != (p = zbx_json_next(&jp_data, p))) { /* {"regexp":[{"name":"regexp1",...,...},{...},...]} * ^------------------------^ */ if (SUCCEED != zbx_json_brackets_open(p, &jp_row)) goto json_error; if (SUCCEED != zbx_json_value_by_name(&jp_row, "name", name, sizeof(name))) { zabbix_log(LOG_LEVEL_WARNING, "cannot retrieve value of tag \"%s\"", "name"); continue; } if (SUCCEED != zbx_json_value_by_name(&jp_row, "expression", expression, sizeof(expression)) || '\0' == *expression) { zabbix_log(LOG_LEVEL_WARNING, "cannot retrieve value of tag \"%s\"", "expression"); continue; } if (SUCCEED != zbx_json_value_by_name(&jp_row, "expression_type", tmp, sizeof(tmp)) || '\0' == *tmp) { zabbix_log(LOG_LEVEL_WARNING, "cannot retrieve value of tag \"%s\"", "expression_type"); continue; } expression_type = atoi(tmp); if (SUCCEED != zbx_json_value_by_name(&jp_row, "exp_delimiter", tmp, sizeof(tmp))) { zabbix_log(LOG_LEVEL_WARNING, "cannot retrieve value of tag \"%s\"", "exp_delimiter"); continue; } exp_delimiter = tmp[0]; if (SUCCEED != zbx_json_value_by_name(&jp_row, "case_sensitive", tmp, sizeof(tmp)) || '\0' == *tmp) { zabbix_log(LOG_LEVEL_WARNING, "cannot retrieve value of tag \"%s\"", "case_sensitive"); continue; } case_sensitive = atoi(tmp); add_regexp_ex(®exps, name, expression, expression_type, exp_delimiter, case_sensitive); } } return SUCCEED; json_error: zabbix_log(LOG_LEVEL_ERR, "cannot parse list of active checks: %s", zbx_json_strerror()); return FAIL; }