/*******************************************************************************
 * Copyright (C) 2004-2006 Intel Corp. All rights reserved.
 *
 * Redistribution and use in source and binary forms, with or without
 * modification, are permitted provided that the following conditions are met:
 *
 *  - Redistributions of source code must retain the above copyright notice,
 *    this list of conditions and the following disclaimer.
 *
 *  - Redistributions in binary form must reproduce the above copyright notice,
 *    this list of conditions and the following disclaimer in the documentation
 *    and/or other materials provided with the distribution.
 *
 *  - Neither the name of Intel Corp. nor the names of its
 *    contributors may be used to endorse or promote products derived from this
 *    software without specific prior written permission.
 *
 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS ``AS IS''
 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
 * ARE DISCLAIMED. IN NO EVENT SHALL Intel Corp. OR THE CONTRIBUTORS
 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
 * POSSIBILITY OF SUCH DAMAGE.
 *******************************************************************************/

/**
 * @author Anas Nashif
 * @author Vadim Revyakin
 * @author Liang Hou
 */

#define _GNU_SOURCE
#ifdef HAVE_CONFIG_H
#include "wsman_config.h"
#endif

#include <stdlib.h>
#include <stdio.h>
#include <ctype.h>
#include <string.h>
#include <sys/stat.h>
#include <assert.h>

#ifdef HAVE_UNISTD_H
#include <unistd.h>
#endif

#ifndef WIN32
#include <dlfcn.h>
#endif

#include "u/libu.h"
#include "wsman-xml-api.h"
#include "wsman-soap.h"
#include "wsman-soap-envelope.h"

#include "wsman-xml.h"
#include "wsman-xml-serializer.h"
#include "wsman-dispatcher.h"


#include "shttpd.h"
#include "adapter.h"

#include "wsman-plugins.h"
#include "wsmand-listener.h"
#include "wsmand-daemon.h"
#include "wsman-server.h"
#include "wsman-server-api.h"
#include "wsman-plugins.h"
#ifdef ENABLE_EVENTING_SUPPORT
#include "wsman-cimindication-processor.h"
#endif


#ifdef HAVE_PTHREAD_H
#include <pthread.h>
#endif
#include <sys/socket.h>

/* SSL thread safe */
#include <openssl/crypto.h>
static pthread_mutex_t *lock_cs;
static long *lock_count;

static pthread_mutex_t shttpd_mutex;
static pthread_cond_t shttpd_cond;
int continue_working = 1;
static int (*basic_callback) (char *, char *) = NULL;

struct thread {
    struct thread       *next;
    struct shttpd_ctx   *ctx;
};

static struct thread    *threads;   /* List of worker threads */

typedef struct {
	char *response;
	int length;
	int ind;
} ShttpMessage;

#ifdef SHTTPD_GSS
char * gss_decrypt(struct shttpd_arg *arg, char *data, int len);
int gss_encrypt(struct shttpd_arg *arg, char *input, int inlen, char **output, int *outlen);
#endif

/* SSL thread safe */
void pthreads_locking_callback(int mode, int type, char *file, int line) {
	if (mode & CRYPTO_LOCK) {
		pthread_mutex_lock(&(lock_cs[type]));
		lock_count[type]++;
	}
	else {
		pthread_mutex_unlock(&(lock_cs[type]));
	}
}

unsigned long pthreads_thread_id(void) {
	unsigned long ret;

	ret = (unsigned long)pthread_self();
	return(ret);
}

void thread_setup(void) {
	int i;

	lock_cs = OPENSSL_malloc(CRYPTO_num_locks() * sizeof(pthread_mutex_t));
	lock_count = OPENSSL_malloc(CRYPTO_num_locks() * sizeof(long));
	for (i = 0; i < CRYPTO_num_locks(); i++) {
		lock_count[i] = 0;
		pthread_mutex_init(&(lock_cs[i]), NULL);
	}

	CRYPTO_set_id_callback((unsigned long (*)())pthreads_thread_id);
	CRYPTO_set_locking_callback((void (*)())pthreads_locking_callback);
}

void thread_cleanup(void) {
	int i;

	CRYPTO_set_locking_callback(NULL);
	for (i = 0; i < CRYPTO_num_locks(); i++) {
		pthread_mutex_destroy(&(lock_cs[i]));
	}

	OPENSSL_free(lock_cs);
	OPENSSL_free(lock_count);
}

