This commit is contained in:
Oliver Lehmann 1989-04-18 13:05:09 +00:00
parent 65202e087b
commit 35b61c8634
4 changed files with 1830 additions and 0 deletions

View File

@ -0,0 +1,278 @@
# include <stdio.h>
# include "gen.h"
# include "../h/dbs.h"
# include "../h/aux.h"
# include "../h/pipes.h"
# include "../h/symbol.h"
# include "../h/tree.h"
# include "../h/bs.h"
# include "parser.h"
# include "../h/scanner.h"
static struct retcode *Lastcnt; /* ptr to last tuple count, or 0 */
static struct retcode Lastcsp; /* space for last tuple count */
/*
** CONTROL.C -- -- collection of control functions for the parser
**
** These routines administrate the operation of the parser for internal
** sequencing. There are 3 pairs of routines, one pair for each
** QL statement, one for each go-block, and one to handle syncronization
** with up and down processes.
**
** Defines:
** init_qlst -- initialize for a QL statement
** endqlst -- clean up after a QL statement
** syncup -- sync the process above
** syncdn -- sync the process below
** startgo -- initialize for a go-block
** endgo -- clean up after a go-block
**
**
**
** INIT_QLST -- set vbles for default mode before each QL statement
*/
init_qlst()
{
extern int neederr();
# ifdef xPTR3
AAtTfp(60, 0, "INIT_QLST:\n");
# endif
initp(); /* reset dbu buffer */
initbuf(Qbuf, TREEMAX, TREEOFLO, neederr); /* reset tree allocation */
Dbserr = 0; /* clear error condition */
Patflag = 0; /* reset pattern matching flag */
Pars = 1; /* set scanner into "parser" mode */
Lcase = Dcase; /* set case mapping to default */
Agflag = 0; /* reset aggregate flag */
Opflag = 0; /* reset qmode flag */
Resrng = 0; /* reset result relation ptr */
Qlflag = 0; /* reset qualification flag */
freesym(); /* free symbol table space */
rngreset(); /* reset used bits in range tbl */
fflush(stdout);
}
/*
** ENDQLST -- finish command checking and processing for each QL statement
*/
endqlst(op1)
int op1;
{
register int i;
register int op;
char ibuf[2]; /* two char buffer for index keys */
# ifdef xPTR3
AAtTfp(60, 2, "ENDQLST:\n");
# endif
op = op1;
/* check next token for GOVAL if the next token has been read */
switch (op)
{
case mdSAVE:
case mdCOPY:
case mdCREATE:
# ifdef DISTRIB
case mdDCREATE:
# endif
case mdINDEX:
case mdRANGE:
break;
default:
/* has vble ending and therefore must detect valid end of command */
if (Lastok.tokop != GOVAL) /* next token not start of command */
yyerror(NXTCMDERR, (char *) 0);
break;
}
if (Agflag >= MAXAGG) /* too many aggregates */
yyerror(AGGXTRA, (char *) 0);
/* command ok so far, finish up */
switch (op)
{
case mdRETR:
case mdRET_UNI:
case mdVIEW:
if (Resrng)
{
/* need to do create, everything is ready */
call_p(mdCREATE, EXEC_DBU);
cleanrel(&Desc);
}
else if (!Eql) /* need to print header */
header();
if (Dbserr)
{
/*
** might be nice to back out the create already done
** by this point so that the user doesn't need to
*/
endgo(); /* abort rest of go-block */
reset();
}
/* fall through */
case mdAPP:
case mdDEL:
case mdREPL:
if (op != (int) mdVIEW)
{
call_tree(op, EXEC_DECOMP);
break;
}
# ifdef DISTRIB
case mdDISTRIB:
op = mdVIEW;
# endif
/* else, do VIEW */
initp();
setp(Resrng->relnm);
call_tree(mdDEFINE, EXEC_QRYMOD);
call_p(op, EXEC_QRYMOD);
break;
case mdINTEG:
case mdPROT:
call_tree(mdDEFINE, EXEC_QRYMOD);
call_p(op, EXEC_QRYMOD);
break;
case mdCREATE:
# ifdef DISTRIB
case mdDCREATE:
# endif
case mdDESTROY:
case mdMODIFY:
call_p(op, EXEC_DBU);
cleanrel(&Desc);
break;
case mdCOPY:
case mdHELP:
case mdPRINT:
case mdSAVE:
case mdDISPLAY:
case mdREMQM:
call_p(op, EXEC_DBU);
break;
case mdRANGE:
break;
case mdINDEX:
call_p(op, EXEC_DBU);
if (Dbserr)
{
endgo(); /* abort rest of go-block */
reset();
}
if (Indexspec)
{
setp(Indexname);
setp(Indexspec);
setp("num");
for (i = 1; i <= Rsdmno; i++)
{
ibuf[0] = ctou(i);
ibuf[1] = '\0';
setp(ibuf);
}
call_p(mdMODIFY, EXEC_DBU);
}
break;
}
/* refresh relstat bits if necessary */
rngfresh(op);
init_qlst();
}
/*
** SYNCUP -- sync with process above
**
** send tuple count if present
*/
syncup()
{
struct pipfrmt p;
register struct pipfrmt *pp;
# ifdef xPTR3
AAtTfp(60, 3, "SYNCUP:\n");
# endif
pp = &p;
wrpipe(P_PRIME, pp, 0, (char *) 0, 0);
if (Lastcnt)
{
wrpipe(P_NORM, pp, W_up, Lastcnt, sizeof(*Lastcnt));
}
wrpipe(P_END, pp, W_up);
}
/*
** SYNCDN -- wait for sync from below
**
** save tuple count if present
*/
syncdn()
{
struct retcode up;
struct pipfrmt p;
register struct pipfrmt *pp;
# ifdef xPTR3
AAtTfp(60, 4, "SYNCDN:\n");
# endif
pp = &p;
rdpipe(P_PRIME, pp);
if (rdpipe(P_NORM, pp, R_down, &up, sizeof(up)) != 0)
{
AAbmove(&up, &Lastcsp, sizeof(up));
Lastcnt = &Lastcsp;
# ifdef xPTR3
AAtTfp(60, 1, "Reading tuple count: %ld\n", Lastcnt->rc_tupcount);
# endif
}
}
/*
** STARTGO -- do whatever needs doing to set up a go-block
*/
startgo()
{
# ifdef xPTR3
AAtTfp(60, 5, "STARTGO:\n");
# endif
/* initialize for go-block */
getscr(1); /* prime the scanner input */
Lastcnt = (struct retcode *) 0; /* reset ptr to last tuple count */
init_qlst(); /* most other init's are done for each statement */
yyline = 1; /* reset line counter */
yypflag = 1; /* reset action stmnts */
}
/*
** ENDGO -- do whatever needs doing to clean up after a go block
*/
endgo()
{
# ifdef xPTR3
AAtTfp(60, 6, "ENDGO:\n");
# endif
getscr(2);
syncup();
}

