/*******************************************************************************
 * 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
 */

#ifdef HAVE_CONFIG_H
#include <wsman_config.h>
#endif


#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#ifdef HAVE_UNISTD_H
#include <unistd.h>
#endif

#include "u/libu.h"
#include "wsman-client-transport.h"
#include "wsman-soap.h"
#include "wsman-client.h"

static char *auth_methods[] = {
  _WS_NO_AUTH,
  _WS_BASIC_AUTH,
  _WS_DIGEST_AUTH,
  _WS_PASS_AUTH,
  _WS_NTLM_AUTH,
  _WS_GSSNEGOTIATE_AUTH,
	NULL,
};


extern void wsmc_handler(WsManClient * cl, WsXmlDocH rqstDoc,
				 void *user_data);

#ifdef BENCHMARK
static long long transfer_time = 0;
#endif

int wsman_send_request(WsManClient * cl, WsXmlDocH request)
{
        int ret = 0;
#ifdef BENCHMARK
	struct timeval tv0, tv1;
	long long t0, t1;
#endif

	if (wsmc_lock(cl) != 0 ) {
		error("Client busy");
		return 1;
	}
	wsmc_reinit_conn(cl);

#ifdef BENCHMARK
	gettimeofday(&tv0, NULL);
#endif

	wsmc_handler(cl, request, NULL);
        if (cl->last_error != WS_LASTERR_OK) {
          warning("Couldn't send request to client: %s\n", cl->fault_string);
          ret = 1;
        }
#ifdef BENCHMARK
	gettimeofday(&tv1, NULL);
	t0 = tv0.tv_sec * 10000000 + tv0.tv_usec;
	t1 = tv1.tv_sec * 10000000 + tv1.tv_usec;
	transfer_time += t1 - t0;
#endif
	wsmc_unlock(cl);
	return ret;
}

#ifdef BENCHMARK
long long get_transfer_time()
{
	long long l = transfer_time;
	transfer_time = 0;
	return l;
}
#endif


const char *wsmc_transport_get_auth_name(wsman_auth_type_t auth)
{
	switch (auth) {
	case WS_NO_AUTH:
		return _WS_NO_AUTH;
	case WS_BASIC_AUTH:
		return _WS_BASIC_AUTH;
	case WS_DIGEST_AUTH:
		return _WS_DIGEST_AUTH;
	case WS_PASS_AUTH:
		return _WS_PASS_AUTH;
	case WS_NTLM_AUTH:
		return _WS_NTLM_AUTH;
	case WS_GSSNEGOTIATE_AUTH:
		return _WS_GSSNEGOTIATE_AUTH;
	default:;
	}
	return "Unknown";
}

void wsmc_transport_set_auth_request_func(WsManClient * cl,
				  wsman_auth_request_func_t f)
{
	cl->authentication.auth_request_func = f;
}


void wsman_transport_set_agent(WsManClient * cl, const char *arg)
{
	u_free(cl->user_agent);
	cl->user_agent = arg ? u_strdup( arg ) : NULL;
}

char *wsman_transport_get_agent(WsManClient * cl)
{
	if (cl->user_agent)
		return u_strdup(cl->user_agent);
	else
		return DEFAULT_USER_AGENT;
}


void wsman_transport_set_proxy(WsManClient * cl, const char *arg)
{
	u_free(cl->proxy_data.proxy);
	cl->proxy_data.proxy = arg ? u_strdup( arg ) : NULL;
}

char *wsman_transport_get_proxy(WsManClient *cl)
{
	return cl->proxy_data.proxy ? u_strdup( cl->proxy_data.proxy ) : NULL;
}

void wsman_transport_set_userName(WsManClient * cl, const char *arg)
{
	u_free(cl->data.user);
	cl->data.user = arg ? u_strdup(arg) : NULL;
}

char *wsman_transport_get_userName(WsManClient * cl)
{
	return cl->data.user ? u_strdup(cl->data.user) : NULL;
}

void wsman_transport_set_password(WsManClient * cl, const char *arg)
{
	u_free(cl->data.pwd);
	cl->data.pwd = arg ? u_strdup(arg) : NULL;
}

char *wsman_transport_get_password(WsManClient * cl)
{
	return cl->data.pwd ? u_strdup(cl->data.pwd) : NULL;
}

void wsman_transport_set_proxyauth(WsManClient * cl, const char *arg)
{
	u_free(cl->proxy_data.proxy_auth);
	cl->proxy_data.proxy_auth = arg ? u_strdup( arg ) : NULL;
}

char *wsman_transport_get_proxyauth(WsManClient *cl)
{
	return cl->proxy_data.proxy_auth ? u_strdup( cl->proxy_data.proxy_auth ) : NULL;
}


unsigned long wsman_transport_get_timeout(WsManClient * cl)
{
	return cl->transport_timeout;
}

void wsman_transport_set_timeout(WsManClient * cl, unsigned long arg)
{
	cl->transport_timeout = arg;
}