/* Check HTTP headers */
static
int check_request_content_type(struct shttpd_arg *arg) {
	const char *content_type;
	int status = WSMAN_STATUS_OK;

	content_type = shttpd_get_header(arg, "Content-Type");
	if (content_type && strncmp(content_type,
				    SOAP_CONTENT_TYPE,
				    strlen(SOAP_CONTENT_TYPE)) != 0) {
		status = WSMAN_STATUS_UNSUPPORTED_MEDIA_TYPE;
	}
	return status;
}

static
char *get_request_encoding(struct shttpd_arg *arg) {
	const char *content_type;
	char *p;
	char *encoding = "UTF-8";

	content_type = shttpd_get_header(arg, "Content-Type");
	if(content_type ) {
		if(( p = strstr(content_type, "charset")) != NULL ) {
			p += strlen("charset");
			p++;
			encoding = p;
		}
	}
	return encoding;
}

static
void server_callback(struct shttpd_arg *arg)
{
	char *encoding = "UTF-8";
	const char  *s;
	SoapH soap;
	int k;
	int status = WSMAN_STATUS_OK;
	char *request_uri;

	char *fault_reason = NULL;
	struct state {
        	size_t  cl;     /* Content-Length   */
	        size_t  nread;      /* Number of bytes read */
	 	u_buf_t *request;
	 	char    *response;
		size_t  len;
		int     index;
		int     type;
	} *state;


	/* If the connection was broken prematurely, cleanup */
	if ( (arg->flags & SHTTPD_CONNECTION_ERROR ) && arg->state) {
        	free(arg->state);
		return;
	} else if ((s = shttpd_get_header(arg, "Content-Length")) == NULL) {
        	shttpd_printf(arg, "HTTP/1.0 411 Length Required\n\n");
	        arg->flags |= SHTTPD_END_OF_OUTPUT;
		return;
	} else if (arg->state == NULL) {
        	/* New request. Allocate a state structure */
        	arg->state = state = calloc(1, sizeof(*state));
	        state->cl = strtoul(s, NULL, 10);
		u_buf_create(&(state->request));
	}

	state = arg->state;
	if ( state->response ) {
		goto CONTINUE;
	}

	if (state->nread>0 )
		u_buf_append(state->request, arg->in.buf, arg->in.len);
	else
		u_buf_set(state->request, arg->in.buf, arg->in.len);

	state->nread += arg->in.len;
	arg->in.num_bytes = arg->in.len;
	if (state->nread >= state->cl) {
		debug("Done reading request");
	} else {
		return;
	}
#ifdef SHTTPD_GSS
	const char *ct = shttpd_get_header(arg, "Content-Type");
	char *payload = 0; // used for gss encrypt

	if (ct && !memcmp(ct, "multipart/encrypted", 19)) {
	        // we have a encrypted payload. decrypt it 
        	payload = gss_decrypt(arg, u_buf_ptr(state->request), u_buf_len(state->request));
	}
#endif
	request_uri = (char *)shttpd_get_env(arg, "REQUEST_URI");
	if (strcmp(request_uri, "/wsman") == 0 ) {

		/* Here we must handle the initial request */
		WsmanMessage *wsman_msg = wsman_soap_message_new();
#ifdef SHTTPD_GSS
	        if(payload == 0) {
#endif
			if ( (status = check_request_content_type(arg) ) != WSMAN_STATUS_OK ) {
				wsman_soap_message_destroy(wsman_msg);
				goto DONE;
			}
			encoding = get_request_encoding(arg);

			u_buf_set(wsman_msg->request, u_buf_ptr(state->request), u_buf_len(state->request));
#ifdef SHTTPD_GSS
	        }
		else {
			u_buf_set(wsman_msg->request, payload, strlen(payload));
		}
#endif
	        wsman_msg->charset = u_strdup(encoding);
		soap = (SoapH) arg->user_data;
		wsman_msg->status.fault_code = WSMAN_RC_OK;

		/*
		 * some plugins can use credentials for their own authentication
		 * works only with basic authentication
		 */
		shttpd_get_credentials(arg, &wsman_msg->auth_data.username,
				&wsman_msg->auth_data.password);

		/* Call dispatcher. Real request handling */
		if (status == WSMAN_STATUS_OK) {
			/* dispatch if we didn't find out any error */
			char *idfile = wsmand_options_get_identify_file();
			if (idfile && wsman_check_identify(wsman_msg) == 1) {
				if (u_buf_load(wsman_msg->response, idfile)) {
					dispatch_inbound_call(soap, wsman_msg, NULL);
					status = wsman_msg->http_code;
				}
			} else {
				dispatch_inbound_call(soap, wsman_msg, NULL);
				status = wsman_msg->http_code;
			}
		}
		if (wsman_msg->request) {
#ifdef SHTTPD_GSS
			if (payload) {
				free(payload);
				/* note that payload is stiil set - this is used as a flag later */
			}
			else {
#endif
				u_buf_free(wsman_msg->request);
#ifdef SHTTPD_GSS
			}
#endif
			wsman_msg->request = NULL;
		}

		state->len =  u_buf_len(wsman_msg->response);;
		state->response = u_buf_steal(wsman_msg->response);
		state->index = 0;
		state->type = 0;

		wsman_soap_message_destroy(wsman_msg);
#ifdef ENABLE_EVENTING_SUPPORT
	} else if (strncmp(request_uri, DEFAULT_CIMINDICATION_PATH, strlen(DEFAULT_CIMINDICATION_PATH)) == 0 ) {
		status = CIMXML_STATUS_OK;
		int cim_error_code = 0;
		char *cim_error = NULL;
		char *fault_reason = NULL;
		char *uuid = NULL, *tmp, *end;
		cimxml_context *cntx = NULL;
		SoapH soap = NULL;
		CimxmlMessage *cimxml_msg = cimxml_message_new();
		tmp = (char *)shttpd_get_env(arg, "REQUEST_URI");
		if (tmp && ( end = strrchr(tmp, '/')) != NULL ) {
			uuid = &end[1];
		}
	        encoding = get_request_encoding(arg);
		cimxml_msg->charset = u_strdup(encoding);
		const char *cimexport = shttpd_get_header(arg, "CIMExport");
		const char *cimexportmethod = shttpd_get_header(arg, "CIMExportMethod");
		if ( cimexportmethod && cimexport ) {
			if(strncmp(cimexport, "MethodRequest", strlen("MethodRequest")) ||
					strncmp(cimexportmethod, "ExportIndication", strlen("ExportIndication"))) {
			}
		} else {
			status = WSMAN_STATUS_FORBIDDEN;
			cim_error_code = CIMXML_STATUS_UNSUPPORTED_OPERATION;
			cim_error = "unsupported-operation";
			goto DONE;
		}
		soap = (SoapH) arg->user_data;
		u_buf_set(cimxml_msg->request, u_buf_ptr(state->request), u_buf_len(state->request));
		cntx = u_malloc(sizeof(cimxml_context));
		cntx->soap = soap;
		cntx->uuid = uuid;
		CIM_Indication_call(cntx, cimxml_msg, NULL);
		status = cimxml_msg->http_code;
		cim_error_code = cimxml_msg->status.code;
		cim_error = cimxml_msg->status.fault_msg;
		if (cim_error) {
			shttpd_printf(arg, "HTTP/1.1 %d %s\r\n", status, fault_reason);
			shttpd_printf(arg, "CIMError:%d:%s\r\n", cim_error_code, cim_error);
			cimxml_message_destroy(cimxml_msg);
			goto CONTINUE;
		}
		state->len =  u_buf_len(cimxml_msg->response);;
		state->response = u_buf_steal(cimxml_msg->response);
		state->index = 0;
		state->type = 1;
		cimxml_message_destroy(cimxml_msg);
#endif

	} else if (strcmp(request_uri, ANON_IDENTIFY_PATH) == 0 ) {
		char *idfile = wsmand_options_get_anon_identify_file();
		u_buf_t *id;
		u_buf_create(&id);
		if (idfile && u_buf_load(id, idfile) == 0 ) {
			state->len =  u_buf_len(id);;
			state->response = u_buf_steal(id);
			state->index = 0;
			u_buf_free(id);
		} else {
			shttpd_printf(arg, "HTTP/1.0 404 Not foundn\n");
			arg->flags |= SHTTPD_END_OF_OUTPUT;
			u_buf_free(id);
			return;
		}
	} else {
		shttpd_printf(arg, "HTTP/1.0 404 Not foundn\n");
		arg->flags |= SHTTPD_END_OF_OUTPUT;
		return;
	}

DONE:

	if (fault_reason == NULL) {
		fault_reason = shttpd_reason_phrase(status);
	}
	debug("Response status=%d (%s)", status, fault_reason);

	/*
	 * Here we begin to create the http response.
	 * Create the headers at first.
	 */

	shttpd_printf(arg, "HTTP/1.1 %d %s\r\n", status, fault_reason);
	shttpd_printf(arg, "Server: %s/%s\r\n", PACKAGE_NAME, PACKAGE_VERSION);
#ifdef SHTTPD_GSS
	if(payload) {
		// we had an encrypted message so now we have to encypt the reply
		char *enc;
		int enclen;
		gss_encrypt(arg, state->response, state->len, &enc, &enclen);
		u_free(state->response);
		state->response = enc;
		state->len = enclen;
		payload = 0; // and reset the indicator so that if we send in packates we dont do this again
		shttpd_printf(arg, "Content-Type: multipart/encrypted;protocol=\"application/HTTP-Kerberos-session-encrypted\";boundary=\"Encrypted Boundary\"\r\n");
		shttpd_printf(arg, "Content-Length: %d\r\n", state->len);
	}
	else {
#endif
		if (state->type == 1) { /* eventing */
			shttpd_printf(arg, "Content-Type: application/xml; charset=\"utf-8\"\r\n");
			shttpd_printf(arg, "CIMExport: MethodResponse\r\n");
		} else {
			shttpd_printf(arg, "Content-Type: application/soap+xml;charset=%s\r\n", encoding);
		}
    		shttpd_printf(arg, "Content-Length: %d\r\n", state->len);
#ifdef SHTTPD_GSS
	}
#endif
	shttpd_printf(arg,"Connection: Close\r\n");
  
        /* separate header from message-body */
	shttpd_printf(arg, "\r\n");

	/* add response body to output buffer */
CONTINUE:


	k = arg->out.len - arg->out.num_bytes;
	if (k <= state->len - state->index) {
		 memcpy(arg->out.buf + arg->out.num_bytes, state->response + state->index, k );
		 state->index += k ;
		 arg->out.num_bytes += k;
		 return;
	}
	else {
	         int l = state->len - state->index;
		 memcpy(arg->out.buf + arg->out.num_bytes, state->response + state->index, l);
		 state->index += l ;
		 arg->out.num_bytes += l;
	}

	u_buf_free(state->request);
	u_free(state->response);
	u_free(state);
	arg->flags |= SHTTPD_END_OF_OUTPUT;
	return;
}

