/*
 * Sigma Control API DUT - Miracast interface
 * Copyright (c) 2017, Qualcomm Atheros, Inc.
 * Copyright (c) 2018, The Linux Foundation
 * All Rights Reserved.
 * Licensed under the Clear BSD license. See README for more details.
 *
 * Implementation of MIRACAST specific functionality.
 * For example, starting wfd session.
*/

#include "sigma_dut.h"
#include <dlfcn.h>
#include <sys/ioctl.h>
#include <sys/select.h>
#include "wpa_ctrl.h"
#include "wpa_helpers.h"
#include "miracast.h"
#ifdef ANDROID
#include "properties.h"
#ifndef MIRACAST_DHCP_M
#include <netutils/ifc.h>
#endif /* MIRACAST_DHCP_M */
#endif /* ANDROID */

#define HUNDRED_SECOND_TIMEOUT   100 /* 100 seconds */
#define DHCP_LEASE_FILE_PATH "/data/misc/dhcp/dnsmasq.leases"
#define MIRACAST_CMD_LEN         512

extern char *sigma_main_ifname;
extern char *sigma_station_ifname;

static int session_management_control_port = 7236;
/* Followingng stores p2p interface name after P2P group formation */
static char wfd_ifname[32];

#ifndef MIRACAST_DHCP_M
extern void get_dhcp_info(uint32_t *ipaddr, uint32_t *gateway,
			  uint32_t *prefixLength, uint32_t *dns1,
			  uint32_t *dns2, uint32_t *server,
			  uint32_t *lease);

extern int do_dhcp(char *);

const char *ipaddr (in_addr_t addr)
{
	struct in_addr in_addr;
	in_addr.s_addr = addr;
	return inet_ntoa(in_addr);
}
#endif /* MIRACAST_DHCP_M */




static int miracast_load(struct sigma_dut *dut)
{
	static int once = 1;

	if (!once)
		return 0;

	once = 0;
	dlerror();
	dut->miracast_lib = dlopen(dut->miracast_lib_path ?
				   dut->miracast_lib_path : "libmiracast.so",
				   RTLD_LAZY);
	if (!dut->miracast_lib) {
		sigma_dut_print(dut, DUT_MSG_INFO,
				"Fail to load Miracast library %s",
				dlerror());
		return -1;
	}
	sigma_dut_print(dut, DUT_MSG_INFO,
			"Miracast Wi-Fi Display library found - starting service");
	return 0;
}


static int miracast_unload(struct sigma_dut *dut)
{
	int err;

	if (!dut->miracast_lib)
		return -1;

	dlerror();
	sigma_dut_print(dut, DUT_MSG_INFO, "Unloading Miracast library");
	err = dlclose(dut->miracast_lib);
	dut->miracast_lib = NULL;
	if (err == 0) {
		sigma_dut_print(dut, DUT_MSG_INFO,
			 "Miracast library successfully unloaded");
	} else {
		sigma_dut_print(dut, DUT_MSG_INFO,
			"Failed to unload Miracast library");
	}
	return err;
}


static int get_peer_ip_p2p_go(struct sigma_dut *dut, char *ipaddr,
			      const char *macaddr, unsigned int wait_limit)
{

	FILE *fp;

	fp = fopen(DHCP_LEASE_FILE_PATH, "r");
	if (!fp) {
		sigma_dut_print(dut, DUT_MSG_ERROR,
				"Could not open DHCP lease file");
		return -1;
	}

	sigma_dut_print(dut, DUT_MSG_INFO, "macaddress %s", macaddr);
	while (wait_limit > 0) {
		char line[100] = { 0 };
		char *str1 = NULL;
		char *dummy_str = NULL;
		char dummy_macaddress[32];
		int ip_found = 0;
		int len;

		fseek(fp, 0, SEEK_SET);
		while (fgets(line, sizeof(line), fp) != NULL) {
			len = strlen(line);
			if (len == 0)
				continue;

			str1 = strtok_r(line, " ", &dummy_str);
			if (str1 == NULL)
				break;

			/* Look for mac address */
			str1 = strtok_r(NULL, " ", &dummy_str);
			if (str1 == NULL)
				break;

			strlcpy(dummy_macaddress, str1,
				sizeof(dummy_macaddress));

			/* Look for ip address */
			str1 = strtok_r(NULL, " ", &dummy_str);
			if (str1 == NULL)
				break;

			strlcpy(ipaddr,str1,32);

			sigma_dut_print(dut, DUT_MSG_INFO,
					"Peer IP Address obtained and mac %s %s",
					ipaddr, dummy_macaddress);

			/*
			 * The idea is that the p2p mac address may differ by 1
			 * nibble mostly it is the first byte, hence try the
			 * middle two octets.
			 */
			if (strncasecmp(macaddr + 6, dummy_macaddress + 6,
					5) == 0) {
				ip_found = 1;
				sigma_dut_print(dut, DUT_MSG_INFO,
						"Obtained the IP address %s",
						ipaddr);
				break;
			}
		}

		if (ip_found)
			break;

		sigma_dut_print(dut, DUT_MSG_INFO,
				"Failed to find IP from DHCP lease file");
		sleep(1);
		wait_limit--;
	}
	fclose(fp);
	return 0;
}


static int miracast_start_dhcp_client(struct sigma_dut *dut, const char *ifname)
{
#ifdef MIRACAST_DHCP_M
	 start_dhcp(dut, ifname, 0);
#else /* MIRACAST_DHCP_M */
	int ret = ifc_init();

	sigma_dut_print(dut, DUT_MSG_DEBUG, "ifc init returned %d", ret);
	ret = do_dhcp((char *) ifname);
	sigma_dut_print(dut, DUT_MSG_DEBUG, "do dhcp returned %d", ret);
#endif /* MIRACAST_DHCP_M */
	return 0;
}


static void miracast_stop_dhcp_client(struct sigma_dut *dut, char *ifname)
{
#ifdef MIRACAST_DHCP_M
	stop_dhcp(dut, ifname, 0);
#else /* MIRACAST_DHCP_M */
	ifc_close();
#endif /* MIRACAST_DHCP_M */
}


#ifdef MIRACAST_DHCP_M

static int get_local_ip_address(struct sigma_dut *dut,
				char *local_ip_addr, size_t buflen,
				const char *intf, int size)
{
	struct ifreq ifr;
	int s;

	memset(&ifr, 0, sizeof(struct ifreq));
	strlcpy(ifr.ifr_name, intf, IFNAMSIZ);
	ifr.ifr_name[IFNAMSIZ-1] = 0;

	if ((s = socket(AF_INET, SOCK_DGRAM, 0)) < 0) {
		sigma_dut_print(dut, DUT_MSG_INFO,
				"%s: Error in creating socket", __func__);
		return -1;
	}

	if (ioctl(s, SIOCGIFADDR, &ifr) < 0) {
		sigma_dut_print(dut, DUT_MSG_INFO, "ioctl failed: %s",
				strerror(errno));
		close(s);
		return -1;
	}

	strlcpy(local_ip_addr,
		inet_ntoa(((struct sockaddr_in *) &ifr.ifr_addr)->sin_addr),
		buflen);
	close(s);
	return 0;
}


