/*  DateBook.c  */

/****************************************************************************
*									    *
*		     DateBook.c						    *
*									    *
*	           by Robert Hardy					    *
*	    								    *
*      Copyright  April  87 - HardKore Software -  Port Coquitlam, B.C.     *
*	     released for free distribution as long as 			    *
*	   this copyright notice is retained in the file.		    *
*									    *
*									    *
*		  							    *
*    USAGE : DateBook							    *
*									    *
*    NOTE  : Looks for file `s:dates.dat' and checks for comming events.    *
*	     Once the difference between the current date and the event's   *
*	     date is less than specified warning, the event is displayed.   *
*	     Records with no date or that have already passed are deleted.  *
*	     If the Event field starts with a `*', when the event has       *
*	     passed instead of being deleted the year will be incremented.  *
*	     A `!' at the start of the event field will increment the       *
*	     month after the event has passed.
*									    *
*****************************************************************************/

#include "datebook.h"

int input, output;

void main()
{
    int changed, copy = 0;
    char date[7], expanded_date[40];

    if (Open_Files () == ERROR)
	exit(0);
    GetDate(date);
    expand_date(date, expanded_date);
    printf("\n\n%s\n\n\t\tComing Events  %s%s0m\n\n", HEADER, expanded_date, CSI);

    while(  read( input, (char *) &rec, sizeof(rec) )  )
    {
	if(  ( changed = Check_Event(date) )  != 0  )
	    write( output, (char *) &rec, sizeof(rec) );
	if(changed < 1)
	    ++copy;
    }
    Close_Files(copy);
    printf("\n\n\t  That's All Folks !!\n\n");
}

int Check_Event(dt)
    char *dt;
{
    int diff;
    int add_year = 0;

    if( !(isdigit(rec.date[0])) )
	return FALSE; 

    diff = get_diff(rec.date, dt);
    if(diff == EQUAL || diff == 1)
    {
	print_event();
    }
    else if(diff == -1)
    {
	printf("%s",REVERSE);
	print_event();
	printf("%s",NORMAL);
	if(rec.event[0] == '!')
	{
	    int month;
	    
	    month = convert2digits(rec.date[MONTH_OFFSET]);
	    if(++month > 12)
	    {
		month = 1;
		add_year = TRUE;
	    }
	    rec.date[MONTH_OFFSET] = month/10 + '0';
	    rec.date[MONTH_OFFSET + 1] = month%10 + '0';
	    if(!add_year)
	    {
		rec.warning = abs(rec.warning);
		return -1; 
	    }
	}
	if(rec.event[0] == '*' || add_year)
	{
	    int year;
	    year = convert2digits(rec.date[YEAR_OFFSET]);
	    if (++year > 100)
		year = 0;
	    rec.date[YEAR_OFFSET] = year/10 + '0';
	    rec.date[YEAR_OFFSET + 1] = year%10 + '0';
	    rec.warning = abs(rec.warning);
	    return -1; 
	}
	return FALSE;
    }
    else if(  rec.warning < 0 && ( rec.freq == 0 || !(diff % rec.freq) )  )
    {
	print_event();
    }
    else if(rec.warning >= diff)
    {
	print_event();
	rec.warning = -rec.warning;
	return -1;
    }
    return TRUE;
}

int get_diff(str1, str2)
    char *str1, *str2;
{
    register int years = 0, months = 0, days = 0;

    days = convert2digits(str1 + DAY_OFFSET) - convert2digits(str2 + DAY_OFFSET);
    if(days < 0)
    {
	days += 30;
	--months;
    }
    months += convert2digits(str1 + MONTH_OFFSET) - convert2digits(str2 + MONTH_OFFSET);
    if(months < 0)
    {
	months += 12;
	--years;
    }
    years += convert2digits(str1 + YEAR_OFFSET) - convert2digits(str2 + YEAR_OFFSET);
    if(years < 0)
	return -1;
    return years * 365 + months * 30 + days;
}

int convert2digits(str)
    char *str;
{
    return ( (*str++ - '0') * 10 + *str - '0');
}

void GetDate(dt)
    char *dt;
{
    long now;
    register struct tm *tp;

    time(&now);
    tp = localtime(&now);

    *dt++ = tp->tm_year/10 + '0';
    *dt++ = tp->tm_year%10 + '0';
    *dt++ = (tp->tm_mon + 1)/10 + '0';
    *dt++ = (tp->tm_mon + 1)%10 + '0';
    *dt++ = tp->tm_mday/10 + '0';
    *dt++ = tp->tm_mday%10 + '0';
    *dt = 0;
}


void print_event()
{
    char date[40];

    expand_date(rec.date, date);

    if (rec.event[0] == '*' || rec.event[0] == '!')
	printf("%-40.40s %-30s %.5s\n", &rec.event[1], date, rec.time);
    else	
	printf("%-40.40s %-30s %.5s\n", rec.event, date, rec.time);

}

int Open_Files()
{
    if(  (input = open(FILENAME, O_RDONLY, PROT) ) == ERROR  ) 
    {
	printf("\n\n File `%s' does not exist.\n Use `CheckDateBook' to create the it.\n\n", FILENAME);
	return ERROR;
    }
    if(  ( output = open(TEMP_FILE_NAME, O_WRONLY | O_CREAT, PROT) ) == ERROR  )
    {
	printf("\n Cannot open temporary file `%s'.\n\n",TEMP_FILE_NAME);
	close(input);
	return ERROR;
    }
    return OK;
}

void Close_Files(copy)
    int copy;
{
    close(input);
    close(output);
    #ifndef DEBUG
	if(copy)
	    Execute(CLEAN_UP1, 0, 0);
	Execute(CLEAN_UP2, 0, 0);
    #endif
}

void expand_date(dt, string)
    char *dt, *string;
{
    register int year, mon, day;
    int w_day;

    *string = 0;

    year = convert2digits(dt+YEAR_OFFSET);
    mon = convert2digits(dt+MONTH_OFFSET);
    day = convert2digits(dt+DAY_OFFSET);

    w_day = (year/4 + year + months[mon].fix + day) % 7 + 1;
    if ( (year % 4 == 0) && (mon < 3) )
	--w_day;
    if (w_day <= 0)
	w_day += 7;

    strcpy(string, WeekName[w_day]);
    while (*string)
	++string;		/* search for eos */
    strcpy(string, ", ");
    string += 2;

    strcpy(string, months[mon].Name);
 
    while (*string)
	++string;	/* search for eos */

    *string++ = ' ';	/* space */
 
    *string++ = *(dt + DAY_OFFSET);
    *string++ = *(dt + 1 + DAY_OFFSET);

    strcpy(string, ", 19");
    string += 4;

    *string++ = *(dt + YEAR_OFFSET);
    *string++ = *(dt + 1 + YEAR_OFFSET);
            
    *string = 0;		/* null at end */
}