static void listener_shutdown_handler(void *p)
{
	int *a = (int *) p;
	debug("listener_shutdown_handler started");
	*a = 0;
}

static void protect_uri(struct shttpd_ctx *ctx, char *uri)
{
	if (wsmand_options_get_digest_password_file()) {
		shttpd_protect_uri(ctx, uri,
                   wsmand_options_get_digest_password_file(),NULL, 1);
		debug("Using Digest Authorization for %s:", uri);
	}
	if (basic_callback) {
		shttpd_protect_uri(ctx, uri, wsmand_options_get_basic_password_file(),
						basic_callback, 0);
		debug("Using Basic Authorization %s for %s",
		      wsmand_option_get_basic_authenticator()?
		      wsmand_option_get_basic_authenticator() :
		      wsmand_default_basic_authenticator(), uri);
	}
}

static struct shttpd_ctx *create_shttpd_context(SoapH soap)
{
	struct shttpd_ctx *ctx;
	if (wsmand_options_get_use_ssl()) {
		message("ssl certificate: %s", wsmand_options_get_ssl_cert_file());
		message("Using SSL");
		ctx = shttpd_init(NULL,
				  "ssl_certificate",
				  wsmand_options_get_ssl_cert_file(),
				  "auth_realm",
				  AUTHENTICATION_REALM,
				  NULL);
	} else {
		ctx = shttpd_init(NULL,
				  "auth_realm", AUTHENTICATION_REALM,
				   NULL);
	}
	if (ctx == NULL) {
		return NULL;
	}
	shttpd_register_uri(ctx, wsmand_options_get_service_path(),
			    server_callback, (void *) soap);
	shttpd_register_uri(ctx, ANON_IDENTIFY_PATH,
			    server_callback, (void *) soap);

#ifdef ENABLE_EVENTING_SUPPORT
	message("Registered CIM Indication Listener: %s", DEFAULT_CIMINDICATION_PATH "/*");
	shttpd_register_uri(ctx, DEFAULT_CIMINDICATION_PATH "/*", server_callback,(void *)soap);
	protect_uri( ctx, DEFAULT_CIMINDICATION_PATH );
#endif