static int get_peer_ip_p2p_client(struct sigma_dut *dut, char *ip_addr,
				  const char *intf, unsigned int wait_limit)
{
	char prop_name[128];
	char prop_name_self[128];
	char self_ip[128];

	memset(self_ip, 0, sizeof(self_ip));
	/* For P2P Client read the server property */
	snprintf(prop_name, sizeof(prop_name), "%s.%s.server", "dhcp", "p2p");
	snprintf(prop_name_self, sizeof(prop_name_self),
		 "%s.%s.ipaddress", "dhcp", "p2p");

	while (wait_limit > 0) {
#ifdef ANDROID
		property_get(prop_name, ip_addr, NULL);
#else /* ANDROID */
		ip_addr[0] = '\0';
#endif /* ANDROID */
		get_local_ip_address(dut, self_ip, sizeof(self_ip), intf, 20);
		sigma_dut_print(dut, DUT_MSG_INFO, "Peer IP, self IP: %s %s",
				ip_addr, self_ip);
		if (strlen(ip_addr) > 8 &&
		    ip_addr[0] == '1' && ip_addr[1] == '9' &&
		    self_ip[0] == '1' && self_ip[1] == '9')
			break; /* connected */

		/* What if DHCP server was started before Client was started?
		 * Request DHCP yet again */
		miracast_start_dhcp_client(dut, intf);
		sleep(5); /* Sleep always helps */
		wait_limit--;
	}

	return wait_limit > 0 ? 0 : -1;
}

#else /* MIRACAST_DHCP_M */

static int get_peer_ip_p2p_client(struct sigma_dut *dut, char *ipAddr,
				  const char *intf, unsigned int wait_limit)
{
	uint32_t ipaddress, gateway, prefixLength,
		dns1, dns2, serveraddr, lease;

	get_dhcp_info(&ipaddress, &gateway, &prefixLength, &dns1, &dns2,
		      &serveraddr, &lease);
	while (wait_limit > 0) {
		sigma_dut_print(dut, DUT_MSG_INFO, "Peer IP: %u", ipaddress);
		if (strlen(ipaddr(serveraddr)) > 8) {
			/* connected */
			strlcpy(ipAddr, ipaddr(serveraddr), 16);
			break;
		}
		sleep(1);
		wait_limit--;
	}
	return wait_limit == 0 ? -1 : 0;
}

#endif /* MIRACAST_DHCP_M */


static int get_p2p_connection_event(struct sigma_dut *dut,
				    const char *input_intf,
				    char *output_intf,
				    int size_output_intf,
				    int *is_group_owner)
{
	/*
	* Poll for the P2P Connection
	* Then poll for IP
	* Then poll for WFD session ID and exit
	* P2P connection done
	* Loop till connection is ready
	*/
	struct wpa_ctrl *ctrl;
	char *mode_string;
	char event_buf[256];
	char *ifname;
	char *pos;
	int res = 0;
	const char *events[] = {
		"P2P-GROUP-STARTED",
		"P2P-GO-NEG-FAILURE",
		"P2P-GROUP-FORMATION-FAILURE",
		NULL
	};

	/* Wait for WPA CLI EVENTS */
	/* Default timeout is 120s */
	ctrl = open_wpa_mon(input_intf);
	if (!ctrl) {
		sigma_dut_print(dut, DUT_MSG_ERROR,
				"Failed to open wpa_supplicant monitor connection");
		return -1;
	}

	res = get_wpa_cli_events(dut, ctrl, events, event_buf,
				 sizeof(event_buf));

	wpa_ctrl_detach(ctrl);
	wpa_ctrl_close(ctrl);

	if (res < 0) {
		sigma_dut_print(dut, DUT_MSG_ERROR,
				"Group formation did not complete");
		return -1;
	}

	sigma_dut_print(dut, DUT_MSG_DEBUG, "Received event %s", event_buf);

	if (strstr(event_buf, "P2P-GROUP-FORMATION-FAILURE") ||
	    strstr(event_buf, "P2P-GO-NEG-FAILURE"))
		return -1;

	sigma_dut_print(dut, DUT_MSG_INFO, "P2P connection done");
	ifname = strchr(event_buf, ' ');
	if (!ifname) {
		sigma_dut_print(dut, DUT_MSG_INFO, "No P2P interface found");
		return -1;
	}
	ifname++;
	pos = strchr(ifname, ' ');
	if (!pos) {
		sigma_dut_print(dut, DUT_MSG_ERROR, "No P2P interface found");
		return -1;
	}
	*pos++ = '\0';
	sigma_dut_print(dut, DUT_MSG_DEBUG, "Group interface %s", ifname);

	strlcpy(output_intf, ifname, size_output_intf);

	mode_string = pos;
	pos = strchr(mode_string, ' ');
	if (!pos) {
		sigma_dut_print(dut, DUT_MSG_ERROR, "No group role found");
		return -1;
	}

	*pos++ = '\0';
	sigma_dut_print(dut, DUT_MSG_DEBUG, "Group Role %s", mode_string);

	if (strcmp(mode_string, "GO") == 0)
		*is_group_owner = 1;
	sigma_dut_print(dut, DUT_MSG_DEBUG, "Value of is_group_owner %d",
			*is_group_owner);
	return 0;
}


/* Following serves as an entry point function to perform rtsp tasks */
static void * miracast_rtsp_thread_entry(void *ptr)
{
	struct sigma_dut *dut = ptr;
	char output_ifname[16];
	int is_group_owner = 0;
	const char *intf = sigma_station_ifname;
	unsigned int wait_limit;
	char peer_ip_address[32];
	char rtsp_session_id[12];
	int (*extn_start_wfd_connection)(const char *,
					 const char *, /* Peer IP */
					 int, /* RTSP port number */
					 int, /* WFD Device Type; 0-Source,
						 1-P-Sink, 2-Secondary Sink */
					 char *); /* for returning session ID */

	miracast_load(dut);

	if (sigma_main_ifname) {
		intf = sigma_main_ifname;
		sigma_dut_print(dut, DUT_MSG_DEBUG,
				"miracast_rtsp_thread_entry: sigma_main_ifname = [%s]",
				intf);
	} else {
		sigma_dut_print(dut, DUT_MSG_DEBUG,
				"miracast_rtsp_thread_entry: sigma_main_ifname is NULL");
	}

	if (get_p2p_connection_event(dut, intf, output_ifname,
				     sizeof(output_ifname),
				     &is_group_owner) < 0) {
		sigma_dut_print(dut, DUT_MSG_ERROR, "P2P connection failure");
		goto EXIT;
	}

	sigma_dut_print(dut, DUT_MSG_DEBUG, "Waiting to start dhcp");

	/* Calling WFD APIs now */
	/* If you are a source, go ahead and start the RTSP server */
	if (dut->wfd_device_type != 0)
		wait_limit = HUNDRED_SECOND_TIMEOUT;
	else
		wait_limit = 500;

	if (!is_group_owner) {
		sigma_dut_print(dut, DUT_MSG_INFO,
				"Waiting to start dhcp client");
		sleep(5); /* Wait for IP */
		miracast_start_dhcp_client(dut, output_ifname);
		sleep(5); /* Wait for IP */
		if (get_peer_ip_p2p_client(dut, peer_ip_address, output_ifname,
					   wait_limit) < 0) {
			sigma_dut_print(dut, DUT_MSG_ERROR,
					"Could not get peer IP");
			goto EXIT;
		}
	} else {
		stop_dhcp(dut, output_ifname, 1);
		/* For GO read the DHCP Lease File */
		sigma_dut_print(dut, DUT_MSG_INFO,
				"Waiting to start dhcp server");
		start_dhcp(dut, output_ifname, 1);
		sleep(5);
		if (get_peer_ip_p2p_go(dut, peer_ip_address,
				       dut->peer_mac_address, wait_limit) < 0) {
			sigma_dut_print(dut, DUT_MSG_ERROR,
					"Could not get peer IP");
			goto EXIT;
		}
	}

	extn_start_wfd_connection = dlsym(dut->miracast_lib,
					  "start_wfd_connection");
	if (extn_start_wfd_connection) {
		extn_start_wfd_connection(NULL, peer_ip_address,
					  session_management_control_port,
					  1 - dut->wfd_device_type,
					  rtsp_session_id);
	} else {
		sigma_dut_print(dut, DUT_MSG_INFO,
				"dlsym seems to have error %p %p",
				dut->miracast_lib, extn_start_wfd_connection);
	}

EXIT:
	sigma_dut_print(dut, DUT_MSG_INFO, "Reached Miracast thread exit");

	return NULL;
}


