1 /*
2 ** Zabbix
3 ** Copyright (C) 2001-2021 Zabbix SIA
4 **
5 ** This program is free software; you can redistribute it and/or modify
6 ** it under the terms of the GNU General Public License as published by
7 ** the Free Software Foundation; either version 2 of the License, or
8 ** (at your option) any later version.
9 **
10 ** This program is distributed in the hope that it will be useful,
11 ** but WITHOUT ANY WARRANTY; without even the implied warranty of
12 ** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 ** GNU General Public License for more details.
14 **
15 ** You should have received a copy of the GNU General Public License
16 ** along with this program; if not, write to the Free Software
17 ** Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
18 **/
19
20 #include "common.h"
21 #include "sysinfo.h"
22
23 #include "log.h"
24
25 #include "file.h"
26 #include "dir.h"
27 #include "http.h"
28 #include "net.h"
29 #include "system.h"
30 #include "zabbix_stats.h"
31 #include "zbxexec.h"
32
33 #if !defined(_WINDOWS)
34 # define VFS_TEST_FILE "/etc/passwd"
35 # define VFS_TEST_REGEXP "root"
36 # define VFS_TEST_DIR "/var/log"
37 #else
38 # define VFS_TEST_FILE "c:\\windows\\win.ini"
39 # define VFS_TEST_REGEXP "fonts"
40 # define VFS_TEST_DIR "c:\\windows"
41 #endif
42
43 extern int CONFIG_TIMEOUT;
44
45 static int ONLY_ACTIVE(AGENT_REQUEST *request, AGENT_RESULT *result);
46 static int SYSTEM_RUN(AGENT_REQUEST *request, AGENT_RESULT *result);
47
48 ZBX_METRIC parameters_common[] =
49 /* KEY FLAG FUNCTION TEST PARAMETERS */
50 {
51 {"system.localtime", CF_HAVEPARAMS, SYSTEM_LOCALTIME, "utc"},
52 {"system.run", CF_HAVEPARAMS, SYSTEM_RUN, "echo test"},
53
54 {"web.page.get", CF_HAVEPARAMS, WEB_PAGE_GET, "localhost,,80"},
55 {"web.page.perf", CF_HAVEPARAMS, WEB_PAGE_PERF, "localhost,,80"},
56 {"web.page.regexp", CF_HAVEPARAMS, WEB_PAGE_REGEXP, "localhost,,80,OK"},
57
58 {"vfs.file.size", CF_HAVEPARAMS, VFS_FILE_SIZE, VFS_TEST_FILE},
59 {"vfs.file.time", CF_HAVEPARAMS, VFS_FILE_TIME, VFS_TEST_FILE ",modify"},
60 {"vfs.file.exists", CF_HAVEPARAMS, VFS_FILE_EXISTS, VFS_TEST_FILE},
61 {"vfs.file.contents", CF_HAVEPARAMS, VFS_FILE_CONTENTS, VFS_TEST_FILE},
62 {"vfs.file.regexp", CF_HAVEPARAMS, VFS_FILE_REGEXP, VFS_TEST_FILE "," VFS_TEST_REGEXP},
63 {"vfs.file.regmatch", CF_HAVEPARAMS, VFS_FILE_REGMATCH, VFS_TEST_FILE "," VFS_TEST_REGEXP},
64 {"vfs.file.md5sum", CF_HAVEPARAMS, VFS_FILE_MD5SUM, VFS_TEST_FILE},
65 {"vfs.file.cksum", CF_HAVEPARAMS, VFS_FILE_CKSUM, VFS_TEST_FILE},
66
67 {"vfs.dir.size", CF_HAVEPARAMS, VFS_DIR_SIZE, VFS_TEST_DIR},
68 {"vfs.dir.count", CF_HAVEPARAMS, VFS_DIR_COUNT, VFS_TEST_DIR},
69
70 {"net.dns", CF_HAVEPARAMS, NET_DNS, ",zabbix.com"},
71 {"net.dns.record", CF_HAVEPARAMS, NET_DNS_RECORD, ",zabbix.com"},
72 {"net.tcp.dns", CF_HAVEPARAMS, NET_DNS, ",zabbix.com"}, /* deprecated */
73 {"net.tcp.dns.query", CF_HAVEPARAMS, NET_DNS_RECORD, ",zabbix.com"}, /* deprecated */
74 {"net.tcp.port", CF_HAVEPARAMS, NET_TCP_PORT, ",80"},
75
76 {"system.users.num", 0, SYSTEM_USERS_NUM, NULL},
77
78 {"log", CF_HAVEPARAMS, ONLY_ACTIVE, "logfile"},
79 {"log.count", CF_HAVEPARAMS, ONLY_ACTIVE, "logfile"},
80 {"logrt", CF_HAVEPARAMS, ONLY_ACTIVE, "logfile"},
81 {"logrt.count", CF_HAVEPARAMS, ONLY_ACTIVE, "logfile"},
82 {"eventlog", CF_HAVEPARAMS, ONLY_ACTIVE, "system"},
83
84 {"zabbix.stats", CF_HAVEPARAMS, ZABBIX_STATS, "127.0.0.1,10051"},
85
86 {NULL}
87 };
88
ONLY_ACTIVE(AGENT_REQUEST * request,AGENT_RESULT * result)89 static int ONLY_ACTIVE(AGENT_REQUEST *request, AGENT_RESULT *result)
90 {
91 ZBX_UNUSED(request);
92
93 SET_MSG_RESULT(result, zbx_strdup(NULL, "Accessible only as active check."));
94
95 return SYSINFO_RET_FAIL;
96 }
97
EXECUTE_USER_PARAMETER(AGENT_REQUEST * request,AGENT_RESULT * result)98 int EXECUTE_USER_PARAMETER(AGENT_REQUEST *request, AGENT_RESULT *result)
99 {
100 char *command;
101
102 if (1 != request->nparam)
103 {
104 SET_MSG_RESULT(result, zbx_strdup(NULL, "Too many parameters."));
105 return SYSINFO_RET_FAIL;
106 }
107
108 command = get_rparam(request, 0);
109
110 return EXECUTE_STR(command, result);
111 }
112
EXECUTE_STR(const char * command,AGENT_RESULT * result)113 int EXECUTE_STR(const char *command, AGENT_RESULT *result)
114 {
115 const char *__function_name = "EXECUTE_STR";
116
117 int ret = SYSINFO_RET_FAIL;
118 char *cmd_result = NULL, error[MAX_STRING_LEN];
119
120 if (SUCCEED != zbx_execute(command, &cmd_result, error, sizeof(error), CONFIG_TIMEOUT,
121 ZBX_EXIT_CODE_CHECKS_DISABLED))
122 {
123 SET_MSG_RESULT(result, zbx_strdup(NULL, error));
124 goto out;
125 }
126
127 zbx_rtrim(cmd_result, ZBX_WHITESPACE);
128
129 zabbix_log(LOG_LEVEL_DEBUG, "%s() command:'%s' len:" ZBX_FS_SIZE_T " cmd_result:'%.20s'",
130 __function_name, command, (zbx_fs_size_t)strlen(cmd_result), cmd_result);
131
132 SET_TEXT_RESULT(result, zbx_strdup(NULL, cmd_result));
133
134 ret = SYSINFO_RET_OK;
135 out:
136 zbx_free(cmd_result);
137
138 return ret;
139 }
140
EXECUTE_DBL(const char * command,AGENT_RESULT * result)141 int EXECUTE_DBL(const char *command, AGENT_RESULT *result)
142 {
143 if (SYSINFO_RET_OK != EXECUTE_STR(command, result))
144 return SYSINFO_RET_FAIL;
145
146 if (NULL == GET_DBL_RESULT(result))
147 {
148 zabbix_log(LOG_LEVEL_WARNING, "Remote command [%s] result is not double", command);
149 SET_MSG_RESULT(result, zbx_strdup(NULL, "Invalid result. Double is expected."));
150 return SYSINFO_RET_FAIL;
151 }
152
153 UNSET_RESULT_EXCLUDING(result, AR_DOUBLE);
154
155 return SYSINFO_RET_OK;
156 }
157
EXECUTE_INT(const char * command,AGENT_RESULT * result)158 int EXECUTE_INT(const char *command, AGENT_RESULT *result)
159 {
160 if (SYSINFO_RET_OK != EXECUTE_STR(command, result))
161 return SYSINFO_RET_FAIL;
162
163 if (NULL == GET_UI64_RESULT(result))
164 {
165 zabbix_log(LOG_LEVEL_WARNING, "Remote command [%s] result is not unsigned integer", command);
166 SET_MSG_RESULT(result, zbx_strdup(NULL, "Invalid result. Unsigned integer is expected."));
167 return SYSINFO_RET_FAIL;
168 }
169
170 UNSET_RESULT_EXCLUDING(result, AR_UINT64);
171
172 return SYSINFO_RET_OK;
173 }
174
SYSTEM_RUN(AGENT_REQUEST * request,AGENT_RESULT * result)175 static int SYSTEM_RUN(AGENT_REQUEST *request, AGENT_RESULT *result)
176 {
177 char *command, *flag;
178
179 if (2 < request->nparam)
180 {
181 SET_MSG_RESULT(result, zbx_strdup(NULL, "Too many parameters."));
182 return SYSINFO_RET_FAIL;
183 }
184
185 command = get_rparam(request, 0);
186 flag = get_rparam(request, 1);
187
188 if (NULL == command || '\0' == *command)
189 {
190 SET_MSG_RESULT(result, zbx_strdup(NULL, "Invalid first parameter."));
191 return SYSINFO_RET_FAIL;
192 }
193
194 if (1 == CONFIG_LOG_REMOTE_COMMANDS)
195 zabbix_log(LOG_LEVEL_WARNING, "Executing command '%s'", command);
196 else
197 zabbix_log(LOG_LEVEL_DEBUG, "Executing command '%s'", command);
198
199 if (NULL == flag || '\0' == *flag || 0 == strcmp(flag, "wait")) /* default parameter */
200 {
201 return EXECUTE_STR(command, result);
202 }
203 else if (0 == strcmp(flag, "nowait"))
204 {
205 if (SUCCEED != zbx_execute_nowait(command))
206 {
207 SET_MSG_RESULT(result, zbx_strdup(NULL, "Cannot execute command."));
208 return SYSINFO_RET_FAIL;
209 }
210 }
211 else
212 {
213 SET_MSG_RESULT(result, zbx_strdup(NULL, "Invalid second parameter."));
214 return SYSINFO_RET_FAIL;
215 }
216
217 SET_UI64_RESULT(result, 1);
218
219 return SYSINFO_RET_OK;
220 }
221