char *wsman_transport_get_auth_method(WsManClient * cl)
{
  return cl->authentication.method ? u_strdup(cl->authentication.method) : NULL;
}

void wsman_transport_set_auth_method(WsManClient * cl, const char *arg)
{
	u_free(cl->authentication.method);
	cl->authentication.method = arg ? u_strdup( arg ) : NULL;
}

int wsman_is_auth_method(WsManClient * cl, int method)
{
	if (cl->authentication.method == NULL) {
		return 1;
	}
	if (method >= WS_MAX_AUTH) {
		return 0;
	}
	return (!strncasecmp
		(cl->authentication.method, auth_methods[method],
		 strlen(cl->authentication.method)));
}

wsman_auth_type_t wsmc_transport_get_auth_value(WsManClient * cl)
{
	char *m = cl->authentication.method;
	wsman_auth_type_t i;

	if (m == NULL) {
		return WS_NO_AUTH;
	}
	for (i = 0; auth_methods[i] != NULL; i++) {
		if (!strcasecmp(m, auth_methods[i])) {
			return i;
		}
	}
	return WS_MAX_AUTH;
}


void wsman_transport_set_verify_peer(WsManClient * cl, unsigned int arg)
{
	cl->authentication.verify_peer = arg;
}

unsigned int wsman_transport_get_verify_peer(WsManClient *cl)
{
	return cl->authentication.verify_peer;
}


void wsman_transport_set_verify_host(WsManClient * cl, unsigned int arg)
{
	cl->authentication.verify_host = arg;
}

unsigned int wsman_transport_get_verify_host(WsManClient *cl)
{
	return cl->authentication.verify_host;
}

void wsman_transport_set_crlcheck(WsManClient * cl, unsigned int arg)
{
	cl->authentication.crl_check = arg;
}

unsigned int wsman_transport_get_crlcheck(WsManClient * cl)
{
        return cl->authentication.crl_check;
}

#ifndef _WIN32
void wsman_transport_set_crlfile(WsManClient * cl, const char *arg)
{
        u_free(cl->authentication.crl_file);
        cl->authentication.crl_file = arg ? u_strdup( arg ) : NULL;
}

char *wsman_transport_get_crlfile(WsManClient *cl)
{
  return cl->authentication.crl_file ? u_strdup(cl->authentication.crl_file) : NULL; 
}
#endif



void wsman_transport_set_cainfo(WsManClient * cl, const char *arg)
{
	u_free(cl->authentication.cainfo);
	cl->authentication.cainfo = arg ? u_strdup( arg ) : NULL;
}

char *wsman_transport_get_cainfo(WsManClient *cl)
{
	return cl->authentication.cainfo ? u_strdup( cl->authentication.cainfo ) : NULL;
}

static int hexadecimal2raw(const char *str, unsigned char *dest, int len) {
        int i = 0;
        unsigned char v1 =0 , v2 = 0;
        while(*str != 0 && *(str+1) != 0 && i < len) {
                if(*str <= '9' && *str >= '0')
                        v1 = *str - '0';
                else if(*str <= 'f' && *str >= 'a')
                        v1 = *str - 'a' + 10;
                else if(*str <= 'F' && *str >= 'A')
                        v1 = *str - 'A' + 10;
                v1 <<= 4;
                str++;
                if(*str <= '9' && *str >= '0')
                        v2 = *str - '0';
                else if(*str <= 'f' && *str >= 'a')
                        v2 = *str - 'a' + 10;
                else if(*str <= 'F' && *str >= 'A')
                        v2 = *str - 'A' + 10;
                str++;
                dest[i] = v1 + v2;
                i++;
        }
        return i;
}

static char * raw2hexadecimal(unsigned char *dest, int len)
{
        int i = 0;
        char v;
        char * str = calloc(1, len*2+1);
        char * p = str;
        if(str == NULL) return str;
        while(i < len) {
                v = (dest[i] & 0xf0) >> 4;
                if(v <= 9)
                        *str = '0' + v;
                else
                        *str = 'a' + v - 10;
                str++;
                v = dest[i] & 0x0f;
                if(v <= 9)
                        *str = '0' + v;
                else
                        *str = 'a' + v - 10;
                str++;
                i++;
        }
        return p;
}


void wsman_transport_set_certhumbprint(WsManClient *cl, const char *arg)
{
	if(arg == NULL)
		return;
	hexadecimal2raw(arg, cl->authentication.certificatethumbprint, 20);
}

char *wsman_transport_get_certhumbprint(WsManClient *cl)
{
	return raw2hexadecimal(cl->authentication.certificatethumbprint, 20);
}

void wsman_transport_set_capath(WsManClient *cl, const char *arg)
{
	u_free(cl->authentication.capath);
	cl->authentication.capath = arg ? u_strdup( arg ) : NULL;
}

char *wsman_transport_get_capath(WsManClient *cl)
{
	return cl->authentication.capath ? u_strdup( cl->authentication.capath ) : NULL;
}