View File

@ -0,0 +1,122 @@
# include <stdio.h>
# include "gen.h"
# include "../h/dbs.h"
# include "../h/aux.h"
# include "../h/pipes.h"
# include "../h/tree.h"
# include "parser.h"
# include "../h/access.h"
# include "../h/bs.h"
# ifdef P8000
ret_buf AAjmp_buf;
# else
jmp_buf AAjmp_buf;
# endif
DESC Desc; /* descriptor for attribute relation */
char *Relspec; /* ptr to storage structure of result relation */
char *Indexspec; /* ptr to stor strctr of index */
int Dbserr; /* set if a query returns an error from processes below */
int Noupdt; /* DBS user override of no update restriction */
int Dcase; /* default case mapping */
int Lcase; /* UPPER->lower conversion flag */
char *Qbuf; /* buffer which holds tree allocated on stack in main.c to get data space */
int Qrymod; /* qrymod on in database flag */
main(argc, argv1)
int argc;
char *argv1[];
{
register char **argv;
struct pipfrmt pbuf;
extern char *valflag;
extern int yydebug;
/*
** This is a ROYAL kludge used to obtain data space for the
** parser. The treebuffer should really be allocated in
** ../parser.h but unfortunately.
*/
char treebuffer[TREEMAX];
/* set up parser */
set_so_buf();
argv = argv1;
Qbuf = treebuffer; /* see kludge notice above */
# ifdef xPTR1
AAtTrace(&argc, argv, 'P');
# endif
# ifdef xPTR2
if (AAtTf(17, 0))
AAprargs(argc, argv);
# endif
initproc("PARSER", argv);
Noupdt = !setflag(argv, 'U', 0);
Dcase = setflag(argv, 'L', 1);
Relspec = setflag(argv, 'r', 1)? "cheapsort": valflag;
Indexspec = setflag(argv, 'n', 1)? "isam": valflag;
if (AAsequal(Relspec, "heap"))
Relspec = (char *) 0;
if (AAsequal(Indexspec, "heap"))
Indexspec = (char *) 0;
rnginit();
AArelopen(&Desc, 0, AA_ATT);
/*
** The 'AArelopen' must be done before this test so that the 'AAdmin'
** structure is initialized. The 'Qrymod' flag is set when
** the database has query modification turned on.
*/
Qrymod = ((AAdmin.adhdr.adflags & A_QRYMOD) == A_QRYMOD);
/* resync to startup */
wrpipe(P_PRIME, &pbuf, 0, (char *) 0, 0);
wrpipe(P_INT, &pbuf, W_up);
setexit();
/* EXECUTE */
for ( ; ; )
{
startgo(); /* initializations for start of go-block */
yyparse(); /* will not return until end of go-block or error */
endgo(); /* do cleanup (resync, etc) for a go-block */
}
}
/*
** RUBPROC
*/
rubproc()
{
resyncpipes();
}
/*
** PROC_ERROR ROUTINE
**
** This routine handles the processing of errors for the parser
** process. It sets the variable 'Dbserr' if an error is passes
** up from one of the processes below.
*/
proc_error(s, fd)
register struct pipfrmt *s;
register int fd;
{
struct pipfrmt t;
if (fd != R_down)
AAsyserr(18011);
wrpipe(P_PRIME, &t, s->exec_id, (char *) 0, s->func_id);
t.err_id = s->err_id;
copypipes(s, fd, &t, W_up);
rdpipe(P_PRIME, s);
Dbserr = 1;
}