	protect_uri( ctx, wsmand_options_get_service_path());

	return ctx;
}


static int initialize_basic_authenticator(void)
{
	char *auth;
	char *arg;
	void *hnd;
	int (*init) (char *);
	char *name;
	int should_return = 0;
	int res = 0;

	if (wsmand_options_get_basic_password_file() != NULL) {
		if ((wsmand_option_get_basic_authenticator() &&
		     (strcmp(wsmand_default_basic_authenticator(),
			     wsmand_option_get_basic_authenticator()))) ||
		    wsmand_option_get_basic_authenticator_arg()) {
			fprintf(stderr,
				"basic authentication is ambigious in config file\n");
			return 1;
		}
		auth = wsmand_default_basic_authenticator();
		arg = wsmand_options_get_basic_password_file();
	} else {
		auth = wsmand_option_get_basic_authenticator();
		arg = wsmand_option_get_basic_authenticator_arg();
	}

	if (auth == NULL) {
		/* No basic authenticationame */
		return 0;
	}

	if (auth[0] == '/') {
		name = auth;
	} else {
		name = u_strdup_printf("%s/%s", PACKAGE_AUTH_DIR, auth);
		should_return = 1;
	}

	hnd = dlopen(name, RTLD_LAZY | RTLD_GLOBAL);
	if (hnd == NULL) {
		fprintf(stderr, "Could not dlopen %s\n", name);
		res = 1;
		goto DONE;
	}
	basic_callback = dlsym(hnd, "authorize");
	if (basic_callback == NULL) {
		fprintf(stderr, "Could not resolve authorize() in %s\n",
			name);
		res = 1;
		goto DONE;
	}

	init = dlsym(hnd, "initialize");
	if (init != NULL) {
		res = init(arg);
	}
      DONE:
	if (should_return) {
		u_free(name);
	}
	return res;
}


