/*******************************************************************************
 * 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
 */
#ifdef HAVE_CONFIG_H
#include "config.h"
#endif

#include <stdio.h>
#include <stdlib.h>
#include <string.h>

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

#include <errno.h>
#include <time.h>

#include <wsman-client.h>
#include <wsman-client-transport.h>
#include <wsman-debug.h>


#if __linux__
extern char *getpass (const char *__prompt);
#endif

static long int server_port = 0;
static char *cainfo = NULL;
static char *cert = NULL;
static char *sslkey = NULL;
static char *endpoint = NULL;
static char *username = NULL;
static char *password = NULL;
static char *server = "localhost";
static char *agent = NULL;
static char *url_path = NULL;
static char *authentication_method = NULL;
static char noverify_peer = 0;
static char noverify_host = 0;

static long int  transport_timeout = 0;
static char *proxy = NULL;
static char *proxy_upwd = NULL;


static long int debug_level = -1;
static char *encoding = NULL;
static char *test_case = NULL;
static long int enum_max_elements = 0;
char enum_optimize = 0;
char enum_estimate = 0;
char dump_request = 0;
char step = 0;
char request_only = 0;
char cim_extensions = 0;
static char *enum_mode = NULL;
static char *binding_enum_mode = NULL;
static char *enum_context = NULL;
static char *event_delivery_mode = NULL;
static char *event_delivery_sec_mode = NULL;
static char *event_delivery_uri = NULL;
static long int event_subscription_expire = 0;
static long int event_heartbeat = 0;
static int event_sendbookmark =0;
static char *event_subscription_id = NULL;
static char *event_reference_properties = NULL;
static char *event_username = NULL;
static char *event_password = NULL;
static char *event_thumbprint = NULL;

static char *cim_namespace = NULL;
static char *fragment = NULL;
static char *wsm_filter = NULL;
static char *wsm_dialect = NULL;
static char *input = NULL;

static unsigned long operation_timeout = 0;
static unsigned long max_envelope_size = 0;

static char *_action = NULL;
static char *config_file = NULL;
static char *output_file = NULL;
static char *resource_uri_opt = NULL;
static char *invoke_method = NULL;
static char **properties = NULL;

struct _WsActions {
	char *action;
	int value;
};
typedef struct _WsActions WsActions;

WsActions action_data[] = {
	{"get", WSMAN_ACTION_TRANSFER_GET},
	{"put", WSMAN_ACTION_TRANSFER_PUT},
	{"create", WSMAN_ACTION_TRANSFER_CREATE},
	{"delete", WSMAN_ACTION_TRANSFER_DELETE},
	{"enumerate", WSMAN_ACTION_ENUMERATION},
	{"pull", WSMAN_ACTION_PULL},
	{"release", WSMAN_ACTION_RELEASE},
	{"invoke", WSMAN_ACTION_CUSTOM},
	{"identify", WSMAN_ACTION_IDENTIFY},
	{"anonid", WSMAN_ACTION_ANON_IDENTIFY},
	{"subscribe", WSMAN_ACTION_SUBSCRIBE},
	{"unsubscribe", WSMAN_ACTION_UNSUBSCRIBE},
	{"renew", WSMAN_ACTION_RENEW},
	{"associators", WSMAN_ACTION_ASSOCIATORS},
	{"references", WSMAN_ACTION_REFERENCES},
	{"test", WSMAN_ACTION_TEST},
	{NULL, 0},
};

WsActions delivery_mode[] = {
	{"push", WSMAN_DELIVERY_PUSH},
	{"pushwithack", WSMAN_DELIVERY_PUSHWITHACK},
	{"events", WSMAN_DELIVERY_EVENTS},
	{"pull", WSMAN_DELIVERY_PULL},
	{NULL, 0}
};

WsActions delivery_sec_mode[] = {
	{"httpbasic", WSMAN_DELIVERY_SEC_HTTP_BASIC},
	{"httpdigest", WSMAN_DELIVERY_SEC_HTTP_DIGEST},
	{"httpsbasic", WSMAN_DELIVERY_SEC_HTTPS_BASIC},
	{"httpsdigest", WSMAN_DELIVERY_SEC_HTTPS_DIGEST},
	{"httpsmutual", WSMAN_DELIVERY_SEC_HTTPS_MUTUAL},
	{"httpsmutualbasic", WSMAN_DELIVERY_SEC_HTTPS_MUTUAL_BASIC},
	{"httpsmutualdigest", WSMAN_DELIVERY_SEC_HTTPS_MUTUAL_DIGEST},
	{NULL, 0}
};

