#include <stdlib.h>
#include <stdio.h>
#include <string.h>
#include <ctype.h>
#include <dos.h>
#include <exec/types.h>
#include <libraries/dosextens.h>

#include <dlg/cron.h>
#include <dlg/misc.h>
#include <dlg/dlg.h>

#include <link/io.h>

#include <proto/dos.h>
#include <proto/exec.h>
#include <proto/dlg.h>

#include <pragmas/dlg.h>

#include <private/Version.h>
#define  ObjRev "1"
const UBYTE version[]="\0$VER: CronEvent " BUILDVER "." ObjRev " ©" COPYRIGHT " by Digerati Dreams "__AMIGADATE__;

void  main(int, char **);
char *GetCommand(char **, int );
void  Usage(char *);
void  CleanUp(char *);

BPTR            sout;
char           *command = NULL;
struct Library *DLGBase = NULL;


void main(int argc, char **argv)

{ULONG  minutes     = 0;
 ULONG  currminutes = 0;
 char   messtype;


 sout = Output();

 if (!(DLGBase = OpenLibrary(DLGNAME,DLGVERSION)))  exit(5);
 if (argc < 2)   Usage(argv[0]);

*argv[1] = toupper(*argv[1]);
 switch(*argv[1])
       {case 'A': messtype = ADDEVENT;
                  break;

        case 'C': messtype = CHANGEDIR;
                  break;

        case 'D': messtype = DELEVENT;
                  break;

        case 'L': messtype = LISTEVENTS;
                  break;

        case 'W': messtype = WHENEVENT;
                  break;

        case 'R': messtype = READFILE;
                  break;

        case 'T': messtype = TABLIST;
                  break;

        case 'Q': messtype = CRONEXIT;
                  break;

         default: AFPrintf(NULL, sout, "\n Error: Unrecognized option <%c>\n\n", *argv[1]);
                  Usage(argv[0]);
                  break;
       }

 if (((messtype==ADDEVENT) && (argc<4))  ||
    (((messtype==DELEVENT) || (messtype==CHANGEDIR) || (messtype==WHENEVENT)) && (argc<3)))
     Usage(argv[0]);

 if (messtype == ADDEVENT)
    {char        *pos;
     struct ATime tm;

     if (!(pos = index(argv[2], ':')))
           minutes = atol(argv[2]);
         else
          {*pos = 0;
           pos++;

           minutes = (atol(argv[2]) * 60) + atol(pos);

           UnpackTime(AmigaTime(), &tm);
           currminutes = (tm.hour * 60) + tm.min;

           if (minutes <= currminutes)
               minutes += (1440 - currminutes);
             else
               minutes -=  currminutes;
          }

     command = GetCommand(argv+3, argc-3);
    }
  else
     if (argc > 2)  command = GetCommand(argv+2, argc-2);

 minutes = CronEvent(messtype, minutes, command);
 if (minutes == NOCRON)  CleanUp("Couldn't find TPTCron's control port");

 switch(messtype)
       {case ADDEVENT:   if (minutes == OUTOFMEM)  CleanUp("Not enough memory to add event");
                         AFPrintf(NULL, sout, "\n Event added successfully\n\n");
                         break;

        case CHANGEDIR:  if (minutes == CNOERR)
                             AFPrintf(NULL, sout, "\n Directory changed successfully\n\n");
                           else
                             CleanUp("Unable to change to specified directory");
                         break;

        case DELEVENT:   AFPrintf(NULL, sout, "\n %d events were deleted\n\n", minutes);
                         break;

        case LISTEVENTS: if (minutes == NOEVENTS)
                             AFPrintf(NULL, sout, "\n There are no events to list\n\n");
                           else
                             AFPrintf(NULL, sout, "\n Event list printed successfully\n\n");
                         break;

        case TABLIST:    if (minutes == NOEVENTS)
                             AFPrintf(NULL, sout, "\n There are no events to list\n\n");
                           else
                             AFPrintf(NULL, sout, "\n CronTab event list printed successfully\n\n");
                         break;

        case WHENEVENT:  if (!minutes)
                             AFPrintf(NULL, sout, "\n Event not found\n\n");
                           else
                            {char  buf[20];

                             SMDate(minutes, buf);
                             AFPrintf(NULL, sout, "\n The event will occur on: %s\n\n", buf);
                            }
                         break;

        case READFILE:   if (minutes == TABNOTFOUND)
                             CleanUp("Unable to read CronTab file");
                           else
                             AFPrintf(NULL, sout, "\n\n CronTab file read successfully\n\n");
                         break;

        case CRONEXIT:   AFPrintf(NULL, sout, "\n TPTCron shut down successfully\n\n");
                         break;
       }

 CleanUp(NULL);
}


char *GetCommand(char **args, int numargs)

{long  pos;
 long  size;

 char *buf;
 char *s;
 char *ns;

 for(pos=0, size=0; pos < numargs; pos++)
     size += strlen(args[pos]) + 1;
 buf = malloc(size);

 for(s=buf, pos=0; pos < numargs; pos++)
    {s = stpcpy(s, args[pos]);
     if (pos < (numargs-1))  s = stpcpy(s, " ");
    }

 for(s = buf, ns = buf; *s; s++, ns++)
    {if (*s == '\'')
        {if (*(s+1) == '\'')
             *ns = *s++;
            else
             *ns = '"';
        }
      else
        *ns = *s;
    }

 *ns = 0;

 return(buf);
}


void Usage(char *callname)

{AFPrintf(NULL, sout, "\n Usage:\n   ");
 AFPrintf(NULL, sout, callname);
 AFPrintf(NULL, sout, " (Add|ChangeDir|Delete|List|Read|TabList|When|Quit)\n");
 AFPrintf(NULL, sout, "             [<minutes> <command>]\n\n");

 CleanUp(NULL);
}


void CleanUp(char *s)

{if (command)  free(command);
 CloseLibrary(DLGBase);

 if (s)
    {Write(sout, "\n Error: ", 9);
     Write(sout,  s,   strlen(s));
     Write(sout, "\n\n",      2);
    }

 exit(s?5:0);
 return;
}
