/*---------------------------------------------------------------------
File Name: Redirect.c
Author: Christopher Huyler
Date: February 12, 2002
Description:
Check arguments in command for redirection '<', '>' and '>>' symbols and
change stdin and stdout accordingly.  If one of the symbols does not
contain a file name in the same argument, redirect will asume the
next argument is the file name. All redirection args are removed from
argument list when complete
---------------------------------------------------------------------*/
#include <string.h>

// prototypes
void shift_left(char **);				// shifts all args left one slot
void set_redirect(struct command_struct *);	// checks for redirection
void redirect_in(char *);				// handles input redirection
void redirect_out(char *,char *);     	// handles output redirection


// shift left for array of char arrays
void shift_left(char **argv){
	char **ptr = argv;
	
	while(*ptr != 0){
		*ptr = *(ptr+1);
		ptr++;
	}
}
	
// main redirection function parses arguments for symbols
void set_redirect(struct command_struct *command)
{
	char **argv, 			// argument ptr
		 mode[2];           // file open mode
	int  *argc;             // # of arguments ptr
		
	argv = command->argv;   // set argv ptr to first argument
	argc = command->argc;   // set argc ptr to argc
	
	while(*argv != 0) { // check all arguments in argv for redirection
		if(**argv == '<'){ 	  				// input '<'
			if(*(*argv+1)=='\0')			// check 2nd char of string for eos
			{	 // take next arg as file name		
				shift_left(argv);   		// shift all args left one
				*argc--;            		// subtract 1 from total args
			}
			else // cut off '<'
				(*argv)++;
				
			redirect_in(*argv); 			// send file name to r_in
			shift_left(argv);               // shift all args left one
			*argc--;                        // subtract 1 from total args
		}  // end if '<'
		else {
			if(**argv == '>'){ 	// output '>'	
				if(*(*argv+1)=='\0')
				{	// take next arg as file name
					shift_left(argv);
					*argc--;
					strcpy(mode,"w");
				}
				else {
					if(*(*argv+1)=='>') {
						if(*(*argv+2)=='\0')
						{	// output append '>>' take next arg as file name
							shift_left(argv);
							*argc--;
						}		
						else // cut off '>>'
							(*argv) += 2;
						strcpy(mode,"a");
					}		
					else  {// cut off '>'
						(*argv)++;
						strcpy(mode,"w");
					}
				}
				redirect_out(*argv,mode); 	// send file name to r_out
				shift_left(argv);           // shift all args left 1
				*argc--;                    // subtract 1 from total args
			} // end if '>'
			else   			
				argv++;	// otherwise get next argument
		}
	}
}// end redirect

// change stdin to redirection file
void redirect_in(char *filename)
{
	char *mode;              	// mode to open file
	mode = malloc(2);
	strcpy(mode,"r");           // read mode
	
	if(!freopen(filename,"r",stdin)) {
		fprintf(stderr,"Could not redirect stdin to file %s\n",filename);
		exit(2);
	}
}// end redirect_in

// change stdout to redirection file
void redirect_out(char *filename, char *mode)
{	
	if(!freopen(filename,mode,stdout)) {
		fprintf(stderr,"could not redirect stdout to file %s\n",filename);
		exit(2);
	}
}// end redirect_out