View File

@ -0,0 +1,132 @@
# define PARBUFSIZ 2000 /* size of buffer for dbu commands */
# define TREEMAX 2500 /* max number of bytes for tree */
# define MAXATT 150 /* max number of attributes in the att stash */
/* mode parameters for range table manipulation */
# define LOOKREL 1
# define LOOKVAR 2
# define R_INTERNAL 3
# define R_EXTERNAL 4
/* error numbers */
# define TREEOFLO 2118 /* over flow tree buffer */
# define PBUFOFLO 2106 /* over flow dbu arg buffer */
# define NOATTRIN 2100 /* attrib not in relation */
# define CANTUPDATE 2107 /* can't update rel */
# define NOVBLE 2109 /* vble not declared */
# define NOPATMAT 2120 /* no pattern matching in tl */
# define RNGEXIST 2117 /* can't find rel for var */
# define REPALL 2123 /* x.all on replace */
# define BADCONSTOP 2134 /* bad constant operator */
# define INDEXTRA 2111 /* too many atts in key */
# define RESXTRA 2130 /* too many resdoms in tl */
# define TARGXTRA 2131 /* tl larger than MAXTUP */
# define AGGXTRA 2132 /* too many aggs */
# define MODTYPE 2119 /* type conflict for MOD */
# define CONCATTYPE 2121 /* type conflict for CONCAT */
# define AVGTYPE 2125 /* type conflict for AVG(U) */
# define SUMTYPE 2126 /* type conflict for SUM(U) */
# define FOPTYPE 2127 /* type conflict for func ops */
# define UOPTYPE 2128 /* type conflict for unary ops */
# define NUMTYPE 2129 /* type conflict for numeric ops */
# define RELTYPE 2133 /* type conflict for relatv op */
# define RESTYPE 2103 /* result type mismatch w/expr */
# define RESAPPEX 2108 /* append res rel not exist */
# define RESEXIST 2135 /* result rel already exists */
# define NXTCMDERR 2501 /* misspelt where problem */
# define NOQRYMOD 2139 /* no qrymod in database */
# define BADHOURS 2136 /* no such hour */
# define BADMINS 2137 /* no such minute */
# define BAD24TIME 2138 /* only 24:00 can be used */
/* -- ASSORTED DATA STRUCTURES -- */
struct atstash /* attribute table */
{
char atbid; /* attribute number */
char atbfrmt; /* attribute form type */
char atbfrml; /* attribute form length */
char atbname[MAXNAME]; /* attribute name */
struct atstash *atbnext; /* pointer to next entry in chain */
};
struct rngtab /* range table */
{
short rentno; /* variable number of this table position */
char rmark; /* was it used in this command */
char ractiv; /* is entry empty */
short rposit; /* lru position of entry */
char varname[MAXNAME + 1]; /* variable name */
char relnm[MAXNAME + 1]; /* relation name */
char relnowner[2]; /* relation owner */
short rstat; /* relstat field of relation relation */
short ratts; /* number of attributes in relation */
struct atstash *attlist; /* head of attrib list for this reln */
};
struct constop /* constant operator lookup table */
{
char *copname; /* string name for identification */
short copnum; /* op number */
char coptype; /* op result type for formating */
char coplen; /* op result length for formatting */
};
extern struct rngtab *Resrng; /* ptr to result reln entry */
extern struct atstash *Freeatt; /* free list of attrib stash */
extern struct querytree *Lastree; /* pointer to root node of tree */
extern DESC Reldesc; /* descriptor for range table lookup */
extern DESC Desc; /* descriptor for attribute relation */
extern struct atstash Faketid; /* atstash structure for TID node */
#ifdef DISTRIB
extern struct atstash Fakesid; /* atstash structure for SID node */
#endif
extern short Rsdmno; /* result domain number */
extern int Opflag; /* operator flag contains query mode */
extern char *Relspec; /* ptr to storage structure of result relation */
extern char *Indexspec; /* ptr to stor strctr of index */
extern char *Indexname; /* ptr to name of index */
extern char Trfrmt; /* format for type checking */
extern char Trfrml; /* format length for type checking */
extern char *Trname; /* pointer to attribute name */
extern int Agflag; /* how many aggs in this qry */
extern int Eql; /* indicates EQL preprocessor on */
extern int Qrymod; /* qrymod on in database flag */
extern int Dbserr; /* set if a query returns an error from processes below */
extern int Patflag; /* signals a pattern match reduction */
extern int Qlflag; /* set when processing a qual */
extern int Noupdt; /* DBS user override of no update restriction */
extern int yypflag; /* disable action stmts if = 0 */
extern int yyline; /* line counter */
extern int Dcase; /* default case mapping */
extern char **Pv; /* ptr to list of dbu params */
extern int Pc; /* number of dbu commands */
extern char *Qbuf; /* buffer which holds tree allocated on stack in main.c to get data space */
extern short Permcomd;
extern char *AA_iocv();
# ifdef ESER_PSU
# define CAST(x) ((char *) ((unsigned short) (x)))
# else
# define CAST(x) ((char *) (x))
# endif
/* character type mapping */
# define ASCII_MASK 0177
# define BYTE_MASK 0377
extern char Cmap[];
# ifdef EBCDIC
# ifdef ESER_PSU
extern char _etoa_[];
# define ETOA(c) _etoa_[(c) & BYTE_MASK]
# endif
# define CMAP(c) Cmap[(ETOA(c)) & ASCII_MASK]
# else
# define CMAP(c) Cmap[(c) & ASCII_MASK]
# endif

File diff suppressed because it is too large Load Diff