static int wsman_options_get_action(void)
{
	int op = 0;
	int i;
	for (i = 0; action_data[i].action != NULL; i++) {
		if (strcmp(action_data[i].action, _action) == 0) {
			op = action_data[i].value;
			break;
		}
	}
	return op;
}

static char wsman_parse_options(int argc, char **argv)
{
	char retval = 0;
	u_error_t *error = NULL;
	char my_version = 0;

	u_option_entry_t options[] = {
		{"version", 'q', U_OPTION_ARG_NONE, &my_version,
			"Display application version", NULL},
		{"debug", 'd', U_OPTION_ARG_INT, &debug_level,
			"Set the verbosity of debugging output.", "1-6"},
		{"encoding", 'j', U_OPTION_ARG_STRING, &encoding,
			"Set request message encoding"},
		{"cacert", 'c', U_OPTION_ARG_STRING, &cainfo,
			"Certificate file to verify the peer", "<filename>"},
		{"cert", 'A', U_OPTION_ARG_STRING, &cert,
			"Certificate file. The certificate must be in PEM format.", "<filename>"},
		{"sslkey", 'K', U_OPTION_ARG_STRING, &sslkey,
			"SSL Key.", "<key>"},
		{"username", 'u', U_OPTION_ARG_STRING, &username,
			"User name", "<username>"},
		{"path", 'g', U_OPTION_ARG_STRING, &url_path,
			"Service Path (default: 'wsman')", "<path>"},
		{"input", 'J', U_OPTION_ARG_STRING, &input,
			"File with resource for Create and Put operations in XML, can be a SOAP envelope",
			"<filename>"},
		{"password", 'p', U_OPTION_ARG_STRING, &password,
			"User Password", "<password>"},
		{"hostname", 'h', U_OPTION_ARG_STRING, &server,
			"Host name", "<hostname>"},
		{"endpoint", 'b', U_OPTION_ARG_STRING, &endpoint,
			"End point", "<url>"},
		{"port", 'P', U_OPTION_ARG_INT, &server_port,
			"Server Port", "<port>"},
		{"proxy", 'X', U_OPTION_ARG_STRING, &proxy,
			"Proxy name", "<proxy>"},
		{"proxyauth", 'Y', U_OPTION_ARG_STRING, &proxy_upwd,
			"Proxy user:pwd", "<proxyauth>"},
		{"auth", 'y', U_OPTION_ARG_STRING, &authentication_method,
			"Authentication Method", "<basic|digest|gss>"},
		{"method", 'a', U_OPTION_ARG_STRING, &invoke_method,
			"Method (Works only with 'invoke')", "<custom method>"},
		{"prop", 'k', U_OPTION_ARG_STRING_ARRAY, &properties,
			"Properties with key value pairs (For 'put', 'invoke' and 'create')",
			"<key=val>"},
		{"config-file", 'C', U_OPTION_ARG_STRING, &config_file,
			"Alternate configuration file", "<file>"},
		{"out-file", 'O', U_OPTION_ARG_STRING, &output_file,
			"Write output to file", "<file>"},
		{"noverifypeer", 'V', U_OPTION_ARG_NONE, &noverify_peer,
			"Not to verify peer certificate", NULL},
		{"noverifyhost", 'v', U_OPTION_ARG_NONE, &noverify_host,
			"Not to verify hostname", NULL},
		{"transport-timeout", 'I', U_OPTION_ARG_INT, &transport_timeout,
			"Transport timeout in seconds", "<time in sec>"},
		{NULL}
	};



	u_option_entry_t request_options[] = {
		{"filter", 'x', U_OPTION_ARG_STRING, &wsm_filter,
			"Filter", "<filter>"},
		{"dialect", 'D', U_OPTION_ARG_STRING, &wsm_dialect,
			"Filter Dialect", "<dialect>"},
		{"operation-timeout", 't', U_OPTION_ARG_INT, &operation_timeout,
			"Operation timeout in seconds", "<time in sec>"},
		{"max-envelope-size", 'e', U_OPTION_ARG_INT,
			&max_envelope_size,
			"maximal envelope size", "<size>"},
		{"fragment", 'F', U_OPTION_ARG_STRING, &fragment,
			"Fragment (Supported Dialects: XPATH)", "<fragment>"},
		{NULL}
	};

	u_option_entry_t enum_options[] = {

		{"max-elements", 'm', U_OPTION_ARG_INT, &enum_max_elements,
			"Max Elements Per Pull/Optimized Enumeration",
			"<max number of elements>"},
		{"optimize", 'o', U_OPTION_ARG_NONE, &enum_optimize,
			"Optimize enumeration results", NULL},
		{"estimate-count", 'E', U_OPTION_ARG_NONE, &enum_estimate,
			"Return estimation of total items", NULL},
		{"enum-mode", 'M', U_OPTION_ARG_STRING, &enum_mode,
			"Enumeration Mode", "epr|objepr"},
		{"enum-context", 'U', U_OPTION_ARG_STRING, &enum_context,
			"Enumeration Context (For use with Pull and Release)",
			"<enum context>"},
		{NULL}
	};

	u_option_entry_t event_options[] = {
		{"delivery-mode", 'G', U_OPTION_ARG_STRING, &event_delivery_mode,
			"Four delivery modes available: push/pushwithack/events/pull",
			"<mode>"},
		{"delivery-sec-mode", 's', U_OPTION_ARG_STRING, &event_delivery_sec_mode,
			"Four delivery modes available: httpbasic/httpdigest/httpsbasic/httpsdigest/httpsmutual/httpsmutualbasic/httpsmutualdigest",
			"<mode>"},
		{"delivery-username", 'n', U_OPTION_ARG_STRING, &event_username,
			"username for the eventing receiver",
			"<username>"},
		{"delivery-password", 'z', U_OPTION_ARG_STRING, &event_password,
			"password for the eventing receiver",
			"<password>"},
		{"delivery-thumbprint", 'Y', U_OPTION_ARG_STRING, &event_thumbprint,
			"ceritificate thumbprint of the eventing receiver",
			"<thumbprint>"},
		{"notification-uri", 'Z', U_OPTION_ARG_STRING, &event_delivery_uri,
			"Where notifications are sent",
			"<uri>"},
		{"subscription-expiry-time", 'r', U_OPTION_ARG_INT, &event_subscription_expire,
			"subscription expiry time in seconds",
			"<seconds>"},
		{"heartbeat",'H', U_OPTION_ARG_INT, &event_heartbeat,
			"Send hearbeat in an interval",
			"<seconds>"},
		{"bookmark", 'l', U_OPTION_ARG_NONE, &event_sendbookmark,
			"Send bookmark",NULL},
		{"subscription-identifier", 'i', U_OPTION_ARG_STRING, &event_subscription_id,
			"Used to specify which subscription",
			"<uuid:XXX>"},
		{"event-reference-properties", 'L', U_OPTION_ARG_STRING, &event_reference_properties,
			"Event Reference Properties, correlation of Events with Subscription",
			"<xml string>"},
		{NULL}
	};

	u_option_entry_t cim_options[] = {

		{"namespace", 'N', U_OPTION_ARG_STRING, &cim_namespace,
			"CIM Namespace (default is root/cimv2)", "<namespace>"},
		{"binding-enum-mode", 'B', U_OPTION_ARG_STRING,
			&binding_enum_mode,
			"CIM binding Enumeration Mode", "none|include|exclude"},
		{"cim-extensions", 'T', U_OPTION_ARG_NONE, &cim_extensions,
			"Show CIM Extensions", NULL},
		{NULL}
	};

	u_option_entry_t test_options[] = {
		{"from-file", 'f', U_OPTION_ARG_STRING, &test_case,
			"Send request from file", "<file name>"},
		{"print-request", 'R', U_OPTION_ARG_NONE, &dump_request,
			"print request on stdout", NULL},
		{"request", 'Q', U_OPTION_ARG_NONE, &request_only,
			"Only output reqest. Not send it.", NULL},
		{"step", 'S', U_OPTION_ARG_NONE, &step,
			"Do not perform multiple operations (do not pull data when enumerating)",
			NULL},
		//{ "print-response", 'N', 0, G_OPTION_ARG_NONE, &dump_response, "print all responses to stdout", NULL},
		{NULL}
	};

	u_option_group_t *enum_group;
	u_option_group_t *event_group;
	u_option_group_t *test_group;
	u_option_group_t *cim_group;
	u_option_group_t *req_flag_group;

	u_option_context_t *opt_ctx;
	opt_ctx = u_option_context_new("<action> <Resource Uri>");
	enum_group = u_option_group_new("enumeration", "Enumeration",
			"Enumeration Options");
	test_group = u_option_group_new("tests", "Tests", "Test Cases");
	cim_group = u_option_group_new("cim", "CIM", "CIM Options");
	event_group = u_option_group_new("event", "Event subscription", "Subscription Options");
	req_flag_group =
		u_option_group_new("flags", "Flags", "Request Flags");

	u_option_group_add_entries(enum_group, enum_options);
	u_option_group_add_entries(test_group, test_options);
	u_option_group_add_entries(cim_group, cim_options);
	u_option_group_add_entries(req_flag_group, request_options);
	u_option_group_add_entries(event_group, event_options);

	u_option_context_set_ignore_unknown_options(opt_ctx, FALSE);
	u_option_context_add_main_entries(opt_ctx, options, "wsman");
	u_option_context_add_group(opt_ctx, enum_group);
	u_option_context_add_group(opt_ctx, test_group);
	u_option_context_add_group(opt_ctx, cim_group);
	u_option_context_add_group(opt_ctx, req_flag_group);
	u_option_context_add_group(opt_ctx, event_group);

	retval = u_option_context_parse(opt_ctx, &argc, &argv, &error);
	u_option_context_free(opt_ctx);

	if (error) {
		if (error->message)
			printf("%s\n", error->message);
		u_error_free(error);
		return FALSE;
	}

	if (my_version) {
		fprintf(stdout, PACKAGE_STRING " (" PACKAGE_BUILDTS ")\n\n");
		exit(0);
	}

	if (argc > 2) {
		_action = argv[1];
		resource_uri_opt = argv[2];
	} else {
		if (argv[1] && (strcmp(argv[1], "identify") == 0 ||
					strcmp(argv[1], "test") == 0 ||
					strcmp(argv[1], "anonid") == 0 ||
					strcmp(argv[1], "unsubscribe") == 0 ||
					strcmp(argv[1], "renew") == 0)) {
			_action = argv[1];
		} else {
			fprintf(stderr,
					"Error: operation can not be completed."
					" Action or/and Resource Uri missing.\n");
			return FALSE;
		}
	}
	u_error_free(error);

	// set default options
	if (server_port == 0) {
		server_port = cainfo ? 5986 : 5985;
	}
	if (url_path == NULL) {
		if (strcmp(argv[1], "anonid") == 0)
			url_path = "/wsman-anon/identify";
		else
			url_path = "/wsman";
	}
	return TRUE;
}