/*----------------------------------------------------------------------
  WFD Source IE: 000601101c440036
  len        WFD device info          control port              throughput
  110]    [00000 00100010 000]    [00011 10001000 100]    [00000 00000110 110]
				       = 7236

  WFD Sink IE: 000601511c440036
  len        WFD device info          control port              throughput
  110]    [00000 00101010 001]    [00011 10001000 100]    [00000 00000110 110]
				       = 7236

  WFD device info:
  BITS        NAME                DESCRIPTION
  -------------------------------------------
  1:0     WFD Device Type     0b00: WFD Source
			      0b01: Primary Sink
			      0b10: Secondary Sink
			      0b11: Dual Role, either WFD Source/Primary sink

  5:4     WFD Session         0b00: Not available for WFD Session
			Availibility	0b01: Available for WFD Session
							0b10, 0b11: Reserved

  6       WSD Support Bit     0b0: WFD Service Discovery not supported
			      0b1: WFD Service Discovery supported

  8       CP Support Bit      0b0: Content Protection via HDCP not supported
			      0b1: Content Protection via HDCP supported
---------------------------------------------------------------------------
*/

static void miracast_set_wfd_ie(struct sigma_dut *sigma_dut)
{
	char *intf = sigma_station_ifname;

	if (sigma_main_ifname != NULL)
		intf = sigma_main_ifname;

	sigma_dut_print(sigma_dut, DUT_MSG_DEBUG, "miracast_set_wfd_ie() = intf = %s",
			intf);
	wpa_command(intf, "SET wifi_display 1");

	if (sigma_dut->wfd_device_type == 0) {
		wpa_command(intf, "WFD_SUBELEM_SET 0 000601101c440036");
		wpa_command(intf, "WFD_SUBELEM_SET 11 00020000");
	} else {
		wpa_command(intf, "WFD_SUBELEM_SET 0 000601511c440036");
		wpa_command(intf, "WFD_SUBELEM_SET 11 00020001");
	}
}


void miracast_init(struct sigma_dut *dut)
{
	sigma_dut_print(dut, DUT_MSG_DEBUG, "Create thread pool for VDS");
	miracast_set_wfd_ie(dut);
	sigma_dut_print(dut, DUT_MSG_DEBUG, "Clear groupID @ start");
}


void miracast_deinit(struct sigma_dut *dut)
{
	(void) miracast_unload(dut);
}


static void miracast_generate_string_cmd(struct sigma_cmd *cmd, char *strcmd,
					 size_t size)
{
	int i = 0;
	char *pos, *end;
	int ret;

	if (!strcmd)
		return;
	strcmd[0] = '\0';
	pos = strcmd;
	end = strcmd + size;
	for (i = 0; i < cmd->count; i++) {
		ret = snprintf(pos, end - pos, "%s,%s,", cmd->params[i],
			       cmd->values[i]);
		if (ret < 0 || ret >= end - pos)
			break;
		pos += ret;
	}

	pos = strrchr(strcmd, ',');
	if (pos)
		*pos = '\0';
	printf("Miracast: generated command: %s\n", strcmd);
}


static void * auto_go_thread_entry(void *ptr)
{
	struct sigma_dut *dut = ptr;
	struct wpa_ctrl *ctrl;
	char event_buf[64];
	char *peer = NULL;
	int res = 0;
	char macaddress[32];
	char peer_ip_address[32];
	char rtsp_session_id[12];
	int (*extn_start_wfd_connection)(const char *,
					 const char *, /* Peer IP */
					 int, /* RTSP port number */
					 int, /* WFD Device Type; 0-Source,
						1-P-Sink, 2-Secondary Sink */
					 char *); /* for returning session ID */

	stop_dhcp(dut, wfd_ifname, 1);
	/* For auto-GO, start the DHCP server and wait for 5 seconds */
	start_dhcp(dut, wfd_ifname, 1);
	sleep(5); /* Wait for IP */

	sigma_dut_print(dut, DUT_MSG_INFO, "Wait for AP-STA-CONNECTED");
	ctrl = open_wpa_mon(wfd_ifname); /* Refer to wfd_ifname */
	if (!ctrl) {
		sigma_dut_print(dut, DUT_MSG_ERROR,
				"Failed to open wpa_supplicant monitor connection");
		goto THR_EXIT;
	}
	res = get_wpa_cli_event(dut, ctrl, "AP-STA-CONNECTED",
				event_buf, sizeof(event_buf));
	wpa_ctrl_detach(ctrl);
	wpa_ctrl_close(ctrl);

	if (res < 0) {
		sigma_dut_print(dut, DUT_MSG_ERROR,
				"Could not get event before timeout");
		goto THR_EXIT;
	}

	sigma_dut_print(dut, DUT_MSG_DEBUG, "STA Connected Event: '%s'",
			event_buf);
	peer = strchr(event_buf, ' ');
	if (!peer) {
		sigma_dut_print(dut, DUT_MSG_ERROR, "Could not find STA MAC");
		goto THR_EXIT;
	}

	peer++;
	strlcpy(macaddress, peer, sizeof(macaddress));
	if (get_peer_ip_p2p_go(dut, peer_ip_address, macaddress, 30) < 0) {
		sigma_dut_print(dut, DUT_MSG_ERROR, "Could not get peer IP");
		goto THR_EXIT;
	}

	sigma_dut_print(dut, DUT_MSG_INFO, "dlsym %p", dut->miracast_lib);
	extn_start_wfd_connection = dlsym(dut->miracast_lib,
					  "start_wfd_connection");
	if (!extn_start_wfd_connection)
		sigma_dut_print(dut, DUT_MSG_INFO, "dlsym function NULL");
	else
		extn_start_wfd_connection(NULL, peer_ip_address,
					  session_management_control_port,
					  1 - dut->wfd_device_type,
					  rtsp_session_id);

THR_EXIT:
	sigma_dut_print(dut, DUT_MSG_INFO, "Reached auto GO thread exit");
	return NULL;
}


void miracast_sta_reset_default(struct sigma_dut *dut, struct sigma_conn *conn,
				struct sigma_cmd *cmd)
{
	char *intf = sigma_station_ifname;
	int (*extn_sta_reset_default)(char *);
	char string_cmd[MIRACAST_CMD_LEN] = { 0 };

	if (sigma_main_ifname != NULL)
		intf = sigma_main_ifname;
	sigma_dut_print(dut, DUT_MSG_DEBUG,
			"miracast_sta_reset_default() = intf = %s", intf);
	stop_dhcp(dut, intf, 1); /* IFNAME argument is ignored */
	miracast_stop_dhcp_client(dut, intf);

	/* This is where vendor Miracast library is loaded and function pointers
	 * to Miracast functions (defined by CAPI) are loaded. */

