/* Burn - the Whitix shell */

#include <syscalls.h>
#include <stdio.h>
#include <ctype.h>
#include <errno.h>

#include "builtins.h"

#define BUFFER_SIZE 32768
char buffer[BUFFER_SIZE];

char currPath[PATH_MAX];

#define MAJOR_BURN_VERSION		0
#define MINOR_BURN_VERSION		3

int ProcessLine(char* buffer)
{
	/* Strtok isn't flexible enough */
	char* array[100];
	int i=0;
	int j=0;

	int length=strlen(buffer);

	memset(array,0,100*sizeof(char*));

	while (i < length)
	{
		/* Skip any whitespace */
		while (isspace(buffer[i]))
			++i;

		if (buffer[i] != '\0')
			array[j++]=&buffer[i];
		else{
			/* End of buffer */
			array[j]=NULL; /* Just null-terminate the array for safety */
			break;
		}

		while (buffer[i] != '\0' && !isspace(buffer[i]))
			++i;

		/* Terminate the token string */
		if (buffer[i] != '\0' && i < length)
		{
			buffer[i]='\0';
			++i;
		}
	}

	/* First token should be command */
	if (!array[0])
		return 0; /* Nothing to evaluate */

	struct CmdTable* curr=btTable;

	while (curr->command)
	{
		if (!strcmp(curr->command,array[0]))
		{
			curr->function(array);
			break;
		}

		curr++;
	}

	if (!curr->command)
	{
		/* Try to execute */
		if (BtInExec(array))
			printf("Command %s not found\n",array[0]);
	}

#if 0
	}else{
		/* Ready for I/O redirection */
		int fds[]={0,1,2};
		int fd;
		
		/* Search for the > symbol */
		for (i=0; i<j; i++)
		{
			if (!strcmp(array[i],">"))
				break;
		}

		/* I/O redirection is required */
		if (i != j)
		{
			if (!array[i+1])
			{
				printf("burn: I/O redirection requires a filename\n");
				return 0;
			}

			/* Either way, it'll still overwrite the stuff at the beginning of the file. Use fopen? */
			fd=SysOpen(array[i+1],FILE_CREATE_OPEN | FILE_READ | FILE_WRITE,0);
			if (fd < 0)
			{
				printf("Failed to open %s\n",array[i+1]);
				return 0;
			}

			SysTruncate(fd,0);

			fds[0]=fd;
			array[i]=NULL;
			array[i+1]=NULL;
		}

		int pid=SysCreateProcess(array[0],fds,&array[1]);
		if (pid < 0)
			printf("Command %s not found\n",array[0]);
		else
			SysWaitForProcessFinish(pid);

		if (i != j)
			SysClose(fd);
	}
#endif

	return 0;
}

int gets(char* buffer,int length)
{
	int c,i=0;

	while (i<length)
	{
		c=getchar();

		/* Don't add extended characters */
		if (c >= 0x80)
			continue;

		if (c == EOF || c == '\n')
			break;
		
		if (c == '\b')
		{
			if (i > 0)
			{
				buffer[i]=' ';
				--i;
				putchar('\b');
			}
		}else{
			buffer[i++]=(char)c;
		}
	}

	buffer[i]='\0';

	return 0;
}

int main(int argc,char* argv[])
{
	printf("Burn shell V%d.0%d\n---------------\nPrint help for a list of commands\n", MAJOR_BURN_VERSION, MINOR_BURN_VERSION);

	/* Get the current directory now, and only update when cd is called */
	SysGetCurrDir(currPath,PATH_MAX);

	while (1)
    {	
		printf("%s>",currPath);
		gets(buffer,BUFFER_SIZE-1);

		ProcessLine(buffer);
	}

	return 0;
}