static void wsman_output(WsManClient * cl, WsXmlDocH doc)
{
	FILE *f = stdout;
	const char *filename = output_file;
	const char *badxml = NULL;
	WS_LASTERR_Code err;

	err = wsmc_get_last_error(cl);
	if (err != WS_LASTERR_OK) {
		return;
	}
	if (!doc) {
		error("doc with NULL content");
		badxml = (char*)u_buf_ptr(cl->connection->response);
		if ((-1 == debug_level) || (NULL == badxml)) {
			goto error1;
		}
	}
	if (filename) {
		f = fopen(filename, "w");
		if (f == NULL) {
			error("Could not open file for writing");
			goto error1;
		}
	}
	if (NULL != badxml) {
		fprintf(f, "%s", badxml); // on debug mode, output the bad xml
	} else {
		ws_xml_dump_node_tree(f, ws_xml_get_doc_root(doc));
	}
	if (f != stdout) {
		fclose(f);
	}

error1:
	return;
}

/*
 * output pull results to separate files (appending "-<index>" to the name)
 * 
 */
static void wsman_output_pull(WsManClient * cl, WsXmlDocH doc, int index)
{
	char *strbuf, *origfile = output_file;
	int count;

	if (output_file) {
		count = strlen(output_file) + 16;
		strbuf = (char*)calloc(count, 1);
		snprintf(strbuf, count, "%s-%u.xml", output_file, index);
		output_file = strbuf;
	}
	wsman_output(cl, doc);
	if (origfile) {
		output_file = origfile;
		free(strbuf);
	}
}