	if (miracast_load(dut) != 0) {
		sigma_dut_print(dut, DUT_MSG_INFO,
				"Fail to load Miracast library");
		return;
	}

	if (!dut->miracast_lib) {
		sigma_dut_print(dut, DUT_MSG_ERROR,
				"Miracast library is absent");
		return;
	}

	dlerror();

	miracast_generate_string_cmd(cmd, string_cmd, sizeof(string_cmd));
	extn_sta_reset_default = dlsym(dut->miracast_lib, "sta_reset_default");
	if (extn_sta_reset_default)
		extn_sta_reset_default(string_cmd);

	/* delete threads if any */
	/* TODO: if dut->rtsp_thread_handle running, call
	 * miracast_release_rtsp_thread_resources(dut); */
}


void miracast_start_autonomous_go(struct sigma_dut *dut,
				  struct sigma_conn *conn,
				  struct sigma_cmd *cmd, char *ifname)
{
	strlcpy(wfd_ifname, ifname, sizeof(wfd_ifname));
	(void) pthread_create(&dut->rtsp_thread_handle, NULL,
			      auto_go_thread_entry, dut);
}


static void miracast_rtsp_thread_create(struct sigma_dut *dut,
					struct sigma_conn *conn,
					struct sigma_cmd *cmd)
{
	(void) pthread_create(&dut->rtsp_thread_handle, NULL,
			      miracast_rtsp_thread_entry, dut);
}


int miracast_dev_send_frame(struct sigma_dut *dut, struct sigma_conn *conn,
			    struct sigma_cmd *cmd)
{
	const char *frame_name = get_param(cmd, "FrameName");
	/* const char *source = get_param(cmd, "Source"); */
	/* const char *destination = get_param(cmd, "Destination"); */
	/* const char *dev_type = get_param(cmd, "DevType"); */
	const char *rtsp_msg_type = get_param(cmd, "RtspMsgType");
	/* const char *wfd_session_id = get_param(cmd, "WfdSessionID"); */
	int (*dev_send_frame)(const char *);
	char string_cmd[MIRACAST_CMD_LEN] = { 0 };

	dev_send_frame = dlsym(dut->miracast_lib, "dev_send_frame");
	if (!dev_send_frame)
		return -1;
	sigma_dut_print(dut, DUT_MSG_DEBUG, "miracast_dev_send_frame 1");
	miracast_generate_string_cmd(cmd, string_cmd, sizeof(string_cmd));
	if (!frame_name)
		return 0;
	if (strcasecmp(frame_name, "RTSP") != 0)
		return 0;

	if (!rtsp_msg_type)
		return 0;

	if (strcasecmp(rtsp_msg_type, "PAUSE") == 0 ||
	    strcasecmp(rtsp_msg_type, "TRIGGER-PAUSE") == 0) {
		/* Call RTSP Pause */
		dev_send_frame(string_cmd);
		return 1;
	}

	if (strcasecmp(rtsp_msg_type, "PLAY") == 0 ||
	    strcasecmp(rtsp_msg_type, "TRIGGER-PLAY") == 0) {
		/* Call RTSP Play */;
		dev_send_frame(string_cmd); /* Not for secure playback */
		return 1;
	}

	if (strcasecmp(rtsp_msg_type, "TEARDOWN") == 0 ||
	    strcasecmp(rtsp_msg_type, "TRIGGER-TEARDOWN") == 0) {
		dev_send_frame(string_cmd); /* RTSP Teardown */
		return 1;
	}

	if (strcasecmp(rtsp_msg_type,"SET_PARAMETER") == 0) {
		const char *set_parameter = get_param(cmd, "SetParameter");
		const char *transportType = get_param(cmd, "TransportType");

		if (set_parameter == NULL && transportType == NULL) {
			send_resp(dut, conn, SIGMA_ERROR,
				  "errorCode,Invalid Set Parameter value");
			return 0;
		}

		if (1) /* (strcasecmp(set_parameter, "Standby") == 0) */ {
			dev_send_frame(string_cmd);
			return 1;
		}
		/* TODO More needs to be implemented when the spec is clearer */
		return 1;
	}

	if (strcasecmp(rtsp_msg_type, "SETUP") == 0) {
		dev_send_frame(string_cmd);
		/* TODO More needs to be implemented when the spec is clearer */
		return 1;
	}

	if (strcasecmp(frame_name, "WFD_ProbeReq") == 0) {
		send_resp(dut, conn, SIGMA_ERROR,
			  "errorCode,Unsupported WFD Probe Request");
		return 0;
	}

	if (strcasecmp(frame_name, "WFD_ServiceDiscReq") == 0) {
		send_resp(dut, conn, SIGMA_ERROR,
			  "errorCode,Unsupported WFD Service Discovery");
		return 0;
	}

	send_resp(dut, conn, SIGMA_ERROR,
		  "errorCode,Unsupported dev_send_frame");
	return 0;
}


int miracast_dev_exec_action(struct sigma_dut *dut, struct sigma_conn *conn,
			     struct sigma_cmd *cmd)
{
	const char *service_type = get_param(cmd,"ServiceType");
	int (*dev_exec_action)(const char *);
	char string_cmd[MIRACAST_CMD_LEN] = { 0 };

	sigma_dut_print(dut, DUT_MSG_DEBUG, "miracast_dev_exec_frame");

	if (service_type) {
		char resp_buf[128];

		sigma_dut_print(dut, DUT_MSG_DEBUG, "MDNS Instance Name = %s",
				dut->mdns_instance_name);
		strlcpy(resp_buf, "InstanceName,", sizeof(resp_buf));
		strlcat(resp_buf + strlen(resp_buf), dut->mdns_instance_name,
			sizeof(resp_buf) - strlen(resp_buf));
		send_resp(dut, conn, SIGMA_COMPLETE, resp_buf);
		return 0;
	}

	miracast_generate_string_cmd(cmd, string_cmd, sizeof(string_cmd));
	dev_exec_action = dlsym(dut->miracast_lib, "dev_exec_action");
	if (!dev_exec_action)
		return -2;
	return dev_exec_action(string_cmd);
}


int miracast_preset_testparameters(struct sigma_dut *dut,
				   struct sigma_conn *conn,
				   struct sigma_cmd *cmd)
{
	const char *mdns_disc = get_param(cmd, "mdns_disc");
	const char *mdns_role = get_param(cmd, "mdns_role");
	char string_cmd[MIRACAST_CMD_LEN];
	int ret = 0;
	char string_resp[64] = { 0 };
	int (*extn_sta_preset_test_parameter)(const char *, char *, int);

	miracast_load(dut);
	miracast_generate_string_cmd(cmd, string_cmd, sizeof(string_cmd));
	extn_sta_preset_test_parameter =
		dlsym(dut->miracast_lib, "sta_preset_testparameters");
	if (!extn_sta_preset_test_parameter)
		return -1;
	ret = extn_sta_preset_test_parameter(string_cmd, string_resp,
					     sizeof(string_resp));
	if (ret == SIGMA_ERROR) {
		send_resp(dut, conn, SIGMA_ERROR,
			  "Miracast extension reported error in the command sta_preset_testparameters");
		return 0;
	}

	if (mdns_disc && mdns_role) {
		if (strlen(string_resp))
			strlcpy(dut->mdns_instance_name, string_resp,
				sizeof(dut->mdns_instance_name));
		else
			dut->mdns_instance_name[0] = '\0';
	}

	return 1;
}