static int get_server_auth(void) {
	if (initialize_basic_authenticator()) {
		return 0;
	}

	if (wsmand_options_get_digest_password_file()) {
		message("Using Digest Authorization");
	}
	if (basic_callback) {
		message("Using Basic Authorization %s",
			wsmand_option_get_basic_authenticator()?
			wsmand_option_get_basic_authenticator() :
			wsmand_default_basic_authenticator());
	}

	if ((wsmand_options_get_digest_password_file() == NULL) &&
		    (basic_callback == NULL)) {
		error("Server does not work without authentication");
		return 0;
	}
	return 1;
}

static int get_server_port(void) {
	int port = 0;
	int use_ssl = wsmand_options_get_use_ssl();
	if (use_ssl) {
		message("Using SSL");
		if (wsmand_options_get_ssl_cert_file() &&
		    wsmand_options_get_ssl_key_file() &&
		    (wsmand_options_get_server_ssl_port() > 0)) {
			port = wsmand_options_get_server_ssl_port();
		} else {
			error("Not enough data to use SSL port");
			return 0;
		}
	} else {
		port = wsmand_options_get_server_port();
	}
	return port;
}


static int wsman_setup_thread(pthread_attr_t *pattrs) {
	int r;
	int ret = 0;
	if ((r = pthread_cond_init(&shttpd_cond, NULL)) != 0) {
		debug("pthread_cond_init failed = %d", r);
		return ret;
	}
	if ((r = pthread_mutex_init(&shttpd_mutex, NULL)) != 0) {
		debug("pthread_mutex_init failed = %d", r);
		return ret;
	}

	if ((r = pthread_attr_init(pattrs)) != 0) {
		debug("pthread_attr_init failed = %d", r);
		return ret;
	}

	if ((r = pthread_attr_setdetachstate(pattrs, PTHREAD_CREATE_DETACHED)) != 0) {
		debug("pthread_attr_setdetachstate = %d", r);
		return ret;
	}
	return 1;
        size_t thread_stack_size = wsmand_options_get_thread_stack_size();
        if(thread_stack_size){
                if(( r = pthread_attr_setstacksize(pattrs, thread_stack_size)) !=0) {
                        debug("pthread_attr_setstacksize failed = %d", r);
                        return ret;
                }
        }
}