static void initialize_logging(void)
{
	debug_add_handler(wsman_debug_message_handler, DEBUG_LEVEL_ALWAYS,
			NULL);
}



static void
request_usr_pwd( WsManClient *client, wsman_auth_type_t auth,
		char **username,
		char **password)
{
	char *pw;
	char user[21];
	char *p;

	fprintf(stdout,"Authentication failed, please retry\n");
	/*
	   fprintf(stdout, "%s authentication is used\n",
	   wsmc_transport_get_auth_name( auth));
	   */
	printf("User name: ");
	fflush(stdout);
	if ( (p = fgets(user, 20, stdin) ) != NULL )
	{

		if (strchr(user, '\n'))
			(*(strchr(user, '\n'))) = '\0';
		*username = u_strdup_printf ("%s", user);
	} else {
		*username = NULL;
	}

	pw = (char *)getpass("Password: ");
	*password = u_strdup_printf ("%s", pw);
}



static hash_t *wsman_options_get_properties(void)
{
	int c = 0;
	hash_t *h = hash_create(HASHCOUNT_T_MAX, 0, 0);

	while (properties != NULL && properties[c] != NULL) {
		char *cc[3] = { NULL, NULL, NULL };
		u_tokenize1(cc, 2, properties[c], '=');
		if (!hash_lookup(h, cc[0])) {
			if (!hash_alloc_insert(h, cc[0], cc[1])) {
				debug("hash_alloc_insert failed");
			}
		} else {
			warn("duplicate not added to hash");
		}

		c++;
	}
	return h;
}