static int get_p2p_peers(char *respbuf, size_t bufsize)
{
	char addr[1024], cmd[64];
	char *intf = get_main_ifname();
	int ret;
	char *pos, *end;

	pos = respbuf;
	end = respbuf + bufsize;

	if (wpa_command_resp(intf, "P2P_PEER FIRST", addr, 128) >= 0) {
		addr[17] = '\0';
		strlcpy(respbuf, addr, bufsize);
		pos += strlen(respbuf);
		snprintf(cmd, sizeof(cmd), "P2P_PEER NEXT-%s", addr);
		memset(addr, 0, sizeof(addr));
		while (wpa_command_resp(intf, cmd, addr, sizeof(addr)) >= 0) {
			if (memcmp(addr, "FAIL", 4) == 0)
				break;
			addr[17] = '\0';
			ret = snprintf(pos, end - pos, " %s", addr);
			if (ret < 0 || ret >= end - pos)
				break;
			pos += ret;
			snprintf(cmd, sizeof(cmd), "P2P_PEER NEXT-%s", addr);
			memset(addr, 0, sizeof(addr));
		}
	}

	return 0;
}


int miracast_cmd_sta_get_parameter(struct sigma_dut *dut,
				   struct sigma_conn *conn,
				   struct sigma_cmd *cmd)
{
	/* const char *intf = get_param(cmd, "Interface"); */
	/* const char *program = get_param(cmd, "Program"); */
	const char *parameter = get_param(cmd, "Parameter");
	char resp_buf[1024]; /* may need to change depending on number of peer
				devices found */

	if (!parameter) {
		send_resp(dut, conn, SIGMA_COMPLETE, "NULL");
		return 0;
	}

	if (strcasecmp(parameter, "DiscoveredDevList") == 0) {
		int len = strlen("DeviceList,");

		snprintf(resp_buf, sizeof(resp_buf), "DeviceList,");
		get_p2p_peers(resp_buf + len, 1024 - len);
	} else {
		send_resp(dut, conn, SIGMA_ERROR, "Invalid Parameter");
		return 0;
	}

	send_resp(dut, conn, SIGMA_COMPLETE, resp_buf);
	return 0;
}


int miracast_mdns_start_wfd_connection(struct sigma_dut *dut,
				       struct sigma_conn *conn,
				       struct sigma_cmd *cmd)
{
	const char *init_wfd = get_param(cmd, "init_wfd");
	int int_init_wfd = -1;
	char rtsp_session_id[12];
	char cmd_response[128];
	int (*extn_start_wfd_connection)(const char *,
					 const char *, /* Peer IP */
					 int, /* RTSP port number */
					 int, /* WFD Device Type; 0-Source,
						1-P-Sink, 2-Secondary Sink */
					 char *); /* for returning session ID */
	int count = 0;
	char *sig_resp = NULL;

	if (init_wfd)
		int_init_wfd = atoi(init_wfd);

	extn_start_wfd_connection = dlsym(dut->miracast_lib,
					  "start_wfd_connection");
	if (!extn_start_wfd_connection)
		return -1;
	rtsp_session_id[0] = '\0';
	if (int_init_wfd != 0) {
		extn_start_wfd_connection(NULL, NULL, -100,
					  1 - dut->wfd_device_type,
					  rtsp_session_id);
		while (strlen(rtsp_session_id) == 0 && count < 60) {
			count++;
			sleep(1);
		}
		snprintf(cmd_response, sizeof(cmd_response),
			 "result,NULL,GroupID,NULL,WFDSessionID,%s",
			 count == 60 ? "NULL" : rtsp_session_id);
		sig_resp = cmd_response;
	} else {
		extn_start_wfd_connection(NULL, NULL, -100,
					  1 - dut->wfd_device_type, NULL);
		sig_resp = "result,NULL,GroupID,NULL,WFDSessionID,NULL";
	}

	send_resp(dut, conn, SIGMA_COMPLETE, sig_resp);
	return 0;
}


static int cmd_start_wfd_connection(struct sigma_dut *dut,
				    struct sigma_conn *conn,
				    struct sigma_cmd *cmd)
{
	const char *intf = get_param(cmd, "Interface");
	const char *peer_address = get_param(cmd, "PeerAddress");
	const char *init_wfd = get_param(cmd, "init_wfd");
	const char *intent_val = get_param(cmd, "intent_val");
	const char *oper_chan = get_param(cmd, "oper_chn");
	const char *coupled_session = get_param(cmd, "coupledSession");
	const char *tdls = get_param(cmd, "TDLS");
	const char *r2_connection = get_param(cmd, "R2ConnectionType");
	char ssid[128];
	char p2p_dev_address[18];
	char output_intf[16];
	char sig_resp_buf[1024];
	char cmd_buf[256]; /* Command buffer */
	char resp_buf[256]; /* Response buffer to UCC */
	int go_intent = 0;
	int freq;
	int res = 0;
	char buf_peer[4096];
	char *availability = NULL;
	char command[64];
	int avail_bit;
	char ctemp[2];
	char rtspport[5] = { '7', '2', '3', '6', '\0' };
	int is_group_owner = 0;
	char peer_ip_address[32];
	int sm_control_port = 7236;
	char rtsp_session_id[12] = { '\0' };
	int (*extn_start_wfd_connection)(const char *,
					 const char *, /* Peer IP */
					 int, /* RTSP port number */
					 int, /* WFD Device Type; 0-Source,
						 1-P-Sink, 2-Secondary Sink */
					 char *); /* for returning session ID */
	int count = 0;

	if (r2_connection) {
		if (strcasecmp(r2_connection, "Infrastructure") == 0)
			return miracast_mdns_start_wfd_connection(dut, conn,
								  cmd);
	}

	if (coupled_session && atoi(coupled_session) == 1) {
		send_resp(dut, conn, SIGMA_ERROR,
			  "errorCode,Coupled Session is unsupported");
		return 0;
	}

	if (tdls && atoi(tdls) == 1) {
		send_resp(dut, conn, SIGMA_ERROR,
			  "errorCode,TDLS is unsupported");
		return 0;
	}

	if (intent_val) {
		go_intent = atoi(intent_val);
		if (go_intent > 15)
			go_intent = 1;
	}

	if (p2p_discover_peer(dut, intf, peer_address, 1) < 0) {
		send_resp(dut, conn, SIGMA_ERROR,
			  "errorCode,Could not find peer");
		return 0;
	}

	snprintf(cmd_buf, sizeof(cmd_buf), "P2P_CONNECT %s", peer_address);

	switch (dut->wps_method) {
	case WFA_CS_WPS_PIN_DISPLAY:
		snprintf(cmd_buf + strlen(cmd_buf),
			 sizeof(cmd_buf) - strlen(cmd_buf), " %s display",
			 dut->wps_pin);
		break;
	case WFA_CS_WPS_PIN_LABEL:
		snprintf(cmd_buf + strlen(cmd_buf),
			 sizeof(cmd_buf) - strlen(cmd_buf), " pin label");
		break;
	case WFA_CS_WPS_PIN_KEYPAD:
		snprintf(cmd_buf + strlen(cmd_buf),
			 sizeof(cmd_buf) - strlen(cmd_buf), " %s keypad",
			 dut->wps_pin);
		break;
	case WFA_CS_WPS_PBC:
	default: /* Configuring default to PBC */
		snprintf(cmd_buf + strlen(cmd_buf),
			 sizeof(cmd_buf) - strlen(cmd_buf), " pbc");
		break;
	}