void wsman_transport_set_caoid(WsManClient *cl, const char *arg)
{
	u_free(cl->authentication.caoid);
	cl->authentication.caoid = arg ? u_strdup( arg ) : NULL;
}

char *wsman_transport_get_caoid(WsManClient *cl)
{
	return cl->authentication.caoid ? u_strdup( cl->authentication.caoid ) : NULL;
}


#ifdef _WIN32
void wsman_transport_set_calocal(WsManClient *cl, BOOL local)
{
	cl->authentication.calocal = local;
}

BOOL wsman_transport_get_calocal(WsManClient *cl)
{
	return cl->authentication.calocal;
}
#endif

char *wsman_transport_get_proxy_username(WsManClient *cl)
{
  return cl->proxy_data.proxy_username ? u_strdup(cl->proxy_data.proxy_username) : NULL;
}

void wsman_transport_set_proxy_username(WsManClient *cl, const char *proxy_username )
{
  u_free(cl->proxy_data.proxy_username);
  cl->proxy_data.proxy_username = proxy_username ? u_strdup(proxy_username) : NULL;
}

char *wsman_transport_get_proxy_password(WsManClient *cl)
{
  return cl->proxy_data.proxy_password ? u_strdup(cl->proxy_data.proxy_password) : NULL;
}

void wsman_transport_set_proxy_password(WsManClient *cl, const char *proxy_password )
{
  u_free(cl->proxy_data.proxy_password);
  cl->proxy_data.proxy_password = proxy_password ? u_strdup(proxy_password) : NULL;
}



void wsman_transport_set_cert(WsManClient * cl, const char *arg)
{
	u_free(cl->authentication.sslcert);
	cl->authentication.sslcert = arg ? u_strdup( arg ) : NULL;
}

char *wsman_transport_get_cert(WsManClient *cl)
{
	return cl->authentication.sslcert ? u_strdup( cl->authentication.sslcert ) : NULL;
}


void wsman_transport_set_key(WsManClient *cl, const char *key)
{
	u_free(cl->authentication.sslkey);
	cl->authentication.sslkey = key ? u_strdup( key ) : NULL;
}

char *wsman_transport_get_key(WsManClient *cl)
{
	return cl->authentication.sslkey ? u_strdup( cl->authentication.sslkey ) : NULL;
}


char *wsman_transport_get_last_error_string(WS_LASTERR_Code err)
{
	switch (err) {
	case WS_LASTERR_OK:
		return "Everything OK";
	case WS_LASTERR_FAILED_INIT:
		return "Transport initialization failed";
	case WS_LASTERR_UNSUPPORTED_PROTOCOL:
		return "Unsupported protocol";
	case WS_LASTERR_URL_MALFORMAT:
		return "URL malformat";
	case WS_LASTERR_COULDNT_RESOLVE_PROXY:
		return "Could not resolve proxy";
	case WS_LASTERR_COULDNT_RESOLVE_HOST:
		return "Could not resolve host";
	case WS_LASTERR_COULDNT_CONNECT:
		return "Could not connect";
	case WS_LASTERR_HTTP_RETURNED_ERROR:
		return "HTTP returned error";
	case WS_LASTERR_WRITE_ERROR:
		return "Write error";
	case WS_LASTERR_READ_ERROR:
		return "Read error";
	case WS_LASTERR_OUT_OF_MEMORY:
		return "Could not alloc memory";
	case WS_LASTERR_OPERATION_TIMEOUTED:
		return "Operation timeout reached";
	case WS_LASTERR_HTTP_POST_ERROR:
		return "HTTP POST error";
	case WS_LASTERR_BAD_DOWNLOAD_RESUME:
		return "Could not resume download";
	case WS_LASTERR_TOO_MANY_REDIRECTS:
		return "Catch endless re-direct loop";
	case WS_LASTERR_SSL_CONNECT_ERROR:
		return "SSL connection error";
	case WS_LASTERR_SSL_PEER_CERTIFICATE:
		return "Peer's certificate wasn't OK";
	case WS_LASTERR_SSL_ENGINE_NOTFOUND:
		return "SSL crypto engine not found";
	case WS_LASTERR_SSL_ENGINE_SETFAILED:
		return "Can't set SSL crypto engine default";
	case WS_LASTERR_SSL_CERTPROBLEM:
		return "Problem with the local certificate";
	case WS_LASTERR_SSL_CACERT:
		return "Problem with the CA certificate";
	case WS_LASTERR_SSL_ENGINE_INITFAILED:
		return "Failed to initialise SSL engine";
	case WS_LASTERR_SEND_ERROR:
		return "Failed sending network data";
	case WS_LASTERR_RECV_ERROR:
		return "Failure in receiving network data";
	case WS_LASTERR_BAD_CONTENT_ENCODING:
		return "Unrecognized transfer encoding";
	case WS_LASTERR_LOGIN_DENIED:
		return "User, password or similar was not accepted";
	default:
		return "Unrecognized error";
	}
}