static void *thread_function(void *param)
{
    struct thread *thread = param;

    for (;;)
        shttpd_poll(thread->ctx, 1000);

    return NULL;
}


static struct thread *
spawn_new_thread(pthread_attr_t pattrs, SoapH soap)
{
    struct shttpd_ctx   *ctx;
    struct thread       *thread;
    pthread_t           tid;
	debug("spawning new thread");

    thread  = malloc(sizeof(*thread));
    ctx = create_shttpd_context(soap);

    assert(ctx != NULL);
    assert(thread != NULL);

    thread->ctx = ctx;
    thread->next    = threads;
    threads     = thread;

	pthread_create(&tid, &pattrs, thread_function, thread);

    return (thread);
}


static struct thread *
find_not_busy_thread(int *num_threads, int max_connections_per_thread)
{
    struct thread   *thread;

    for (thread = threads, *num_threads=0; thread != NULL; thread = thread->next) {
	debug("Active sockets: %d, Thread Number: %d", shttpd_active(thread->ctx), *num_threads );
        (*num_threads)++;
        if (shttpd_active(thread->ctx) < max_connections_per_thread)
            return (thread);
	}

    return (NULL);
}


WsManListenerH *wsmand_start_server(dictionary * ini)
{
	int lsn, port, sock;
	struct thread       *thread;
	pthread_t tid;
#ifdef ENABLE_EVENTING_SUPPORT
	pthread_t notificationManager_id;
#endif
	pthread_attr_t pattrs;
	int use_ssl = wsmand_options_get_use_ssl();
	struct shttpd_ctx   *httpd_ctx;

	WsManListenerH *listener = wsman_dispatch_list_new();
	listener->config = ini;
	WsContextH cntx = wsman_init_plugins(listener);
        int num_threads = 0;
        int max_threads = wsmand_options_get_max_threads();
        int max_connections_per_thread = wsmand_options_get_max_connections_per_thread();
        if (max_threads && !max_connections_per_thread) {
                error("max_threads: %d and max_connections_per_thread : %d", max_threads, max_connections_per_thread);
                return listener;
        }

	if (cntx == NULL) {
		return listener;
	}
#ifdef ENABLE_EVENTING_SUPPORT
	wsman_event_init(cntx->soap);
#endif

#ifndef HAVE_SSL
	if (use_ssl) {
		error("Server configured without SSL support");
		return listener;
	}
#endif
	SoapH soap = ws_context_get_runtime(cntx);
	ws_set_context_enumIdleTimeout(cntx,wsmand_options_get_enumIdleTimeout());


	if ((port = get_server_port()) == 0  )
		return listener;
#ifdef ENABLE_IPV6
	if (wsmand_options_get_use_ipv6()) {
		message("     Working on IPv6 port %d", port);
	}
	else {
#endif
		message("     Working on IPv4 port %d", port);
#ifdef ENABLE_IPV6
	}
#endif
	if (!get_server_auth())
		return listener;

	wsmand_shutdown_add_handler(listener_shutdown_handler,
				    &continue_working);

	httpd_ctx = create_shttpd_context(soap);

	lsn = shttpd_listen(httpd_ctx, port, use_ssl);

	if (wsman_setup_thread(&pattrs) == 0 )
		return listener;

	/* SSL thread safe */
	thread_setup();

	pthread_create(&tid, &pattrs, wsman_server_auxiliary_loop_thread, cntx);

#ifdef ENABLE_EVENTING_SUPPORT
	pthread_create(&notificationManager_id, &pattrs, wsman_notification_manager, cntx);
#endif

	while (continue_working) {
		if ((sock = shttpd_accept(lsn, 1000)) == -1) {
			continue;
		}
		debug("Sock %d accepted", sock);
                if ((thread = find_not_busy_thread(&num_threads, max_connections_per_thread)) == NULL){
                        if(max_threads){
                                if(num_threads < max_threads){
                                        thread = spawn_new_thread(pattrs, soap);
                                }
                                else{
                                        continue;
                                }
                        }
                        else{
                                thread = spawn_new_thread(pattrs, soap);
                        }
		}
                shttpd_add_socket(thread->ctx, sock, use_ssl);
        }

	/* SSL thread safe */
	thread_cleanup();

        return listener;
}