static int wsman_options_get_delivery_mode(void)
{
	int mode = 0;
	int i;
	for (i = 0; delivery_mode[i].action != NULL; i++) {
		if (strcmp(delivery_mode[i].action, event_delivery_mode) == 0) {
			mode = delivery_mode[i].value;
			break;
		}
	}
	return mode;
}

static int wsman_options_get_delivery_sec_mode(void)
{
	int mode = 0;
	int i;
	for (i = 0; delivery_sec_mode[i].action != NULL; i++) {
		if (strcmp(delivery_sec_mode[i].action, event_delivery_sec_mode) == 0) {
			mode = delivery_sec_mode[i].value;
			break;
		}
	}
	return mode;
}


static int wsman_read_client_config(dictionary * ini)
{
	if (iniparser_find_entry(ini, "client")) {
		agent = iniparser_getstr(ini, "client:agent");
		server_port = server_port ?
			server_port : iniparser_getint(ini, "client:port", 5985);
		authentication_method = authentication_method ?
			authentication_method :
			iniparser_getstr(ini, "client:authentication_method");
	} else {
		return 0;
	}
	return 1;
}

static void free_include_result_property(char **resultProps)
{
       if (NULL != resultProps) {
               char **tmp = resultProps;
               while (*tmp != NULL) { // iterate until list terminator
                       u_free(*tmp);
                       tmp++;
               }
               u_free(resultProps);
       }
}

static char ** get_include_result_property(int *propNum)
{
       char **resultProps = NULL;
       char *tok, *val, *copy;
       int idx = 0;

       *propNum = 0;
       if (NULL != enum_context) {
               copy = u_strdup(enum_context);
               for (tok = copy ; NULL != tok ; (*propNum)++, tok = strchr(tok, ',')) { // get count
                       tok++;
               }
               resultProps = (char **)u_calloc((*propNum + 1), sizeof(char *)); // 1 more for list terminator
               val = copy;
               while (val) {
                       tok = strchr(val, ',');
                       if (NULL != tok) {
                               *tok++ = '\0';
                       }
                       resultProps[idx++] = u_strdup(val);
                       val = tok;
               }
               resultProps[idx] = NULL; // list terminator
               u_free(copy);
       }
       return resultProps;
}