	if (dut->persistent) {
		snprintf(cmd_buf + strlen(cmd_buf),
			 sizeof(cmd_buf) - strlen(cmd_buf), " persistent");
	}
	snprintf(cmd_buf + strlen(cmd_buf), sizeof(cmd_buf) - strlen(cmd_buf),
		 " go_intent=%d", go_intent);

	if (init_wfd && atoi(init_wfd) == 0) {
		snprintf(cmd_buf + strlen(cmd_buf),
			 sizeof(cmd_buf) - strlen(cmd_buf), " auth");
	}

	if (oper_chan) {
		int chan;

		chan = atoi(oper_chan);
		if (chan >= 1 && chan <= 13)
			freq = 2407 + chan * 5;
		else if (chan == 14)
			freq = 2484;
		else
			freq = 5000 + chan * 5;

		snprintf(cmd_buf + strlen(cmd_buf),
			 sizeof(cmd_buf) - strlen(cmd_buf), " freq=%d", freq);
	}

	/* WFD SESSION AVAILABILITY CHECK */

	memset(buf_peer, 0, sizeof(buf_peer));
	snprintf(command, sizeof(command), "P2P_PEER %s", peer_address);
	strlcpy(dut->peer_mac_address, peer_address,
		sizeof(dut->peer_mac_address));
	if (wpa_command_resp(intf, command, buf_peer, sizeof(buf_peer)) >= 0 &&
	    strlen(buf_peer) != 0)
		availability = strstr(buf_peer, "wfd_subelems=");

	if (!availability || strlen(availability) < 21) {
		sigma_dut_print(dut, DUT_MSG_INFO, "Did not get WFD SUBELEMS");
		send_resp(dut, conn, SIGMA_COMPLETE,
			  "result,NULL,GroupID,NULL,WFDSessionID,NULL");
		return 0;
	}

	/* Extracting Availability Bit */
	ctemp[0] = availability[21];
	ctemp[1] = '\0';
	avail_bit = (int) strtol(ctemp, NULL, 16);

	if ((avail_bit & 0x3) == 0) {
		send_resp(dut, conn, SIGMA_COMPLETE,
			  "result,NULL,GroupID,NULL,WFDSessionID,NULL");
		return 0;
	}

	/* Extract RTSP Port for Sink */

	if (dut->wfd_device_type != 0) {
		if (strlen(availability) >= 23) {
			availability += 23;
			if (availability[0])
				snprintf(rtspport, 5, "%s", availability);
		}
		sigma_dut_print(dut, DUT_MSG_INFO,
				"rtsp_port = %s, availability = %s ",
				rtspport, availability);
		session_management_control_port = (int) strtol(rtspport, NULL,
							       16);
		sigma_dut_print(dut, DUT_MSG_INFO,
				"SessionManagementControlPort = %d",
				session_management_control_port);
	}

	memset(resp_buf, 0, sizeof(resp_buf));
	res = wpa_command_resp(intf, cmd_buf, resp_buf, sizeof(resp_buf));
	if (res < 0) {
		sigma_dut_print(dut, DUT_MSG_ERROR,
				"wpa_command_resp failed");
		return 1;
	}
	if (strncmp(resp_buf, "FAIL", 4) == 0) {
		sigma_dut_print(dut, DUT_MSG_INFO,
				"wpa_command: Command failed (FAIL received)");
		return 1;
	}

	if (init_wfd && atoi(init_wfd) == 0) {
		/* Start thread to wait for P2P connection */
		miracast_rtsp_thread_create(dut, conn, cmd);
		send_resp(dut, conn, SIGMA_COMPLETE,
			  "result,NULL,GroupID,NULL,WFDSessionID,NULL");
		return 0;
	}

	res = get_p2p_connection_event(dut, intf, output_intf,
				       sizeof(output_intf), &is_group_owner);
	sigma_dut_print(dut, DUT_MSG_DEBUG, "p2p connection done %d",
			is_group_owner);
	if (res < 0) {
		sigma_dut_print(dut, DUT_MSG_ERROR,
				"Group Formation did not complete");
		return 1;
	}

	snprintf(sig_resp_buf, sizeof(sig_resp_buf), "result");

	if (is_group_owner) {
		stop_dhcp(dut, output_intf,1);
		snprintf(sig_resp_buf + strlen(sig_resp_buf),
			 sizeof(sig_resp_buf) - strlen(sig_resp_buf), ",GO");
		start_dhcp(dut, output_intf,1);
		sleep(5);
	} else {
		snprintf(sig_resp_buf + strlen(sig_resp_buf),
			 sizeof(sig_resp_buf) - strlen(sig_resp_buf),
			 ",CLIENT");
		miracast_start_dhcp_client(dut, output_intf);
		sleep(5);
	}

	snprintf(sig_resp_buf + strlen(sig_resp_buf),
		 sizeof(sig_resp_buf) - strlen(sig_resp_buf), ",GroupID,");

	res = get_wpa_status(output_intf, "p2p_device_address",
			     p2p_dev_address, sizeof(p2p_dev_address));
	if (res < 0)
		return -1;
	sigma_dut_print(dut, DUT_MSG_INFO, "p2p_dev_address %s",
			p2p_dev_address);
	strlcpy(sig_resp_buf + strlen(sig_resp_buf), p2p_dev_address,
		sizeof(sig_resp_buf) - strlen(sig_resp_buf));

	res = get_wpa_status(output_intf, "ssid", ssid, sizeof(ssid));
	if (res < 0) {
		sigma_dut_print(dut, DUT_MSG_DEBUG,
				"get_wpa_status failed to get ssid");
		return -1;
	}

	snprintf(sig_resp_buf + strlen(sig_resp_buf),
		 sizeof(sig_resp_buf) - strlen(sig_resp_buf),
		 " %s,WFDSessionId,", ssid);

	if (!is_group_owner) {
		if (get_peer_ip_p2p_client(dut, peer_ip_address, output_intf,
					   60) < 0) {
			send_resp(dut, conn, SIGMA_ERROR,
				  "Could not get remote IP");
			return 0;
		}
	} else {
		if (get_peer_ip_p2p_go(dut, peer_ip_address, peer_address,
				       30) < 0) {
			send_resp(dut, conn, SIGMA_ERROR,
				  "Could not get remote IP");
			return 0;
		}
	}

	if (dut->wfd_device_type != 0)
		sm_control_port = (int) strtol(rtspport, NULL, 16);
	else
		sm_control_port = 7236;

	extn_start_wfd_connection = dlsym(dut->miracast_lib,
					  "start_wfd_connection");
	if (!extn_start_wfd_connection)
		return -1;
	extn_start_wfd_connection(NULL, peer_ip_address, sm_control_port,
				  1 - dut->wfd_device_type, rtsp_session_id);

	while (strlen(rtsp_session_id) == 0 && count < 60) {
		count++;
		sleep(1);
	}

	if (count == 60)
		strlcpy(rtsp_session_id, "00000000", sizeof(rtsp_session_id));

	strlcat(sig_resp_buf, rtsp_session_id,
		sizeof(sig_resp_buf) - strlen(sig_resp_buf));
	send_resp(dut, conn, SIGMA_COMPLETE, sig_resp_buf);
	return 0;
}


