/*
[]=================================================================[]
	test.c

	Copyright (C) 2001 Feitian Tech. Co. Ltd. All rights reserved.
	by Water Bird
	Created at 16-6-2001   21:25

	Comment : Test CGI.
[]=================================================================[]
*/

#include <string.h>
#include <stdlib.h>
#include <time.h>
#include "md5.h"
#include "test.h"

FILE* stream;

/*
 * a. I assume the root of your web site is "/var/www/html"
 * b. I assume you put the excutable files at "/var/www/cgi-bin"
 */

/* Set the root of your web site. */
#define SITE_ROOT "/Users/apple/Sites"

/* Set the excute access folder. */
#define SITE_CGIBIN "/Library/WebServer/CGI-Executables"

int cgiMain(void)
{
	char name[200];

	cgiHeaderContentType("text/html");

	if(cgiFormNotFound == cgiFormString("UserName", name, 200))
	{
		WriteLogonPage();
	}
	else
	{
		WriteVerifyPage();
	}

	return 0;
}

int WriteLogonPage(void)
{
	int i;
	unsigned int uiRnd;

	char szRndData[21];
	char fileID[21] = {0};

	WriteComment();

	srand( (unsigned)time( NULL ) );
	//printf( "  %6d\n", rand() );
	for(i = 0; i < 20; i++)
	{
		uiRnd = rand();
		szRndData[i] = uiRnd % ('z' - 'a') + 'a';
	}

	szRndData[20] = 0;
	for(i=0;i<21;i++) fileID[i] = szRndData[i];

	stream = fopen(fileID, "w");
	fwrite(szRndData, 20, 1, stream);
	fclose(stream);

	fprintf(cgiOut, "<SCRIPT language=Javascript>\n<!--\n");

	fprintf(cgiOut, "RndData = \"");
	fprintf(cgiOut, szRndData);
	fprintf(cgiOut, "\";\n");

	fprintf(cgiOut, "fileID = \"");
	fprintf(cgiOut, fileID);
	fprintf(cgiOut, "\";\n");

	fprintf(cgiOut, "//-->\n</SCRIPT>\n");

	i = WriteHtmlFile("/test/epass1000/logon.htm");

	return i;
}

void WriteComment(void)
{
	fprintf(cgiOut, "<!--\n"
		"[]=================================================================[]\n\n"
		"    Copyright (C) 2001 Feitian Tech. Co. Ltd. All rights reserved.\n"
		"    by Water Bird\n\n"
		"    Comment : Demonstration how to use ePass 1000 Active Control\n"
		"              in WEB page.\n\n"
		"[]=================================================================[]\n"
		"-->\n\n");
}

int WriteVerifyPage(void)
{
	FILE* fUserData;
	int i;
	unsigned int j;
	int iErr = 1;
	int iContinue = 1;

	char szFileUserData[255] = {0};
	char szFileTemp1[100] = {0};
	char szFileTemp2[100] = {0};
	char szUserName[100] = {0};
	char szPassword[100] = {0};
	char szRndData[21] = {0};
	char fileID[21] = {0};
	char szClientDigest[33] = {0};
	char szServerDigest[33] = {0}; 
	char szTemp[3] = {0};

	unsigned char ucSDigest[16];
	unsigned char ucKey1[16];
	unsigned char ucKey2[16];

	cgiFormString("SN_SERAL", szUserName, 100);
	cgiFormString("fileID", fileID, 21);
	cgiFormString("Digest", szClientDigest, 33);

	if (szUserName[0] == 0 ||
		szClientDigest[0] == 0)
	{
		iErr = -1; // Some unknown error.
	}

	if (iErr == 1)
	{
		strcpy(szFileUserData, SITE_CGIBIN);
		strcat(szFileUserData, "/test/epass1000/user.txt");
		if ((fUserData = fopen(szFileUserData, "r")) == NULL)
			iErr = -2; // User data file not found.
		else
		{
			fgets(szFileTemp1, 100, fUserData);
			fgets(szFileTemp2, 100, fUserData);
			while (feof(fUserData) == 0 && iContinue)
			{
				for(j = 0; j < strlen(szFileTemp1); j++)
					if (szFileTemp1[j] == 13 || szFileTemp1[j] == 10)
						szFileTemp1[j] = 0;

				char* pdest;
				pdest = strstr(szFileTemp1,szUserName);
				if(pdest != NULL)
				{
					iContinue = 0;
					for(j = 0; j < strlen(szFileTemp2); j++)
						if (szFileTemp2[j] == 13 || szFileTemp2[j] == 10)
							szFileTemp2[j] = 0;

					strcpy(szPassword, szFileTemp2);
					continue;
				}

				fgets(szFileTemp1, 100, fUserData);
				fgets(szFileTemp2, 100, fUserData);
			}
			if (iContinue)
				iErr = -3; // User account not found.
	
			fclose(fUserData);
		}
	}



	if (iErr == 1)
	{
		stream = fopen(fileID, "r");
		fgets(szRndData, 21, stream);
		fclose(stream);
		remove(fileID);

		MD5_HMAC(
			szRndData,
			20,
			szPassword,
			strlen(szPassword),
			ucKey1,
			ucKey2,
			ucSDigest);

		for(i = 0; i < 16; i++)
		{
			sprintf(szTemp, "%02X", ucSDigest[i]);
			strcat(szServerDigest, szTemp);
		}

		if (strcmp(szServerDigest, szClientDigest) != 0)
			iErr = -4; // Bad user.
	}

	WriteComment();
	WriteHtmlFile("/test/epass1000/verify_head_inc.htm");

	// Output the result.
	switch(iErr)
	{
	case 1:
		fprintf(cgiOut, 
			"<h2 align=\"center\"><font color=\"#0000FF\">Congratulation, %s ! You can get in now.</FONT></h2>\n",
			szUserName);
		break;
	case -1:
		fprintf(cgiOut,
			"<h2 align=\"center\"><font color=\"#FF0000\">Error : Some unknown error occured.</FONT></h2>\n"
			"<P align=\"center\">You'd better to try again.\n");
		break;
	case -2:
		fprintf(cgiOut, 
			"<h2 align=\"center\"><font color=\"#FF0000\">Error : The file named USER.TXT can not be found.</FONT></h2>\n"
			"<P align=\"center\">You should initialize the ePass first.\n");
		break;
	case -3:
		fprintf(cgiOut,
			"<h2 align=\"center\"><font color=\"#FF0000\">Error : The user named \"%s\" not registed yet.</FONT></h2>"
			"<P align=\"center\">You should get an initialized ePass first.",
			szUserName);
		break;
	case -4:
		fprintf(cgiOut,
			"<h2 align=\"center\"><font color=\"#FF0000\">Error : Bad user</FONT></h2>"
			"<P align=\"center\">Oooooooops! Did you forget your password ??");
		break;
	}
	
	WriteHtmlFile("/test/epass1000/verify_foot_inc.htm");

	return 0;
}

int WriteHtmlFile(char* szFileName)
{
	FILE* fHtmlFile;
	char chChar;
	char szHtmlFileName[255];

	strcpy(szHtmlFileName, SITE_ROOT);
	strcat(szHtmlFileName, szFileName);

	if ((fHtmlFile = fopen(szHtmlFileName, "r")) == NULL)
	{
		fprintf(cgiOut, "Error when open file %s.\n", szFileName);
		return -1;
	}

	chChar = fgetc(fHtmlFile);
	while (feof(fHtmlFile) == 0)
	{
		fprintf(cgiOut, "%c" , chChar);
		chChar = fgetc(fHtmlFile);
	}

	fclose(fHtmlFile);

	return 0;
}