int main(int argc, char **argv)
{
	int retVal = 0;
	int op;
	char *filename;
	dictionary *ini = NULL;
	WsManClient *cl;
	WsXmlDocH doc;
	char *enumContext = NULL;
	WsXmlDocH rqstDoc;
	client_opt_t *options;
	WsXmlDocH enum_response;
	WsXmlDocH resource = NULL;
	char *enumeration_mode, *binding_enumeration_mode,
		 *resource_uri_with_selectors;
	char *event_mode, *delivery_uri;
	char *resource_uri = NULL;
	char subscontext[512];
	filter_t *filter = NULL;


	filename = (char *) config_file;

	if (filename) {
		ini = iniparser_new(filename);
		if (ini == NULL) {
			fprintf(stderr, "cannot parse file [%s]",
					filename);
			exit(EXIT_FAILURE);
		} else if (!wsman_read_client_config(ini)) {
			fprintf(stderr, "Configuration file not found\n");
			exit(EXIT_FAILURE);
		}
	}
	if (!wsman_parse_options(argc, argv)) {
		exit(EXIT_FAILURE);
	}
	initialize_logging();
	//      wsmc_transport_init(NULL);
	options = wsmc_options_init();

	debug("Certificate: %s", cainfo);

	if (endpoint) {
		cl = wsmc_create_from_uri(endpoint);
	} else {
		cl = wsmc_create(server,
				server_port,
				url_path,
				cainfo ? "https" : "http",
				username,
				password);
	}

	wsmc_transport_set_auth_request_func(cl ,  &request_usr_pwd );


	if (cl == NULL) {
		error("Null Client");
		exit(EXIT_FAILURE);
	}
	// transport options
	wsman_transport_set_auth_method(cl, authentication_method);
	if (proxy) {
		wsman_transport_set_proxy(cl, proxy);
		if (proxy_upwd) {
			wsman_transport_set_proxyauth(cl, proxy_upwd);
		}
	}

	if (cainfo) {
		wsman_transport_set_cainfo(cl, cainfo);
	}
	if (cert) {
		wsman_transport_set_cert(cl, cert);
		if (!cainfo)
			fprintf(stderr, "Warning: --cacert not set to enable SSL operation\n");
	}
	if (sslkey) {
		wsman_transport_set_key(cl, sslkey);
		if (!cainfo)
			fprintf(stderr, "Warning: --cacert not set to enable SSL operation\n");
	}
	wsman_transport_set_verify_peer(cl, !noverify_peer);
	wsman_transport_set_verify_host(cl, !noverify_host);
	wsman_transport_set_timeout(cl, transport_timeout);

	// library options
	wsman_debug_set_level(debug_level);
	/*
	 * Setup Resource URI and Selectors
	 */
	resource_uri_with_selectors = resource_uri_opt;
	if (resource_uri_with_selectors &&
			strcmp(resource_uri_with_selectors,CIM_ALL_AVAILABLE_CLASSES) != 0) {
		wsmc_set_options_from_uri(resource_uri_with_selectors,
				options);
		wsmc_remove_query_string(resource_uri_with_selectors,
				&resource_uri);
	} else if (resource_uri_with_selectors) {
		wsmc_remove_query_string(resource_uri_with_selectors,
				&resource_uri);
	}
	op = wsman_options_get_action();
	if (encoding) {
		wsmc_set_encoding(cl, encoding);
	}
	if (dump_request) {
		wsmc_set_action_option(options, FLAG_DUMP_REQUEST);
	}
	if (max_envelope_size) {
		options->max_envelope_size = max_envelope_size;
	}
	if (operation_timeout) {
		options->timeout = operation_timeout;
	}
	if (fragment) {
		options->fragment = fragment;
	}

	options->properties = wsman_options_get_properties();
	options->cim_ns = cim_namespace;
	if (cim_extensions) {
		wsmc_set_action_option(options, FLAG_CIM_EXTENSIONS);
	}

	switch (op) {
	case WSMAN_ACTION_TEST:
		rqstDoc = wsmc_read_file(input, wsmc_get_encoding(cl), 0);
		wsman_send_request(cl, rqstDoc);
		doc = wsmc_build_envelope_from_response(cl);
		wsman_output(cl, doc);
		if (doc) {
			ws_xml_destroy_doc(doc);
		}
		break;
	case WSMAN_ACTION_ANON_IDENTIFY:
	case WSMAN_ACTION_IDENTIFY:
		doc = wsmc_action_identify(cl, options);
		wsman_output(cl, doc);
		if (doc) {
			ws_xml_destroy_doc(doc);
		}
		break;
	case WSMAN_ACTION_CUSTOM:
		if (input) {
			resource = wsmc_read_file(input, wsmc_get_encoding(cl), 0);
		}
		doc = wsmc_action_invoke(cl, resource_uri, options,
				invoke_method,
				resource);
		ws_xml_destroy_doc(resource);
		wsman_output(cl, doc);
		if (doc) {
			ws_xml_destroy_doc(doc);
		}
		break;
	case WSMAN_ACTION_TRANSFER_DELETE:
		doc = wsmc_action_delete(cl, resource_uri, options);
		wsman_output(cl, doc);
		if (doc) {
			ws_xml_destroy_doc(doc);
		}
		break;

	case WSMAN_ACTION_TRANSFER_CREATE:
		if (input) {
			resource = wsmc_read_file(input, "UTF-8", 0);
			doc =
				wsmc_action_create(cl, resource_uri, options,
						resource);
			ws_xml_destroy_doc(resource);
			wsman_output(cl, doc);
			if (doc) {
				ws_xml_destroy_doc(doc);
			}
		} else {
			fprintf(stderr, "Missing resource data\n");
		}
		break;
	case WSMAN_ACTION_TRANSFER_PUT:
		if (input) {
			printf("input file provided\n");
			resource = wsmc_read_file(input, wsmc_get_encoding(cl), 0);
			doc =  wsmc_action_put(cl, resource_uri, options,
					resource);
			ws_xml_destroy_doc(resource);
		} else {
			doc =
				wsmc_action_get_and_put(cl, resource_uri,
						options);
		}
		wsman_output(cl, doc);
		if (doc) {
			ws_xml_destroy_doc(doc);
		}
		break;
	case WSMAN_ACTION_TRANSFER_GET:
		doc = wsmc_action_get(cl, resource_uri, options);
		wsman_output(cl, doc);
		if (doc) {
			ws_xml_destroy_doc(doc);
		}
		break;
	case WSMAN_ACTION_PULL:
		doc = wsmc_action_pull(cl, resource_uri, options, filter, enum_context);
		wsman_output(cl, doc);
		if (doc) {
			ws_xml_destroy_doc(doc);
		}
		break;
	case WSMAN_ACTION_RELEASE:
		doc =
			wsmc_action_release(cl, resource_uri, options,
					enum_context);
		wsman_output(cl, doc);
		if (doc) {
			ws_xml_destroy_doc(doc);
		}
		break;
	case WSMAN_ACTION_ASSOCIATORS:
	case WSMAN_ACTION_REFERENCES:
	case WSMAN_ACTION_ENUMERATION:
		if ( op == WSMAN_ACTION_REFERENCES || op == WSMAN_ACTION_ASSOCIATORS ) {
			if (wsm_filter) {
				epr_t *epr = epr_from_string(wsm_filter);
				if(options->cim_ns) {
					epr_add_selector_text(epr, CIM_NAMESPACE_SELECTOR, options->cim_ns);
				}
				if (epr) {
					char **resultProperties = NULL;
					const char *assocClass, *resultClass, *role, *resultRole;
					int propNum;

					if (NULL != (assocClass = wsman_epr_selector_by_name(epr, "AssociationClassName")))
						epr_delete_selector(epr, "AssociationClassName");
					if (NULL != (resultClass = wsman_epr_selector_by_name(epr, "ResultClassName")))
						epr_delete_selector(epr, "ResultClassName");
					if (NULL != (role = wsman_epr_selector_by_name(epr, "Role")))
						epr_delete_selector(epr, "Role");
					if (NULL != (resultRole = wsman_epr_selector_by_name(epr, "ResultRole")))
						epr_delete_selector(epr, "ResultRole");
					resultProperties = get_include_result_property(&propNum);

					filter = filter_create_assoc(epr, (op == WSMAN_ACTION_ASSOCIATORS )?0:1,
								     assocClass, resultClass, role, resultRole, resultProperties, propNum);

					free_include_result_property(resultProperties);
				}
			} else {
				error("Filter Requied");
			}
		} else if (wsm_dialect && strcmp(wsm_dialect, WSM_SELECTOR_FILTER_DIALECT) == 0 ) {
			// fixme: Namespace
			if (wsm_filter) {
				hscan_t hs;
				hnode_t *hn;
				hash_t *selfilter = NULL;
				hash_t *selectors_new = NULL;
				selector_entry *entry;
				selectors_new = hash_create2(HASHCOUNT_T_MAX, 0, 0);
				selfilter = u_parse_query(wsm_filter);
				hash_scan_begin(&hs, selfilter);
				while ((hn = hash_scan_next(&hs))) {
					entry = u_malloc(sizeof(selector_entry));
					entry->type = 0;
					entry->entry.text = (char *)hnode_get(hn);
					hash_alloc_insert(selectors_new, hnode_getkey(hn), entry);
				}

				if (hash_count(selectors_new) > 0 )
					filter = filter_create_selector(selectors_new);
			}
		} else {
			filter = filter_create_simple(wsm_dialect, wsm_filter);
		}
		enumeration_mode = enum_mode;
		binding_enumeration_mode = binding_enum_mode;

		if (enumeration_mode) {
			if (strcmp(enumeration_mode, "epr") == 0)
				wsmc_set_action_option(options,
						FLAG_ENUMERATION_ENUM_EPR);
			else if (strcmp(enumeration_mode, "objepr") == 0)
				wsmc_set_action_option(options,
						FLAG_ENUMERATION_ENUM_OBJ_AND_EPR);
		}
		if (binding_enumeration_mode) {
			if (strcmp(binding_enumeration_mode, "include") ==
					0)
				wsmc_set_action_option(options,
						FLAG_IncludeSubClassProperties);
			else if (strcmp
					(binding_enumeration_mode,
					 "exclude") == 0)
				wsmc_set_action_option(options,
						FLAG_ExcludeSubClassProperties);
			else if (strcmp(binding_enumeration_mode, "none")
					== 0)
				wsmc_set_action_option(options,
						FLAG_POLYMORPHISM_NONE);
		}
		if (enum_optimize) {
			wsmc_set_action_option(options,
					FLAG_ENUMERATION_OPTIMIZATION);
		}
		options->max_elements = enum_max_elements;

		if (enum_estimate) {
			wsmc_set_action_option(options,
					FLAG_ENUMERATION_COUNT_ESTIMATION);
		}
		enum_response = wsmc_action_enumerate(cl, resource_uri, options, filter);
		wsman_output(cl, enum_response);
		if (enum_response) {
			if (!(wsmc_get_response_code(cl) == 200 ||
						wsmc_get_response_code(cl) == 400 ||
						wsmc_get_response_code(cl) == 500)) {
				break;
			}
			enumContext = wsmc_get_enum_context(enum_response);
			ws_xml_destroy_doc(enum_response);
		} else {
			break;
		}

		if (step)
			break;

      int index = 0;
		while (enumContext != NULL && enumContext[0] != 0) {

			doc = wsmc_action_pull(cl, resource_uri, options, filter,
					enumContext);
			wsman_output_pull(cl, doc, ++index);

			if (wsmc_get_response_code(cl) != 200
					&& wsmc_get_response_code(cl) != 400
					&& wsmc_get_response_code(cl) != 500) {
				break;
			}
			u_free(enumContext);
			enumContext = wsmc_get_enum_context(doc);
			if (doc) {
				ws_xml_destroy_doc(doc);
			}
		}
		u_free(enumContext);
		break;
	case WSMAN_ACTION_SUBSCRIBE:
		event_mode = event_delivery_mode;
		delivery_uri = event_delivery_uri;
		if(event_sendbookmark)
			wsmc_set_action_option(options, FLAG_EVENT_SENDBOOKMARK);
		if(event_delivery_mode)
			options->delivery_mode = wsman_options_get_delivery_mode();
		if(event_delivery_sec_mode)
			options->delivery_sec_mode = wsman_options_get_delivery_sec_mode();
		if(event_username)
			options->delivery_username = event_username;
		if(event_password)
			options->delivery_password = event_password;
		if(event_thumbprint)
			options->delivery_certificatethumbprint = event_thumbprint;
		if(event_delivery_uri)
			options->delivery_uri = event_delivery_uri;
		if(event_heartbeat)
			options->heartbeat_interval = event_heartbeat;
		if(event_subscription_expire)
			options->expires = event_subscription_expire;
		if(wsm_filter)
			filter = filter_create_simple(wsm_dialect, wsm_filter);

		if(event_reference_properties)
			options->reference = event_reference_properties;
		rqstDoc = wsmc_action_subscribe(cl, resource_uri, options, filter);
		wsman_output(cl, rqstDoc);
		if (rqstDoc) {
			ws_xml_destroy_doc(rqstDoc);
		}
		break;
	case WSMAN_ACTION_UNSUBSCRIBE:
		snprintf(subscontext, 512 , "<wsa:ReferenceParameters xmlns:wsa=\"http://schemas.xmlsoap.org/ws/2004/08/addressing\" \
				xmlns:wse=\"http://schemas.xmlsoap.org/ws/2004/08/eventing\"><wse:Identifier>%s</wse:Identifier> \
				</wsa:ReferenceParameters>", event_subscription_id);
		rqstDoc = wsmc_action_unsubscribe(cl, resource_uri, options, subscontext);
		wsman_output(cl, rqstDoc);
		if (rqstDoc) {
			ws_xml_destroy_doc(rqstDoc);
		}
		break;
	case WSMAN_ACTION_RENEW:
		if(event_subscription_expire)
			options->expires = event_subscription_expire;
		snprintf(subscontext, 512 , "<wsa:ReferenceParameters xmlns:wsa=\"http://schemas.xmlsoap.org/ws/2004/08/addressing\" \
				xmlns:wse=\"http://schemas.xmlsoap.org/ws/2004/08/eventing\"><wse:Identifier>%s</wse:Identifier> \
				</wsa:ReferenceParameters>", event_subscription_id);
		rqstDoc = wsmc_action_renew(cl, resource_uri, options, subscontext);
		wsman_output(cl, rqstDoc);
		if (rqstDoc) {
			ws_xml_destroy_doc(rqstDoc);
		}
		break;
	default:
		fprintf(stderr, "Action not supported\n");
		retVal = 1;
	}


	if (wsmc_get_response_code(cl) != 200) {
		fprintf(stderr, "Connection failed. response code = %ld\n",
				wsmc_get_response_code(cl));
		if (wsmc_get_fault_string(cl)) {
			fprintf(stderr, "%s\n",
					wsmc_get_fault_string(cl));
		}
	}
	wsmc_options_destroy(options);
	filter_destroy(filter);
	wsmc_transport_fini(cl);
	wsmc_release(cl);
	if (ini) {
		iniparser_free(ini);
	}
#ifdef DEBUG_VERBOSE
	printf("     ******   Transfer Time = %ull usecs ******\n",
			get_transfer_time());
#endif
	return retVal;

}