static int cmd_connect_go_start_wfd(struct sigma_dut *dut,
				    struct sigma_conn *conn,
				    struct sigma_cmd *cmd)
{
	const char *intf = get_param(cmd, "Interface");
	const char *p2p_dev_id = get_param(cmd, "P2PdevID");
	/* const char *p2p_group_id = get_param(cmd, "GroupID"); */
	char sig_resp_buf[1024];
	char method[12];
	char cmd_buf[256];
	char buf[256];
	char resp_buf[256];
	int go = 0;
	int res = 0;
	char output_ifname[32];
	char peer_ip_address[32];
	char rtsp_session_id[12];
	int (*extn_connect_go_start_wfd)(const char *,
					 const char * /* Peer IP */,
					 int /* RTSP port number */,
					 int /* WFD Device Type; 0-Source,
						1-P-Sink, 2-Secondary Sink */,
					 char *); /* for returning session ID */

	snprintf(cmd_buf, sizeof(cmd_buf), "P2P_CONNECT %s", p2p_dev_id);

	switch (dut->wps_method) {
	case WFA_CS_WPS_PBC:
		snprintf(cmd_buf + strlen(cmd_buf),
			 sizeof(cmd_buf) - strlen(cmd_buf), " pbc");
		strlcpy(method, "pbc", sizeof(method));
		break;
	case WFA_CS_WPS_PIN_DISPLAY:
		snprintf(cmd_buf + strlen(cmd_buf),
			 sizeof(cmd_buf) - strlen(cmd_buf), " %s display",
			 dut->wps_pin);
		strlcpy(method, "display", sizeof(method));
		break;
	case WFA_CS_WPS_PIN_LABEL:
		snprintf(cmd_buf + strlen(cmd_buf),
			 sizeof(cmd_buf) - strlen(cmd_buf), " pin label");
		strlcpy(method, "label", sizeof(method));
		break;
	case WFA_CS_WPS_PIN_KEYPAD:
		snprintf(cmd_buf + strlen(cmd_buf),
			 sizeof(cmd_buf) - strlen(cmd_buf), " %s keypad",
			 dut->wps_pin);
		strlcpy(method, "keypad", sizeof(method));
		break;
	default: /* Configuring to PBC */
		snprintf(cmd_buf + strlen(cmd_buf),
			 sizeof(cmd_buf) - strlen(cmd_buf), " pbc");
		strlcpy(method, "pbc", sizeof(method));
		break;
	}
	snprintf(cmd_buf + strlen(cmd_buf),
		 sizeof(cmd_buf) - strlen(cmd_buf), " join");

	/* run provisional discovery */
	if (p2p_discover_peer(dut, intf, p2p_dev_id, 0) < 0) {
		send_resp(dut, conn, SIGMA_ERROR,
			  "ErrorCode,Could not discover the requested peer");
		return 0;
	}

	snprintf(buf, sizeof(buf), "P2P_PROV_DISC %s %s", p2p_dev_id, method);
	if (wpa_command(intf, buf) < 0) {
		sigma_dut_print(dut, DUT_MSG_INFO,
				"Failed to send provision discovery request");
		return -2;
	}

	res = wpa_command_resp(intf, cmd_buf, resp_buf, sizeof(resp_buf));
	if (res < 0) {
		sigma_dut_print(dut, DUT_MSG_ERROR,
				"wpa_command_resp failed");
		return 1;
	}
	if (strncmp(resp_buf, "FAIL", 4) == 0) {
		send_resp(dut, conn, SIGMA_ERROR,
			  "errorCode,failed P2P connection");
		return 0;
	}

	res = get_p2p_connection_event(dut, intf, output_ifname,
				       sizeof(output_ifname), &go);
	if (res < 0) {
		send_resp(dut, conn, SIGMA_ERROR,
			  "errorCode,failed P2P connection");
		return 0;
	}

	miracast_start_dhcp_client(dut, output_ifname);

	if (get_peer_ip_p2p_client(dut, peer_ip_address, output_ifname,
				   30) < 0) {
		send_resp(dut, conn, SIGMA_ERROR, "Could not get remote IP");
		return 0;
	}

	if (dut->wfd_device_type != 0) {
		char rtsp_buff[1000], cmd_buff[32];
		char *sub_elem = NULL;
		char rtspport[5] = { '7', '2', '3', '6', '\0' };

		sigma_dut_print(dut, DUT_MSG_DEBUG,
				"Log --- p2p address = %s", p2p_dev_id);
		snprintf(cmd_buff, sizeof(cmd_buff), "P2P_PEER %s", p2p_dev_id);
		if (wpa_command_resp(output_ifname, cmd_buff, rtsp_buff,
				     sizeof(rtsp_buff)) >= 0 &&
		    strlen(rtsp_buff) != 0)
			sub_elem = strstr(rtsp_buff, "wfd_subelems=");

		/* Extract RTSP Port for Sink */
		if (sub_elem && strlen(sub_elem) >= 23) {
			sub_elem += 23;
			snprintf(rtspport, 5, "%s", sub_elem);
			sigma_dut_print(dut, DUT_MSG_DEBUG,
				"rtsp_port = %s, subElem = %s",
				rtspport, sub_elem);
		}
		session_management_control_port = (int) strtol(rtspport, NULL,
							       16);
		sigma_dut_print(dut, DUT_MSG_DEBUG,
				"SessionManagementControlPort = %d",
				session_management_control_port);

	} else {
		session_management_control_port = 7236;
	}

	extn_connect_go_start_wfd = dlsym(dut->miracast_lib,
					  "connect_go_start_wfd");
	if (!extn_connect_go_start_wfd)
		return -1;
	rtsp_session_id[0] = '\0';
	extn_connect_go_start_wfd(NULL, peer_ip_address,
				  session_management_control_port,
				  1 - dut->wfd_device_type, rtsp_session_id);
	/* Null terminating regardless of what was returned */
	rtsp_session_id[sizeof(rtsp_session_id) - 1] = '\0';
	snprintf(sig_resp_buf, sizeof(sig_resp_buf), "WFDSessionId,%s",
		 rtsp_session_id);

	send_resp(dut, conn, SIGMA_COMPLETE, sig_resp_buf);
	return 0;
}


static int cmd_sta_generate_event(struct sigma_dut *dut,
				  struct sigma_conn *conn,
				  struct sigma_cmd *cmd)
{

	/* const char *intf = get_param(cmd, "Interface"); */
	/* const char *program = get_param(cmd, "Program"); */
	const char *type = get_param(cmd, "Type");
	char string_cmd[MIRACAST_CMD_LEN];
	int (*extn_sta_generate_event)(const char *);

	if (!type) {
		send_resp(dut, conn, SIGMA_INVALID,
			  "errorCode, Invalid Type for Generate Event");
		return 0;
	}
	miracast_generate_string_cmd(cmd, string_cmd, sizeof(string_cmd));
	extn_sta_generate_event = dlsym(dut->miracast_lib,
					"sta_generate_event");
	if (!extn_sta_generate_event)
		return -1;
	if (strcasecmp(type, "UIBC_Gen") == 0 ||
	    strcasecmp(type, "UIBC_HID") == 0) {
		extn_sta_generate_event(string_cmd);
	} else if (strcasecmp(type, "FrameSkip") == 0) {
		return 1;
	} else if (strcasecmp(type, "InputContent") == 0) {
		send_resp(dut, conn, SIGMA_COMPLETE, NULL);
		return 0;
	} else if (strcasecmp(type, "I2cRead") == 0) {
		send_resp(dut, conn, SIGMA_ERROR,
			  "errorCode,Unsupported Type for Generate Event");
		return 0;
	} else if (strcasecmp(type, "I2cWrite") == 0) {
		send_resp(dut, conn, SIGMA_ERROR,
			  "errorCode, Unsupported Type for Generate Event");
		return 0;
	} else if (strcasecmp(type, "IdrReq") == 0) {
		if (dut->wfd_device_type == 0) { /* Source */
			send_resp(dut, conn, SIGMA_ERROR,
				  "errorCode, Unsupported Type for Generate Event");
		} else {
			send_resp(dut, conn, SIGMA_COMPLETE, NULL);
			extn_sta_generate_event(string_cmd);
		}
		return 0;
	}
	return 1;
}


