#include	"unp.h"
#include	"protocol.h"

#define	MAXN	4096		/* max # bytes to request from server */

#define	HostName	"192.168.0.136"
#define Port		"22201"
#define INSERT		1
#define UPDATE		2
#define DELETE		3

/* declare common header and body */
rcmng_cheader_t		*cheader;
servinfo_t			*ch_servinfo;
char				sndBuffer[MAXN];

int main(int argc, char **argv)
{
	void make_rcmng_cheader(rcmng_cheader_t *, char *, char *, unsigned int, unsigned int);
	void make_servinfo_body(servinfo_t *, const char *);
	void view_common_header(rcmng_cheader_t *);
	void view_body(servinfo_t *);
	int send_to_sh_statusd(char *);
	
	unsigned int	bodylen=0;	
	unsigned int	servType=0;
	unsigned int	header_size;
	int				is_success;

	/* Error Processing Main(argv) Parameter */
	if (argc > 5 || argc < 4)
		err_quit("Usage: rcmng_client <RCID> <SERV_NAME> <servType> [<new string>]\n");

	if (!strncmp(argv[3], "INSERT", 6) && argc == 5)
		servType = INSERT;
	else if (!strncmp(argv[3], "UPDATE", 6) && argc == 5)
		servType = UPDATE;
	else if (!strncmp(argv[3], "DELETE", 6) && argc == 4)
		servType = DELETE;
	else
		err_quit("Wrong servType!! only used [INSERT, UPDATE, DELETE]\n");

	/***************** Make rcmmng common header ***********************/
	cheader = (rcmng_cheader_t *)malloc(sizeof(rcmng_cheader_t));
	if (cheader == NULL)
		err_quit("Cannot allocation rcmng_cheader heap!\n");
		
	if (servType == 1 || servType == 2)
		bodylen = sizeof(servinfo_t);
	else if (servType == 3)
		bodylen = 0;
	make_rcmng_cheader(cheader, argv[1], argv[2], servType, bodylen);
	/*******************************************************************/
	
	/****************** Make Server Info body **************************/
	ch_servinfo = (servinfo_t *)malloc(sizeof(servinfo_t));
	if (!ch_servinfo)
		err_quit("Cannot allocation servinfo_t heap!\n");
	
	memset(sndBuffer, 0, MAXN);
	switch(servType)
	{
		case 1 :
		case 2 :
			make_servinfo_body(ch_servinfo, argv[4]);
			view_common_header(cheader);
			view_body(ch_servinfo);
			/* send to new sh_statusd that changed server information */
			header_size = sizeof(rcmng_cheader_t);
			memcpy(sndBuffer, (char *)cheader, header_size);
			memcpy(sndBuffer + header_size, (char *)ch_servinfo, bodylen);
			break;

		case 3 :
			view_common_header(cheader);
			/* send to new sh_statusd that changed server information */
			header_size = sizeof(rcmng_cheader_t);
			memcpy(sndBuffer, (char *)cheader, header_size);
			break;

		default :
			err_quit("Wrong servType!! exit program!!\n");
			exit(EXIT_FAILURE);
			break;
	}
	/*******************************************************************/
	
	is_success = send_to_sh_statusd(sndBuffer);
	if (is_success)
		fprintf(stdout, "SUCCESS");
	else
		fprintf(stdout, "FAIL\n");
	free(cheader);
	free(ch_servinfo);
	exit(0);
}

void make_rcmng_cheader(rcmng_cheader_t *cheader, char *rcid, char *servname,  unsigned int servicetype, unsigned int bodylen)
{
	strncpy(cheader->rcmng_rcid, rcid, MAX_MNG_RCID);
	strncpy(cheader->rcmng_servName, servname, MAX_SRV_NAME);
	cheader->rcmng_serviceType = servicetype;
	cheader->bodylength = bodylen;
}

void make_servinfo_body(servinfo_t *servinfo, const char *serv_str_info)
{
	int		devide(char **, const char *, char);
	
	char	*rbuffer[1024];
	int		str_num;
	char	delim = '|';

	str_num = devide(rbuffer, serv_str_info, delim);
	
	fprintf(stderr, "serv_str_info number : %d\n", str_num);

	strncpy(servinfo->m_pszServName, rbuffer[0], MAX_SRV_NAME);
	strncpy(servinfo->m_szIpString, rbuffer[1], MAX_IP_STRING);
	servinfo->m_sPort = atoi(rbuffer[2]);
	servinfo->m_ServType = atoi(rbuffer[3]);
	servinfo->m_DeadCount = 0;
	strncpy(servinfo->m_monitorYN, rbuffer[4], 2);
	fflush(stderr);
}

void view_common_header(rcmng_cheader_t *cheader)
{
	fprintf(stderr, "***************** Common Header *******************\n");
	fprintf(stderr, "RCID : %s\n", cheader->rcmng_rcid);
	fprintf(stderr, "SERVER NAME : %s\n", cheader->rcmng_servName);
	fprintf(stderr, "SERVICE TYPE : %d\n", cheader->rcmng_serviceType);
	fprintf(stderr, "BODY LENGTH : %ld\n", cheader->bodylength);
	fprintf(stderr, "***************************************************\n");
}

void view_body(servinfo_t *servinfo)
{
	fprintf(stderr, "***************** Server info Body ****************\n");
	fprintf(stderr, "SERVER NAME : %s\n", servinfo->m_pszServName);
	fprintf(stderr, "IP Address : %s\n", servinfo->m_szIpString);
	fprintf(stderr, "PORT : %d\n", servinfo->m_sPort);
	fprintf(stderr, "SERVER TYPE : %d\n", servinfo->m_ServType);
	fprintf(stderr, "Dead Count : %d\n", servinfo->m_DeadCount);
	fprintf(stderr, "Monitoring Y/N : %s\n", servinfo->m_monitorYN);
	fprintf(stderr, "***************************************************\n");
}

int send_to_sh_statusd(char *sndMessage)
{
	char reply[64];
	int fd;
	int n;
	int resnum;
		
	/* connect to new sh_statusd */
	fd = Tcp_connect(HostName, Port);
	/* send sndMessage to new sh_statusd */
	Write(fd, sndMessage, MAXN);
	/* receive result from new sh_statusd */
	if ( (n = Readn(fd, reply, 64)) == 0)
	{
		err_quit("server returned %d bytes", n);
	}
	resnum = atoi(reply);
	fprintf(stderr, "result value : %d\n", resnum);
	Close(fd);
	
	return resnum;
}
