summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authoralex <alex@97f52cf1-0a1b-0410-bd0e-c28be96e8082>2007-04-18 12:03:37 +0000
committeralex <alex@97f52cf1-0a1b-0410-bd0e-c28be96e8082>2007-04-18 12:03:37 +0000
commit0ae3a0ca67fd055ba7735ccd0b010f5508271cb3 (patch)
tree7db28964ae220a77314484c74b2397614f9688b8
parent1bc36b4f63dbe95d7d98be834e1e69a8a7ef4cb4 (diff)
downloadzabbix-0ae3a0ca67fd055ba7735ccd0b010f5508271cb3.tar.gz
zabbix-0ae3a0ca67fd055ba7735ccd0b010f5508271cb3.tar.xz
zabbix-0ae3a0ca67fd055ba7735ccd0b010f5508271cb3.zip
- added discovery based on data receivedfrom ZABBIX and SNMP agents (Alexei)
git-svn-id: svn://svn.zabbix.com/trunk@4036 97f52cf1-0a1b-0410-bd0e-c28be96e8082
-rw-r--r--ChangeLog4
-rw-r--r--create/schema/schema.sql4
-rw-r--r--include/common.h8
-rw-r--r--include/db.h7
-rw-r--r--src/zabbix_server/actions.c48
-rw-r--r--src/zabbix_server/discoverer/discoverer.c112
-rw-r--r--src/zabbix_server/operations.c84
7 files changed, 230 insertions, 37 deletions
diff --git a/ChangeLog b/ChangeLog
index 3eee21c0..dce7df28 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,5 +1,9 @@
Changes for 1.3.5:
+ - added discovery based on data receivedfrom ZABBIX and SNMP agents (Alexei)
+
+Changes for 1.3.5:
+
- removed support of autoregistration, use autodiscovery instead (Alexei)
- fixed creation of Sqlite schema (Alexei)
- fixed dependences of deleted elements for actions (Eugene)
diff --git a/create/schema/schema.sql b/create/schema/schema.sql
index 35c91f43..9c6d8705 100644
--- a/create/schema/schema.sql
+++ b/create/schema/schema.sql
@@ -46,6 +46,8 @@ TABLE|dchecks|dcheckid|ZBX_SYNC
FIELD |dcheckid |t_id |'0' |NOT NULL |ZBX_SYNC
FIELD |druleid |t_id |'0' |NOT NULL |ZBX_SYNC
FIELD |type |t_integer |'0' |NOT NULL |ZBX_SYNC
+FIELD |key_ |t_varchar(255) |'0' |NOT NULL |ZBX_SYNC
+FIELD |snmp_community |t_varchar(255) |'0' |NOT NULL |ZBX_SYNC
FIELD |ports |t_varchar(255) |'0' |NOT NULL |ZBX_SYNC
TABLE|dhosts|dhostid|ZBX_SYNC
@@ -60,6 +62,8 @@ TABLE|dservices|dserviceid|ZBX_SYNC
FIELD |dserviceid |t_id |'0' |NOT NULL |ZBX_SYNC
FIELD |dhostid |t_id |'0' |NOT NULL |ZBX_SYNC
FIELD |type |t_integer |'0' |NOT NULL |ZBX_SYNC
+FIELD |key_ |t_varchar(255) |'0' |NOT NULL |ZBX_SYNC
+FIELD |value |t_varchar(255) |'0' |NOT NULL |ZBX_SYNC
FIELD |port |t_integer |'0' |NOT NULL |ZBX_SYNC
FIELD |status |t_integer |'0' |NOT NULL |ZBX_SYNC
FIELD |lastup |t_integer |'0' |NOT NULL |ZBX_SYNC
diff --git a/include/common.h b/include/common.h
index 7c750198..c632a466 100644
--- a/include/common.h
+++ b/include/common.h
@@ -177,7 +177,10 @@ typedef enum
SVC_POP,
SVC_NNTP,
SVC_IMAP,
- SVC_TCP
+ SVC_TCP,
+ SVC_AGENT,
+ SVC_SNMPv1,
+ SVC_SNMPv2c
} zbx_dservice_type_t;
@@ -221,7 +224,8 @@ typedef enum
CONDITION_TYPE_DSERVICE_TYPE,
CONDITION_TYPE_DSERVICE_PORT,
CONDITION_TYPE_DSTATUS,
- CONDITION_TYPE_DUPTIME
+ CONDITION_TYPE_DUPTIME,
+ CONDITION_TYPE_DVALUE
} zbx_condition_type_t;
/* Condition operators */
diff --git a/include/db.h b/include/db.h
index d68ecfb6..92cdf509 100644
--- a/include/db.h
+++ b/include/db.h
@@ -108,6 +108,9 @@ extern int CONFIG_MASTER_NODEID;
#define ACTION_SUBJECT_LEN 255
#define ACTION_SUBJECT_LEN_MAX ACTION_SUBJECT_LEN+1
+#define DSERVICE_VALUE_LEN 255
+#define DSERVICE_VALUE_LEN_MAX DSERVICE_VALUE_LEN+1
+
#define ZBX_SQL_ITEM_SELECT "i.itemid,i.key_,h.host,h.port,i.delay,i.description,i.nextcheck,i.type,i.snmp_community,i.snmp_oid,h.useip,h.ip,i.history,i.lastvalue,i.prevvalue,i.hostid,h.status,i.value_type,h.errors_from,i.snmp_port,i.delta,i.prevorgvalue,i.lastclock,i.units,i.multiplier,i.snmpv3_securityname,i.snmpv3_securitylevel,i.snmpv3_authpassphrase,i.snmpv3_privpassphrase,i.formula,h.available,i.status,i.trapper_hosts,i.logtimefmt,i.valuemapid,i.delay_flex,h.dns from hosts h, items i"
#define ZBX_MAX_SQL_LEN 65535
@@ -128,7 +131,10 @@ DB_DCHECK
zbx_uint64_t druleid;
int type;
char *ports;
+ char *key_;
+ char *snmp_community;
int status;
+ char value[DSERVICE_VALUE_LEN_MAX];
};
DB_DHOST
@@ -150,6 +156,7 @@ DB_DSERVICE
int status;
int lastup;
int lastdown;
+ char value[DSERVICE_VALUE_LEN_MAX];
};
DB_EVENT
diff --git a/src/zabbix_server/actions.c b/src/zabbix_server/actions.c
index 1f3fdbf8..a6e24d09 100644
--- a/src/zabbix_server/actions.c
+++ b/src/zabbix_server/actions.c
@@ -293,6 +293,52 @@ static int check_action_condition(DB_EVENT *event, DB_CONDITION *condition)
}
}
else if(event->source == EVENT_SOURCE_DISCOVERY &&
+ event->object == EVENT_OBJECT_DSERVICE &&
+ condition->conditiontype == CONDITION_TYPE_DVALUE)
+ {
+ zabbix_log( LOG_LEVEL_DEBUG, "CONDITION_TYPE_DVALUE [%d:%s]",
+ event->value,
+ condition->value);
+
+ result = DBselect("select value from dservices where dserviceid=" ZBX_FS_UI64,
+ event->objectid);
+ row = DBfetch(result);
+ if(row && DBis_null(row[0]) != SUCCEED)
+ {
+ if(condition->operator == CONDITION_OPERATOR_EQUAL)
+ {
+ if(strcmp(condition->value, row[0]) == 0) ret = SUCCEED;
+ }
+ else if(condition->operator == CONDITION_OPERATOR_NOT_EQUAL)
+ {
+ if(strcmp(condition->value, row[0]) != 0) ret = SUCCEED;
+ }
+ else if(condition->operator == CONDITION_OPERATOR_MORE_EQUAL)
+ {
+ if(strcmp(row[0], condition->value) >= 0) ret = SUCCEED;
+ }
+ else if(condition->operator == CONDITION_OPERATOR_LESS_EQUAL)
+ {
+ if(strcmp(row[0], condition->value) <= 0) ret = SUCCEED;
+ }
+ else if(condition->operator == CONDITION_OPERATOR_LIKE)
+ {
+ if(strstr(row[0], condition->value) != NULL) ret = SUCCEED;
+ }
+ else if(condition->operator == CONDITION_OPERATOR_NOT_LIKE)
+ {
+ if(strstr(row[0], condition->value) == NULL) ret = SUCCEED;
+ }
+ else
+ {
+ zabbix_log( LOG_LEVEL_ERR, "Unsupported operator [%d] for condition id [" ZBX_FS_UI64 "]",
+ condition->operator,
+ condition->conditionid);
+ }
+ }
+ DBfree_result(result);
+ }
+ else if(event->source == EVENT_SOURCE_DISCOVERY &&
(event->object == EVENT_OBJECT_DHOST || event->object == EVENT_OBJECT_DSERVICE) &&
condition->conditiontype == CONDITION_TYPE_DHOST_IP)
{
@@ -463,7 +509,7 @@ static int check_action_condition(DB_EVENT *event, DB_CONDITION *condition)
}
else
{
- zabbix_log( LOG_LEVEL_ERR, "Event source [%d] and condition type [%d] is unknown for condition id [" ZBX_FS_UI64 "]",
+ zabbix_log( LOG_LEVEL_DEBUG, "Event source [%d] and condition type [%d] is unknown for condition id [" ZBX_FS_UI64 "]",
event->source,
condition->conditiontype,
condition->conditionid);
diff --git a/src/zabbix_server/discoverer/discoverer.c b/src/zabbix_server/discoverer/discoverer.c
index 06bac07d..51709aeb 100644
--- a/src/zabbix_server/discoverer/discoverer.c
+++ b/src/zabbix_server/discoverer/discoverer.c
@@ -196,13 +196,12 @@ static void register_service(DB_DSERVICE *service,DB_DRULE *rule,DB_DCHECK *chec
{
DB_RESULT result;
DB_ROW row;
- zbx_uint64_t dserviceid = 0;
zabbix_log(LOG_LEVEL_DEBUG, "In register_service(ip:%s,port:%d)",
ip,
port);
- result = DBselect("select dserviceid,dhostid,type,port,status,lastup,lastdown from dservices where dhostid=" ZBX_FS_UI64 " and type=%d and port=%d",
+ result = DBselect("select dserviceid,dhostid,type,port,status,lastup,lastdown,value from dservices where dhostid=" ZBX_FS_UI64 " and type=%d and port=%d",
dhostid,
check->type,
port);
@@ -213,26 +212,30 @@ static void register_service(DB_DSERVICE *service,DB_DRULE *rule,DB_DCHECK *chec
if(check->status == DOBJECT_STATUS_UP)
{
zabbix_log(LOG_LEVEL_DEBUG, "New service discovered on port %d", port);
- dserviceid = DBget_maxid("dservices","dserviceid");
- DBexecute("insert into dservices (dhostid,dserviceid,type,port,status) values (" ZBX_FS_UI64 "," ZBX_FS_UI64 ",%d,%d,%d)",
- dhostid,
- dserviceid,
- check->type,
- port,
- DOBJECT_STATUS_UP);
- service->dserviceid = dserviceid;
+ service->dserviceid = DBget_maxid("dservices","dserviceid");
service->dhostid = dhostid;
service->type = check->type;
service->port = port;
service->status = DOBJECT_STATUS_UP;
service->lastup = 0;
service->lastdown = 0;
+ DBescape_string(check->value, service->value, sizeof(service->value)-1);
+
+ DBexecute("insert into dservices (dhostid,dserviceid,type,port,status,value) values (" ZBX_FS_UI64 "," ZBX_FS_UI64 ",%d,%d,%d,'%s')",
+ service->dhostid,
+ service->dserviceid,
+ check->type,
+ service->port,
+ service->status,
+ service->value);
+
}
}
else
{
zabbix_log(LOG_LEVEL_DEBUG, "Service is already in database");
+
ZBX_STR2UINT64(service->dserviceid, row[0]);
ZBX_STR2UINT64(service->dhostid, row[1]);
service->type = atoi(row[2]);
@@ -240,6 +243,7 @@ static void register_service(DB_DSERVICE *service,DB_DRULE *rule,DB_DCHECK *chec
service->status = atoi(row[4]);
service->lastup = atoi(row[5]);
service->lastdown = atoi(row[6]);
+ strscpy(service->value,row[7]);
}
DBfree_result(result);
@@ -410,22 +414,23 @@ static void update_service(DB_DRULE *rule, DB_DCHECK *check, char *ip, int port)
* Comments: *
* *
******************************************************************************/
-static int discover_service(zbx_dservice_type_t type, char *ip, int port)
+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;
zabbix_log(LOG_LEVEL_DEBUG, "In discover_service(ip:%s, port:%d, type:%d)",
ip,
port,
- type);
+ check->type);
init_result(&value);
- switch(type) {
+ switch(check->type) {
case SVC_SSH:
zbx_snprintf(key,sizeof(key)-1,"net.tcp.service[ssh,%s,%d]",
ip,
@@ -471,6 +476,8 @@ static int discover_service(zbx_dservice_type_t type, char *ip, int port)
ip,
port);
break;
+ case SVC_AGENT:
+ break;
default:
ret = FAIL;
break;
@@ -484,15 +491,70 @@ static int discover_service(zbx_dservice_type_t type, char *ip, int port)
sigaction(SIGALRM, &phan, NULL);
alarm(10);
- if(process(key, 0, &value) == SUCCEED)
- {
- if(GET_UI64_RESULT(&value))
- {
- if(value.ui64 == 0) ret = FAIL;
- }
- else ret = FAIL;
+ 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;
+
+ item.snmp_community = check->key_;
+ 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
+ {
+ if(SUCCEED == get_value_snmp(&item, &value))
+ {
+ if(GET_STR_RESULT(&value))
+ {
+ strscpy(check->value, value.str);
+ }
+ else ret = FAIL;
+ }
+ else
+ {
+ ret = FAIL;
+ }
+ }
+ 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;
}
- else ret = FAIL;
alarm(0);
}
@@ -550,7 +612,7 @@ static void process_check(DB_DRULE *rule, DB_DCHECK *check, char *ip)
for(port=first;port<=last;port++)
{
- check->status = discover_service(check->type,ip,port);
+ check->status = discover_service(check,ip,port);
update_service(rule, check, ip, port);
}
s=(char *)strtok(NULL,"\n");
@@ -621,14 +683,16 @@ static void process_rule(DB_DRULE *rule)
ip1,
i);
zabbix_log(LOG_LEVEL_DEBUG, "IP [%s]", ip);
- result = DBselect("select dcheckid,druleid,type,ports from dchecks where druleid=" ZBX_FS_UI64,
+ result = DBselect("select dcheckid,druleid,type,key_,snmp_community,ports from dchecks where druleid=" ZBX_FS_UI64,
rule->druleid);
while((row=DBfetch(result)))
{
ZBX_STR2UINT64(check.dcheckid,row[0]);
ZBX_STR2UINT64(check.druleid,row[1]);
check.type = atoi(row[2]);
- check.ports = row[3];
+ check.key_ = row[3];
+ check.snmp_community = row[4];
+ check.ports = row[5];
process_check(rule, &check, ip);
}
diff --git a/src/zabbix_server/operations.c b/src/zabbix_server/operations.c
index fcab3c60..a1e51a48 100644
--- a/src/zabbix_server/operations.c
+++ b/src/zabbix_server/operations.c
@@ -363,6 +363,44 @@ void op_run_commands(DB_EVENT *event, DB_OPERATION *operation)
/******************************************************************************
* *
+ * Function: select dhostid by dserviceid *
+ * *
+ * Purpose: select discovered host id *
+ * *
+ * Parameters: dserviceid - servce id *
+ * *
+ * Return value: dhostid - existing dhostid, 0 - if not found *
+ * *
+ * Author: Alexei Vladishev *
+ * *
+ * Comments: *
+ * *
+ ******************************************************************************/
+static zbx_uint64_t select_dhostid_by_dserviceid(zbx_uint64_t dserviceid)
+{
+ DB_RESULT result;
+ DB_ROW row;
+ zbx_uint64_t dhostid = 0;
+
+ zabbix_log(LOG_LEVEL_DEBUG, "In select_dhostid_by_dserviceid(dserviceid:" ZBX_FS_UI64 ")",
+ dserviceid);
+
+ result = DBselect("select dhostid from dservices where dserviceid=" ZBX_FS_UI64,
+ dserviceid);
+ row = DBfetch(result);
+ if(row && DBis_null(row[0]) != SUCCEED)
+ {
+ ZBX_STR2UINT64(dhostid, row[0]);
+ }
+ DBfree_result(result);
+
+ zabbix_log(LOG_LEVEL_DEBUG, "End select_dhostid_by_dserviceid()");
+
+ return dhostid;
+}
+
+/******************************************************************************
+ * *
* Function: select hostid of discovered host *
* *
* Purpose: select discovered host *
@@ -475,15 +513,21 @@ static zbx_uint64_t add_discovered_host(zbx_uint64_t dhostid)
******************************************************************************/
void op_host_add(DB_EVENT *event)
{
- zbx_uint64_t hostid;
+ zbx_uint64_t hostid, dhostid;
zabbix_log(LOG_LEVEL_DEBUG, "In op_host_add()");
if(event->object == EVENT_OBJECT_DHOST)
{
- hostid = add_discovered_host(event->objectid);
+ dhostid = event->objectid;
+ }
+ else if(event->object == EVENT_OBJECT_DSERVICE)
+ {
+ dhostid = select_dhostid_by_dserviceid(event->objectid);
}
+ hostid = add_discovered_host(dhostid);
+
zabbix_log(LOG_LEVEL_DEBUG, "End op_host_add()");
}
@@ -507,14 +551,25 @@ void op_group_add(DB_EVENT *event, DB_ACTION *action, DB_OPERATION *operation)
{
DB_RESULT result;
DB_ROW row;
- zbx_uint64_t hostgroupid, groupid, hostid;
+ zbx_uint64_t hostgroupid, groupid, hostid, dhostid;
+
+ zabbix_log(LOG_LEVEL_DEBUG, "In op_group_add(object:%d)",
+ event->object);
- zabbix_log(LOG_LEVEL_DEBUG, "In op_group_add()");
+ if(operation->operationtype != OPERATION_TYPE_GROUP_ADD) return;
+ if(event->object != EVENT_OBJECT_DHOST && event->object != EVENT_OBJECT_DSERVICE) return;
- if(operation->operationtype != OPERATION_TYPE_GROUP_ADD) return;
- if(event->object != EVENT_OBJECT_DHOST) return;
- hostid = add_discovered_host(event->objectid);
+ if(event->object == EVENT_OBJECT_DSERVICE)
+ {
+ dhostid = select_dhostid_by_dserviceid(event->objectid);
+ }
+ else
+ {
+ dhostid = event->objectid;
+ }
+
+ hostid = add_discovered_host(dhostid);
if(hostid != 0)
{
groupid = operation->objectid;
@@ -554,14 +609,23 @@ void op_group_add(DB_EVENT *event, DB_ACTION *action, DB_OPERATION *operation)
******************************************************************************/
void op_group_del(DB_EVENT *event, DB_ACTION *action, DB_OPERATION *operation)
{
- zbx_uint64_t groupid, hostid;
+ zbx_uint64_t groupid, hostid, dhostid;
zabbix_log(LOG_LEVEL_DEBUG, "In op_group_del()");
if(operation->operationtype != OPERATION_TYPE_GROUP_REMOVE) return;
- if(event->object != EVENT_OBJECT_DHOST) return;
+ if(event->object != EVENT_OBJECT_DHOST && event->object != EVENT_OBJECT_DSERVICE) return;
+
+ if(event->object == EVENT_OBJECT_DSERVICE)
+ {
+ dhostid = select_dhostid_by_dserviceid(event->objectid);
+ }
+ else
+ {
+ dhostid = event->objectid;
+ }
- hostid = select_discovered_host(event->objectid);
+ hostid = select_discovered_host(dhostid);
if(hostid != 0)
{
groupid = operation->objectid;