static int cmd_reinvoke_wfd_session(struct sigma_dut *dut,
				    struct sigma_conn *conn,
				    struct sigma_cmd *cmd)
{
	const char *intf = get_param(cmd, "Interface");
	const char *grp_id = get_param(cmd, "GroupID");
	const char *peer_address = get_param(cmd, "peeraddress");
	const char *invitation_action = get_param(cmd, "InvitationAction");
	char buf[256];
	struct wpa_ctrl *ctrl;
	int res, id;
	char *ssid, *pos;
	unsigned int wait_limit;
	char peer_ip_address[32];
	char rtsp_session_id[12];
	int (*extn_start_wfd_connection)(const char *,
					 const char *, /* Peer IP */
					 int, /* RTSP port number */
					 int, /* WFD Device Type; 0-Source,
						 1-P-Sink, 2-Secondary Sink */
					 char *); /* for returning session ID */

	/* All are compulsory parameters */
	if (!intf || !grp_id || !invitation_action || !peer_address) {
		send_resp(dut, conn, SIGMA_INVALID,
			  "errorCode,Invalid parameters for Reinvoke WFD Session");
		return 0;
	}

	if (strcmp(invitation_action, "accept") == 0) {
		/*
		 * In a client-joining-a-running-group case, we need to
		 * separately authorize the invitation.
		 */
		miracast_stop_dhcp_client(dut, NULL);
		sigma_dut_print(dut, DUT_MSG_DEBUG, "Trying to discover GO %s",
				peer_address);
		if (p2p_discover_peer(dut, intf, peer_address, 1) < 0) {
			send_resp(dut, conn, SIGMA_ERROR,
				  "ErrorCode,Could not discover the requested peer");
			return 0;
		}

		snprintf(buf, sizeof(buf), "P2P_CONNECT %s %s join auth",
			 peer_address, dut->wps_method == WFA_CS_WPS_PBC ?
			 "pbc" : dut->wps_pin);
		if (wpa_command(intf, buf) < 0)
			return -2;

		miracast_rtsp_thread_create(dut, conn, cmd);
		return 1;
	}

	ssid = strchr(grp_id, ' ');
	if (!ssid) {
		sigma_dut_print(dut, DUT_MSG_INFO, "Invalid grpid");
		return -1;
	}
	ssid++;
	sigma_dut_print(dut, DUT_MSG_DEBUG,
			"Search for persistent group credentials based on SSID: '%s'",
			ssid);
	if (wpa_command_resp(intf, "LIST_NETWORKS", buf, sizeof(buf)) < 0)
		return -2;
	pos = strstr(buf, ssid);
	if (!pos || pos == buf || pos[-1] != '\t' ||
	    pos[strlen(ssid)] != '\t') {
		send_resp(dut, conn, SIGMA_ERROR,
			  "ErrorCode,Persistent group credentials not found");
		return 0;
	}
	while (pos > buf && pos[-1] != '\n')
		pos--;
	id = atoi(pos);
	snprintf(buf, sizeof(buf), "P2P_INVITE persistent=%d peer=%s",
		 id, peer_address);

	sigma_dut_print(dut, DUT_MSG_DEBUG,
			"Trying to discover peer %s for invitation",
			peer_address);
	if (p2p_discover_peer(dut, intf, peer_address, 0) < 0) {
		send_resp(dut, conn, SIGMA_ERROR,
			  "ErrorCode,Could not discover the requested peer");
		return 0;
	}

	ctrl = open_wpa_mon(intf);
	if (!ctrl) {
		sigma_dut_print(dut, DUT_MSG_ERROR,
				"Failed to open wpa_supplicant monitor connection");
		return -2;
	}

	if (wpa_command(intf, buf) < 0) {
		sigma_dut_print(dut, DUT_MSG_INFO,
				"Failed to send invitation request");
		wpa_ctrl_detach(ctrl);
		wpa_ctrl_close(ctrl);
		return -2;
	}

	res = get_wpa_cli_event(dut, ctrl, "P2P-INVITATION-RESULT",
				buf, sizeof(buf));
	wpa_ctrl_detach(ctrl);
	wpa_ctrl_close(ctrl);
	if (res < 0)
		return -2;

	miracast_load(dut);

	sigma_dut_print(dut, DUT_MSG_DEBUG, "Waiting to start DHCP");

	/* Calling Miracast multimedia APIs */
	if (dut->wfd_device_type != 0)
		wait_limit = HUNDRED_SECOND_TIMEOUT;
	else
		wait_limit = 500;

	stop_dhcp(dut, intf, 1);
	/* For GO read the DHCP lease file */
	sigma_dut_print(dut, DUT_MSG_INFO, "Waiting to start DHCP server");
	start_dhcp(dut, intf, 1);
	sleep(5);
	if (get_peer_ip_p2p_go(dut, peer_ip_address, dut->peer_mac_address,
			       wait_limit) < 0) {
		sigma_dut_print(dut, DUT_MSG_ERROR, "Could not get peer IP");
		return -2;
	}

	extn_start_wfd_connection = dlsym(dut->miracast_lib,
					  "start_wfd_connection");
	if (extn_start_wfd_connection) {
		extn_start_wfd_connection(NULL, peer_ip_address,
					  session_management_control_port,
					  1 - dut->wfd_device_type,
					  rtsp_session_id);
	} else {
		sigma_dut_print(dut, DUT_MSG_INFO,
				"dlsym seems to have error %p %p",
				dut->miracast_lib,
				extn_start_wfd_connection);
	}

	return 1;
}


static int req_intf_peer(struct sigma_cmd *cmd)
{
	if (!get_param(cmd, "interface") ||
	    !get_param(cmd, "PeerAddress"))
		return -1;
	return 0;
}


static int req_intf_p2pdev_grpid(struct sigma_cmd *cmd)
{
	if (!get_param(cmd, "interface") ||
	    !get_param(cmd, "P2pdevID") ||
	    !get_param(cmd, "GroupID"))
		return -1;
	return 0;
}


static int req_intf_prog_type(struct sigma_cmd *cmd)
{
	const char *prog = get_param(cmd, "Program");

	if (!get_param(cmd, "interface") ||
	    !get_param(cmd, "Type") ||
	    !prog || strcmp(prog, "WFD") != 0)
		return -1;
	return 0;
}


static int req_intf_peeradd_inv(struct sigma_cmd *cmd)
{
	if (!get_param(cmd, "interface") ||
	    !get_param(cmd, "peerAddress") ||
	    !get_param(cmd, "InvitationAction"))
		return -1;
	return 0;
}


void miracast_register_cmds(void)
{
	sigma_dut_reg_cmd("start_wfd_connection", req_intf_peer,
			  cmd_start_wfd_connection);
	sigma_dut_reg_cmd("connect_go_start_wfd", req_intf_p2pdev_grpid,
			  cmd_connect_go_start_wfd);
	sigma_dut_reg_cmd("sta_generate_event", req_intf_prog_type,
			  cmd_sta_generate_event);
	sigma_dut_reg_cmd("reinvoke_wfd_session", req_intf_peeradd_inv,
			  cmd_reinvoke_wfd_session);
}
