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 #include <stdlib.h>
00024 #include <errno.h>
00025
00026 #ifdef HAVE_SYS_TYPES_H
00027 #include <sys/types.h>
00028 #endif
00029
00030 #include <sys/socket.h>
00031 #include <time.h>
00032
00033 #ifdef HAVE_NETDB_H
00034 #include <netdb.h>
00035 #endif
00036
00037 #ifdef HAVE_UNISTD_H
00038 #include <unistd.h>
00039 #endif
00040
00041 #ifdef HAVE_STRING_H
00042 #include <string.h>
00043 #endif
00044
00045 #ifdef HAVE_NETINET_IN_H
00046 #include <netinet/in.h>
00047 #endif
00048
00049 #ifdef HAVE_ARPA_INET_H
00050 #include <arpa/inet.h>
00051 #endif
00052
00053 #include "http_utils.h"
00054 #include "engine.h"
00055
00056 #define HOST 1
00057 #define WRAPPER 2
00058 #define INETADDR 3
00059
00060
00061 static int myServerSocket= 0;
00062 ssl_server_connection * mySSLServerConnection= NULL;
00063 static volatile int stopped= FALSE;
00064 static HostsAllow hostlist= NULL;
00065 static pthread_mutex_t hostlist_mutex= PTHREAD_MUTEX_INITIALIZER;
00066
00067
00068 static void initialize_service();
00069 static void check_Impl();
00070 static int authenticate(RequestWrapper);
00071 static int is_host_allow(char *);
00072 static RequestWrapper socket_producer(int);
00073 static RequestWrapper create_wrapper(struct in_addr, int);
00074 static void destroy_host_allow(HostsAllow);
00075
00102
00103
00104
00111 void start_httpd(int port, int backlog, char *bindAddr) {
00112
00113 RequestWrapper W;
00114
00115 stopped= FALSE;
00116
00117
00118 if ( (myServerSocket= create_server_socket(port, backlog, bindAddr)) < 0 ) {
00119
00120 error("http server: Could not create a server socket at port %d -- %s\n",
00121 port, STRERROR);
00122
00123 error("monit HTTP server not available\n");
00124
00125 } else {
00126
00127 initialize_service();
00128
00129 if ( Run.httpdssl ) {
00130
00131 mySSLServerConnection= init_ssl_server( Run.httpsslpem,
00132 Run.httpsslclientpem );
00133
00134 if ( mySSLServerConnection == NULL ) {
00135
00136 error("http server: Could not initilize SSL engine\n");
00137
00138 error("monit HTTP server not available\n");
00139
00140 return;
00141 }
00142
00143 #ifdef HAVE_OPENSSL
00144 mySSLServerConnection->server_socket= myServerSocket;
00145 #endif
00146 }
00147
00148 while( !stopped ) {
00149
00150 if ( NULL == (W= socket_producer(myServerSocket)) ) {
00151
00152 continue;
00153
00154 }
00155
00156 if ( Run.httpdssl ) {
00157
00158 if ( NULL == (W->ssl=
00159 insert_accepted_ssl_socket(mySSLServerConnection) )) {
00160
00161 error("http server: Cannot create SSL connection -- %s\n",
00162 STRERROR);
00163 destroy_wrapper(W);
00164
00165 continue;
00166
00167 }
00168
00169 if (! embed_accepted_ssl_socket(W->ssl, W->socket)) {
00170
00171 error("http server: Cannot establish SSL connection\n");
00172 destroy_wrapper(W);
00173
00174 continue;
00175
00176 }
00177
00178 }
00179
00180 if ( (!W->status) || (!authenticate(W)) ) {
00181
00182 destroy_wrapper(W);
00183
00184 continue;
00185
00186 }
00187
00188 if ( !Run.httpdssl ) {
00189
00190 if ( !check_socket(W->socket) ) {
00191
00192 error("http server: Client socket not ready -- %s\n", STRERROR);
00193 destroy_wrapper(W);
00194
00195 continue;
00196
00197 }
00198
00199 }
00200
00201 http_processor(W);
00202
00203 }
00204
00205 }
00206
00207 }
00208
00209
00213 void stop_httpd() {
00214
00215 stopped= TRUE;
00216 close_socket(myServerSocket);
00217 delete_ssl_server_socket(mySSLServerConnection);
00218
00219 }
00220
00221
00222
00223
00224
00230 int add_host_allow(char *name) {
00231
00232 struct hostent *hp;
00233
00234 if ( ! (hp= gethostbyname(name)) ) {
00235
00236 return FALSE;
00237
00238 } else {
00239
00240 HostsAllow h= NEW(h);
00241
00242 while(*hp->h_addr_list) {
00243
00244 h->name= xstrdup( inet_ntoa( *(struct in_addr *) *hp->h_addr_list++) );
00245
00246 LOCK(hostlist_mutex)
00247
00248 if ( hostlist ) {
00249
00250 HostsAllow p, n;
00251
00252 for ( n= p= hostlist; p; n= p, p= p->next) {
00253
00254 if ( !strcasecmp(p->name, name) ) {
00255
00256 destroy_host_allow(h);
00257 goto done;
00258
00259 }
00260
00261 }
00262
00263 n->next= h;
00264
00265 } else {
00266
00267 hostlist= h;
00268
00269 }
00270
00271 done:
00272 END_LOCK;
00273
00274 }
00275
00276 }
00277
00278 return TRUE;
00279
00280 }
00281
00282
00287 int has_hosts_allow() {
00288
00289 int rv;
00290
00291 LOCK(hostlist_mutex)
00292 rv= (hostlist != NULL );
00293 END_LOCK;
00294
00295 return rv;
00296
00297 }
00298
00299
00303 void destroy_hosts_allow() {
00304
00305 if ( has_hosts_allow() ) {
00306
00307 LOCK(hostlist_mutex)
00308 destroy_host_allow(hostlist);
00309 hostlist= NULL;
00310 END_LOCK;
00311
00312 }
00313
00314 }
00315
00316
00317
00318
00319
00326 static void initialize_service() {
00327
00328 init_service();
00329 check_Impl();
00330
00331 }
00332
00333
00337 static void check_Impl() {
00338
00339 if ( (Impl.doGet == 0) || (Impl.doPost == 0) ) {
00340
00341 error("http server: Service Methods not implemented\n");
00342 _exit(1);
00343
00344 }
00345
00346 }
00347
00348
00355 static int authenticate(RequestWrapper w) {
00356
00357 if ( is_host_allow(w->inetaddr->remote_host) ) {
00358
00359 return TRUE;
00360
00361 }
00362
00363 if ( ! has_hosts_allow() && Run.Auth.defined ) {
00364
00365 return TRUE;
00366
00367 }
00368
00369 return FALSE;
00370
00371 }
00372
00373
00374
00379 static int is_host_allow(char *name) {
00380
00381 HostsAllow p;
00382 int rv= FALSE;
00383
00384 LOCK(hostlist_mutex)
00385
00386 for ( p= hostlist; p; p= p->next) {
00387
00388 if ( !strncasecmp(p->name, name, STRLEN) ) {
00389
00390 rv= TRUE;
00391 break;
00392
00393 }
00394
00395 }
00396
00397 END_LOCK;
00398
00399 return rv;
00400
00401 }
00402
00403
00404
00405
00406
00412 static RequestWrapper socket_producer(int server) {
00413
00414 int client;
00415 int len= sizeof(struct sockaddr_in);
00416 struct sockaddr_in in;
00417
00418 again:
00419 errno= 0;
00420 if ( (client= accept(server, (struct sockaddr*)&in, &len)) < 0) {
00421
00422 if ( stopped ) {
00423
00424 log("http server: service stopped\n");
00425
00426 } else if ( errno == EINTR ) {
00427
00428 goto again;
00429
00430 } else {
00431
00432 error("http server: cannot accept connection -- %s\n", STRERROR);
00433
00434 }
00435
00436 return NULL;
00437
00438 }
00439
00440 return create_wrapper(in.sin_addr, client);
00441
00442 }
00443
00444
00452 static RequestWrapper create_wrapper(struct in_addr iaddr, int client) {
00453
00454 RequestWrapper w= NEW(w);
00455 InetAddress i= NEW(i);
00456
00457 i->remote_host= xstrdup( inet_ntoa(iaddr) );
00458 i->local_host= get_localhostname();
00459 w->inetaddr= i;
00460 w->socket= client;
00461 w->status= TRUE;
00462
00463 return (w);
00464
00465 }
00466
00467
00468
00469
00470
00474 static void destroy_host_allow(HostsAllow p) {
00475
00476 HostsAllow a= p;
00477
00478 if ( a->next ) {
00479
00480 destroy_host_allow(a->next);
00481
00482 }
00483
00484 free(a->name);
00485 free(a);
00486
00487 }
00488