home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
ftp.barnyard.co.uk
/
2015.02.ftp.barnyard.co.uk.tar
/
ftp.barnyard.co.uk
/
cpm
/
walnut-creek-CDROM
/
CPM
/
AZTEC-C
/
MINDER.ARK
/
MNDREP.C
< prev
next >
Wrap
C/C++ Source or Header
|
1986-06-19
|
9KB
|
447 lines
/* mndrep
Reporting module of reminder service
1985 Mark E. Mallett
*/
#include "minder.h"
#include "comnd.h"
#include "setjmp.h"
/* Local definitions */
/* External routines */
/* External data */
extern int Curdat; /* Current date */
extern int Curtim; /* Current time */
extern EVT *Evthdr; /* Heads the event list */
extern CFB Inicfb; /* CFB for initialization */
extern int Osdate; /* Can OS give date/time ? */
extern char Tmpabf[]; /* Temp atom buffer */
extern CSB Tmpcsb; /* Temp command state block */
extern jmp_buf Tmpenv; /* setjmp environment buffer */
/* Local routines */
extern int dspack(); /* disposition: ack */
extern int dspnxt(); /* disposition: next */
/* Local data */
static char *Mntbl[] = { /* Names of months */
"Foo", /* (month 0) */
"Jan", "Feb", "Mar", "Apr", "May", "Jun",
"Jul", "Aug", "Sep", "Oct", "Nov", "Dec"
};
/* dispositions command keyword and dispatch tables */
BYTE *Dspktb[] = { /* Command keywords.. */
"ACKNOWLEDGE", /* Ack the event, as required */
"NEXT", /* Move along to next event */
NULL /* Ends with a null pointer */
};
int (*Dspdsp[])() = {
dspack, /* ACKNOWLEDGE */
dspnxt, /* NEXT */
0 /* Ends with a zero for convenience */
};
/* COMND blocks */
CFB Dskcfb = {_CMKEY, _CFHPP|_CFDPP, 0, &Dspktb,
"Command, ", "NEXT"};
/*
*//* report()
The reporting function of the minder program
This routine is responsible for showing events which have become active.
Accepts :
Returns :
*/
report ()
{
IND EVT *EVTptr; /* Pointer to event.. */
IND EVT *EVTptr1; /* another pointer */
IND EVT *EVTlst; /* Points to action list */
IND int intcnt; /* Counts interactive events */
IND int okflg; /* OK to proceed flag */
if (Osdate) /* If OS gives it */
curdtm (&Curdat, &Curtim); /* Get current date/time */
/* Go through and report events with automatic dispositions; also
make note of events which need interaction */
EVTptr = Evthdr; /* Point to header */
intcnt = 0; /* Count of events rq action */
while (EVTptr)
{
EVTptr -> EVT_FLG &= ~(_EFACT|_EFRDA);
/* Mark not active, no action */
okflg = chkfor (EVTptr); /* Init ok-to-look flag */
if (okflg) /* If ok.. */
{
if (chkact ((EVTptr->EVT_DTD - EVTptr->EVT_ADV), EVTptr -> EVT_DTM))
{
EVTptr -> EVT_FLG |= _EFACT; /* Set active */
if (EVTptr -> EVT_FLG & _EFACK) /* If ack rqd... */
intcnt++; /* Count interactive.. */
else /* Not auto mode */
{
if (chkact (EVTptr -> EVT_DTD, EVTptr -> EVT_DTM))
EVTptr -> EVT_FLG |= _EFRDA;
/* If action should be taken */
prtrep (EVTptr); /* Print report for this alarm */
}
}
}
EVTptr = EVTptr -> EVT_FLK; /* Link to next */
}
/* Now process active events, if any, requiring interaction */
if (intcnt)
{
printf ("\n***Event(s) requiring interaction follow***\n\n");
EVTptr = Evthdr; /* Start at beginning again */
while (EVTptr)
{
if ((EVTptr -> EVT_FLG & _EFACT) /* Marked active ? */
&& (EVTptr -> EVT_FLG & _EFACK))
{
prtrep (EVTptr); /* Print report */
repdsp (EVTptr); /* Do disposition */
}
EVTptr = EVTptr -> EVT_FLK;
}
}
/* Now attend to events marked as needing attention. */
EVTlst = NULL; /* No disposed-of list, yet */
EVTptr = Evthdr; /* Start at beginning of list */
while (EVTptr) /* Go through it */
{
EVTptr1 = EVTptr; /* Get working copy */
EVTptr = EVTptr -> EVT_FLK; /* Get addr of next one, now */
if (EVTptr1 -> EVT_FLG & _EFRDA) /* Take action ? */
{
remev (EVTptr1); /* Remove this from the list */
switch (EVTptr1 -> EVT_DIS) /* Process by disposition */
{
case _EDDEL: /* delete? */
break; /* just lose it! */
case _EDSCH: /* Reschedule ... */
resched (EVTptr1); /* Process rescheduling */
/* Drop through to keep case */
case _EDKEEP: /* Keep event */
EVTptr1 -> EVT_FLK = EVTlst;
EVTlst = EVTptr1;
break;
default:
printf ("Bad value in disposition\n");
}
}
}
while (EVTlst) /* Add processed EVTs back in */
{
EVTptr = EVTlst;
EVTlst = EVTlst -> EVT_FLK;
addev (EVTptr);
}
}
/*
*//* repdsp (EVTptr)
Handles interactive disposition of an event
Accepts :
EVTptr Address of the event block
Returns :
*/
repdsp (EVTptr)
EVT *EVTptr; /* Address of event block */
{
IND int i; /* Scratch */
IND BYTE **kptr; /* Points to kwd table entry */
printf ("\nPlease enter disposition for this event\n");
Tmpcsb.CSB_PMT = "MIND-DISP> "; /* Set prompt */
/* Enter command loop */
while (TRUE) /* Forever */
{
if (COMND (&Tmpcsb, &Inicfb) != _CROK) /* eh? */
{
printf ("Fatal error initializing COMND\n");
exit();
}
setjmp (Tmpenv); /* Mark here for reparse */
if (COMNDi (&Tmpcsb, &Dskcfb) != _CROK) /* Collect keyword */
continue;
kptr = (char **) (Tmpcsb.CSB_RVL._ADR);
i = kptr - (&Dspktb[0]); /* Get keyword index */
if ((*Dspdsp[i])(EVTptr)) /* Process command */
break; /* Exit command loop on done */
}
}
/*
*//* dspack (EVTptr)
Processes the ACKNOWLEDGE disposition-command.
Accepts :
EVTptr Address of event block
Returns :
*/
dspack (EVTptr)
EVT *EVTptr; /* Addr of EVT block */
{
if (!noise (&Tmpcsb, "event")) /* Give guide words */
return;
if (!confrm (&Tmpcsb)) /* Confirm the command */
return;
EVTptr -> EVT_FLG |= _EFRDA; /* Do the action. */
return (TRUE);
}
/*
*//* dspnxt (EVTptr)
Processes the NEXT disposition-command.
Accepts :
EVTptr Address of event block
Returns :
*/
dspnxt (EVTptr)
EVT *EVTptr; /* Addr of EVT block */
{
if (!noise (&Tmpcsb, "event")) /* Give guide words */
return;
if (!confrm (&Tmpcsb)) /* Confirm the command */
return;
return (TRUE);
}
/*
*//* prtrep (EVTptr)
Print report for an event
Accepts :
EVTptr Address of event block
Returns :
*/
prtrep (EVTptr)
EVT *EVTptr; /* Addr of event block */
{
IND int i; /* Scratch */
IND int m,d,y,hh,mm; /* Date/time components */
IND int nl; /* Newline flag */
cvided (EVTptr -> EVT_DTD, EVTptr -> EVT_DTM, &m, &d, &y, &hh, &mm);
nl = FALSE;
if (EVTptr -> EVT_FRM) /* If any from */
{
printf ("From: %-10s ", EVTptr -> EVT_FRM);
nl = TRUE;
}
if (!chkact (EVTptr -> EVT_DTD, EVTptr -> EVT_DTM))
if (chkact (EVTptr->EVT_DTD - EVTptr->EVT_ADV, EVTptr->EVT_DTM))
{
printf (" *** Advance Notice ***");
nl = TRUE;
}
if (nl)
printf ("\n");
printf (" *** \"%s\"", EVTptr -> EVT_NAM);
i = 20 - strlen(EVTptr -> EVT_NAM);
while (i-- > 0)
putchar (' ');
printf ("%s %2d, %04d %02d:%02d", Mntbl[m], d, y, hh, mm);
if (strlen (EVTptr -> EVT_MSG) >= 23)
printf ("\n");
printf (" >>%s<<\n\n", EVTptr -> EVT_MSG);
}
/*
*//* chkact (chkdat, chktim)
Check a date and time for activation
Accepts :
chkdat Date to check for active
chktim Time to check for active
Returns :
<value> TRUE if chkdat/chktim is le Curdat/Curtim
FALSE if not
*/
chkact (chkdat, chktim)
int chkdat; /* date to check */
int chktim; /* time to check */
{
if (chkdat < Curdat) /* If lt. */
return (TRUE); /* then definitely active */
if (chkdat == Curdat) /* If same */
if (chktim <= Curtim) /* If times lt */
return (TRUE); /* then true */
return (FALSE); /* Not true */
}
/*
*//* resched (EVTptr)
Reschedule an event based on its information
Accepts :
EVTptr Address of EVT
Returns :
Event data modified for rescheduling.
*/
resched (EVTptr)
EVT *EVTptr; /* Addr of EVT */
{
IND int id, it, m, d, y, hh, mm; /* Date/time values */
id = EVTptr -> EVT_DTD; /* Pickup date/time */
it = EVTptr -> EVT_DTM;
cvided (id, it, &m, &d, &y, &hh, &mm); /* Get components */
switch (EVTptr -> EVT_RSU)
{ /* Reschedule by units */
case 0: /* Days */
id += EVTptr -> EVT_RSV; /* Just add in the days */
break; /* Done. */
case 1: /* Weeks */
id += EVTptr -> EVT_RSV*7;
break;
case 2: /* Months */
m += EVTptr -> EVT_RSV;
while (m > 12)
{
y++;
m -= 12;
}
cvedid (&id, &it, m, d, y, mm, hh);
break;
case 3: /* Years */
y += EVTptr -> EVT_RSV;
cvedid (&id, &it, m, d, y, mm, hh);
break;
}
EVTptr -> EVT_DTD = id; /* Store date */
EVTptr -> EVT_DTM = it; /* And time. */
}