00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020 #include <config.h>
00021
00022 #include <stdio.h>
00023
00024 #ifdef HAVE_SYS_TYPES_H
00025 #include <sys/types.h>
00026 #endif
00027
00028 #include <sys/socket.h>
00029 #include <stdlib.h>
00030
00031 #ifdef HAVE_STRING_H
00032 #include <string.h>
00033 #endif
00034
00035 #ifdef HAVE_UNISTD_H
00036 #include <unistd.h>
00037 #endif
00038
00039 #include "monitor.h"
00040 #include "net.h"
00041
00042
00043
00044 static void wait_stop(Process_T);
00045 static void wait_start(Process_T);
00046 static void do_stop(Process_T, int);
00047 static void do_start(Process_T, int);
00048 static void do_depend(Process_T, char *, int);
00049
00050
00062
00063
00064
00070 void control(char *action, int toggle_validate_flag) {
00071
00072 Process_T p;
00073
00074 ASSERT(action);
00075
00076 for(p= processlist; p; p= p->next) {
00077 if(p->visited)
00078 continue;
00079 if(exist_daemon()) {
00080 d_check_process(p->name, action);
00081 } else {
00082 check_process(p->name, action, toggle_validate_flag);
00083 }
00084 }
00085
00086 reset_depend();
00087
00088 }
00089
00090
00091
00092
00093
00094
00095
00096
00097 void control_group(char *G, char *action, int toggle_validate_flag) {
00098
00099 Process_T p;
00100
00101 ASSERT(G);
00102 ASSERT(action);
00103
00104 for(p= processlist; p; p= p->next) {
00105 if(p->visited)
00106 continue;
00107 if(is(p->group, G)) {
00108 if(exist_daemon()) {
00109 d_check_process(p->name, action);
00110 } else {
00111 check_process(p->name, action, toggle_validate_flag);
00112 }
00113 }
00114 }
00115
00116 reset_depend();
00117
00118 }
00119
00120
00126 void d_check_process(char *P, char *action) {
00127
00128 int s;
00129 char req[2*STRLEN];
00130 char *auth= get_basic_authentication_header();
00131 ssl_connection *ssl= NULL;
00132
00133 ASSERT(P);
00134 ASSERT(action);
00135
00136 if(Run.httpdssl) {
00137
00138 ssl= new_ssl_connection(Run.httpsslpem);
00139
00140 }
00141
00142 s= create_socket(Run.bind_addr?Run.bind_addr:"localhost",
00143 Run.httpdport, SOCK_STREAM);
00144
00145 if(s < 0) {
00146
00147 error("%s: Cannot connect to the monit daemon. "
00148 "Did you start it with http support?\n", prog);
00149 goto error;
00150
00151 } else {
00152 snprintf(req, sizeof(req),
00153 "GET /%s?action=%s HTTP/1.0\r\n%s\r\n", P, action, auth);
00154
00155 if(ssl) {
00156
00157 if(!embed_ssl_socket(ssl, s)) {
00158
00159 fprintf(stdout, "Failed establish SSL communication to monit"
00160 " server\n");
00161 goto error;
00162 }
00163
00164 send_ssl_socket(ssl, req, sizeof(req));
00165
00166 close_ssl_socket(ssl);
00167 close_socket(s);
00168
00169 } else {
00170
00171 sock_send(s, req, sizeof(req), 0);
00172 close_socket(s);
00173
00174 }
00175 }
00176
00177 if(Run.httpdssl) {
00178
00179 delete_ssl_socket(ssl);
00180
00181 }
00182
00183 error:
00184 free(auth);
00185
00186 }
00187
00188
00195 void check_process(char *P, char *action, int toggle_validate_flag) {
00196
00197 Process_T p= NULL;
00198
00199 ASSERT(P);
00200 ASSERT(action);
00201
00202 if(NULL==(p= get_process(P))) {
00203 error("%s: Cannot %s program '%s' -- not found in %s\n",
00204 prog, action, P, Run.controlfile);
00205 return;
00206 }
00207
00208 if(is(action, "start")) {
00209
00210 if(is_process_running(p)) {
00211 return;
00212 }
00213
00214 if(!p->start) {
00215 error("%s: Start method not defined -- process %s\n",
00216 prog, P);
00217 return;
00218 }
00219
00220 do_depend(p, "stop", toggle_validate_flag);
00221 do_start(p, toggle_validate_flag);
00222 do_depend(p, "start", toggle_validate_flag);
00223
00224 } else if(is(action, "stop")) {
00225
00226 if(!p->stop) {
00227 error("%s: Stop method not defined -- process %s\n",
00228 prog, P);
00229 return;
00230 }
00231
00232 do_depend(p, "stop", toggle_validate_flag);
00233 do_stop(p, toggle_validate_flag);
00234
00235 }
00236
00237 }
00238
00239
00240
00241
00242
00243 void reset_depend() {
00244
00245 Process_T p;
00246
00247 for (p= processlist; p; p= p->next) {
00248 p->visited= FALSE;
00249 p->depend_visited= FALSE;
00250 }
00251
00252 }
00253
00254
00255
00256
00257
00258
00259
00260
00261
00262
00263
00264 static void do_start(Process_T p, int toggle_validate_flag) {
00265
00266 ASSERT(p);
00267
00268 if(p->visited)
00269 return;
00270
00271 p->visited= TRUE;
00272
00273 if(p->dependantlist) {
00274
00275 Dependant_T d;
00276
00277 for(d= p->dependantlist; d; d= d->next ) {
00278
00279 Process_T dp= get_process(d->dependant);
00280 ASSERT(dp);
00281 do_start(dp, toggle_validate_flag);
00282
00283 }
00284 }
00285
00286 if(toggle_validate_flag) {
00287 LOCK(Run.mutex)
00288 p->do_validate= TRUE;
00289 END_LOCK;
00290 if(Run.debug)
00291 log("Monitoring enabled -- process %s\n", p->name);
00292 }
00293
00294 if(p->start && p->do_validate && (!is_process_running(p))) {
00295 log("start: (%s) %s\n", p->name, p->start->arg[0]);
00296 spawn(p, p->start);
00297 wait_start(p);
00298 }
00299
00300 }
00301
00302
00303
00304
00305
00306
00307
00308 static void do_stop(Process_T p, int toggle_validate_flag) {
00309
00310 ASSERT(p);
00311
00312 if(p->depend_visited)
00313 return;
00314
00315 p->depend_visited= TRUE;
00316
00317 if(p->stop && p->do_validate && is_process_running(p)) {
00318 log("stop: (%s) %s\n", p->name, p->stop->arg[0]);
00319 spawn(p, p->stop);
00320 memset(p->procinfo, 0, sizeof *(p->procinfo));
00321 wait_stop(p);
00322 }
00323
00324
00325 memset(p->procinfo, 0, sizeof *(p->procinfo));
00326
00327 if(toggle_validate_flag) {
00328 LOCK(Run.mutex)
00329 p->do_validate= FALSE;
00330 END_LOCK;
00331 if(Run.debug)
00332 log("Monitoring disabled -- process %s\n", p->name);
00333 }
00334
00335 }
00336
00337
00338
00339
00340
00341
00342
00343
00344
00345
00346
00347
00348 static void do_depend(Process_T p, char *action, int toggle_validate_flag) {
00349
00350 Process_T parent;
00351
00352 ASSERT(p);
00353
00354 for(parent= processlist; parent; parent= parent->next) {
00355
00356 if(parent->dependantlist) {
00357
00358 Dependant_T d;
00359
00360 for(d= parent->dependantlist; d; d= d->next)
00361 if(is(d->dependant, p->name))
00362 break;
00363
00364 if(d) {
00365
00366 if(is(action, "start"))
00367 do_start(parent, toggle_validate_flag);
00368
00369 do_depend(parent, action, toggle_validate_flag);
00370
00371 if(is(action, "stop"))
00372 do_stop(parent, toggle_validate_flag);
00373
00374 }
00375 }
00376 }
00377 }
00378
00379
00380
00381
00382
00383
00384 static void wait_start(Process_T p) {
00385
00386 int max_tries= Run.polltime;
00387
00388 ASSERT(p);
00389
00390 while(max_tries--) {
00391 if(is_process_running(p))
00392 break;
00393 sleep(1);
00394 }
00395
00396 if(!is_process_running(p))
00397 log("%s: Warning process '%s' was not started\n", p->name);
00398
00399 }
00400
00401
00402
00403
00404
00405
00406 static void wait_stop(Process_T p) {
00407
00408 int max_tries= Run.polltime;
00409
00410 ASSERT(p);
00411
00412 while(max_tries--) {
00413 if(!is_process_running(p))
00414 break;
00415 sleep(1);
00416 }
00417
00418 if(is_process_running(p))
00419 log("%s: Warning process '%s' was not stopped\n", p->name);
00420
00421 }