/* SDB - boolean expression evaluator / compiler */ #include "bdscio.h" #include "dbqdefs.h" /* The first section of code originated from sdbint.c */ int db_interpret(slptr) struct sel *slptr; { struct operand *result; int r,inting; if ((cptr = slptr->sl_where) == NULL) return (TRUE); sptr = stack; #ifdef COMDEB printf("com:interpret - entry\n"); #endif /* patch out original while ((*(*cptr++).c_operator)()) #ifdef COMDEB printf("com:interpret - cptr loop\n") #endif ; end of patch */ /* own version */ inting = TRUE; /* Set for loop */ while (inting) { #ifdef COMDEB printf("interpret - operator = %d\n",(*cptr).c_operator); #endif switch ((*cptr++).c_operator) { case XPUSH: *sptr++ = (*cptr++).c_operand; break; case TKXAND: inting = boolean('&'); break; case TKXOR: inting = boolean('|'); break; case LSS: inting = compare(LSS); break; case LEQ: inting = compare(LEQ); break; case EQL: inting = compare(EQL); break; case CONT: inting = compcont(); break; case GEQ: inting = compare(GEQ); break; case GTR: inting = compare(GTR); break; case NEQ: inting = compare(NEQ); break; case XNOT: inting = db_xnot(); break; default: inting = FALSE; } } /* end while cptr loop */ result = *--sptr; r = result->o_value.ov_boolean; if (result->o_type == TEMP) CFREE(result); while (sptr != stack) { #ifdef COMDEB printf("com:interpret - stack loop\n"); #endif if ((*sptr)->o_type == TEMP) CFREE(*sptr); sptr -= 1; } return (r); } /* Patch out unwanted functions int db_xstop() { return (FALSE); } int db_xpush() { *sptr++ = (*cptr++).c_operand; } int db_xand() { return (boolean('&')); } int db_xor() { return (boolean('|')); } int db_xlss() { return (compare(LSS)); } int db_xleq() { return (compare(LEQ)); } int db_xeql() { return (compare(EQL)); } int db_xgeq() { return (compare(GEQ)); } int db_xgtr() { return (compare(GTR)); } int db_xneq() { return (compare(NEQ)); } end of unwanted functions */ int boolean(opr) { struct operand *lval,*rval,*result; int lv,rv,r; rval = *--sptr; lval = *--sptr; lv = lval->o_value.ov_boolean; rv = rval->o_value.ov_boolean; if ((result = CALLOC(OPSIZE)) == NULL) { RETERR(INSMEM) } result->o_type = TEMP; switch (opr) { case '&': r = (lv && rv); break; case '|': r = (lv || rv); break; } #ifdef COMDEB printf("com:bool lv=%d,rv=%d,r=%d\n",lv,rv,r); #endif result->o_value.ov_boolean = r; *sptr++ = result; if (lval->o_type == TEMP) CFREE(lval); if (rval->o_type == TEMP) CFREE(rval); return (TRUE); } int db_xnot() { struct operand *val,*result; val = *--sptr; if ((result = CALLOC(OPSIZE)) == NULL) { RETERR(INSMEM) } result->o_type = TEMP; result->o_value.ov_boolean = !val->o_value.ov_boolean; *sptr++ = result; if (val->o_type == TEMP) CFREE(val); return (TRUE); } int compare(cmp) { struct operand *lval,*rval,*result; int i; rval = *--sptr; lval = *--sptr; if ((result = CALLOC(OPSIZE)) == NULL) { RETERR(INSMEM) } result->o_type = TEMP; if (lval->o_value.ov_char.ovc_type == TCHAR) i = comp(lval,rval); else i = ncomp(lval,rval); #ifdef COMDEB printf("com:compare - cmp=%d\n",cmp); #endif switch (cmp) { case LSS: i = (i < 0); break; case LEQ: i = (i <= 0); break; case EQL: i = (i == 0); break; case GEQ: i = (i >= 0); break; case GTR: i = (i > 0); break; case NEQ: i = (i != 0); break; } result->o_value.ov_boolean = i; *sptr++ = result; if (lval->o_type == TEMP) CFREE(lval); if (rval->o_type == TEMP) CFREE(rval); return (TRUE); } int compcont(cmp) { struct operand *lval,*rval,*result; int i; rval = *--sptr; lval = *--sptr; if ((result = CALLOC(OPSIZE)) == NULL) { RETERR(INSMEM) } result->o_type = TEMP; i = contains(lval,rval); /* printf("i after contains = %d\n",i); */ result->o_value.ov_boolean = i; *sptr++ = result; if (lval->o_type == TEMP) CFREE(lval); if (rval->o_type == TEMP) CFREE(rval); return (TRUE); } int contains(lval,rval) struct operand *lval,*rval; { char *lptr,*rptr; int lctr,rctr; int len; lptr = lval->o_value.ov_char.ovc_string; lctr = lval->o_value.ov_char.ovc_length; rptr = rval->o_value.ov_char.ovc_string; rctr = rval->o_value.ov_char.ovc_length; while (lctr > 0 && (lptr[lctr-1] == 0 || lptr[lctr-1] == ' ')) lctr--; while (rctr > 0 && (rptr[rctr-1] == 0 || rptr[rctr-1] == ' ')) rctr--; /* printf("lctr = %d, rctr = %d\n",lctr,rctr); */ if (lctr < rctr) return(FALSE); else len = rctr; /* printf("length = %d\n",len); */ while (lctr >= rctr) { if(db_sncmp(lptr,rptr,rctr) == 0) return(TRUE); /* printf("forloop - lptr = %s\n",lptr); */ lptr++; lctr--; } /* printf("out of for loop\n"); */ return (FALSE); } int comp(lval,rval) struct operand *lval,*rval; { char *lptr,*rptr; int lctr,rctr; int len; lptr = lval->o_value.ov_char.ovc_string; lctr = lval->o_value.ov_char.ovc_length; rptr = rval->o_value.ov_char.ovc_string; rctr = rval->o_value.ov_char.ovc_length; #ifdef COMDEB printf("com:comp - lptr = %d,%d,%d,%d\n",lptr[6],lptr[7],lptr[8],lptr[9]); #endif while (lctr > 0 && (lptr[lctr-1] == 0 || lptr[lctr-1] == ' ')) lctr--; while (rctr > 0 && (rptr[rctr-1] == 0 || rptr[rctr-1] == ' ')) rctr--; if (lctr < rctr) len = lctr; else len = rctr; #ifdef COMDEB printf("com:comp - lctr=%d,rctr=%d\n",lctr,rctr); #endif while ((len--) > 0) { if (*lptr++ != *rptr++) if (*--lptr < *--rptr) return (-1); else return (1); } if (lctr == rctr) return (0); else if (lctr < rctr) return (-1); else return (1); /* return(db_sncmp(lptr,rptr,len)); */ } int ncomp(lval,rval) struct operand *lval,*rval; { char lstr[NUMBERMAX+1],rstr[NUMBERMAX+1]; int len; strncpy(lstr,lval->o_value.ov_char.ovc_string, (len = lval->o_value.ov_char.ovc_length)); lstr[len] = EOS; strncpy(rstr,rval->o_value.ov_char.ovc_string, (len = rval->o_value.ov_char.ovc_length)); rstr[len] = EOS; return (db_cmp(lstr,rstr)); } /* The following originated from com.c */ int db_compile(slptr) struct sel *slptr; { int result,i; union codecell *cptr; int (*dns)(); #ifdef COMDEB printf("com:compile - entry\n"); #endif selptr = slptr; cndx = 0; if (!expr(&result)) { #ifdef COMDEB printf("com:compile - expr-error = %d\n",dbv_errcode); #endif code[cndx++].c_operator = XSTOP; freelit(code); return (FALSE); } #ifdef COMDEB printf("com:compile - after expr call\n"); #endif code[cndx++].c_operator = XSTOP; if ((cptr = CALLOC(CELLSIZE * cndx)) == NULL) { freelit(code); return(FALSE); } slptr->sl_where = cptr; for (i = 0; i < cndx; i++) { #ifdef COMDEB printf("com.compile - i = %d, op = %d\n",i,code[i].c_operator); #endif (*cptr++).c_operator = code[i].c_operator; if (code[i].c_operator == XPUSH) (*cptr++).c_operand = code[++i].c_operand; } return (TRUE); } db_fcode(slptr) struct sel *slptr; { #ifdef COMDEB printf("com:fcode - entry\n"); #endif if (slptr->sl_where == NULL) return; freelit(slptr->sl_where); CFREE(slptr->sl_where); } int operator(opr) int *opr; { #ifdef COMDEB printf("com:operator - entry\n"); #endif if (cndx < CODEMAX) code[cndx++].c_operator = opr; else { RETERR(CDSIZE) } return (TRUE); } int oprand(opr) struct operand *opr; { #ifdef COMDEB printf("com:oprand - entry\n"); #endif if (!operator(XPUSH)) return (FALSE); if (cndx < CODEMAX) code[cndx++].c_operand = opr; else { RETERR(CDSIZE) } return (TRUE); } int expr(result) int *result; { int lval,rval; #ifdef COMDEB printf("com:expr - entry\n"); #endif if (!land(&lval)) return (FALSE); while (db_token() == '|') { db_ntoken(); if (!land(&rval)) return (FALSE); if (!operator(TKXOR)) return (FALSE); } *result = lval; return (TRUE); } int land(result) int *result; { int lval,rval; #ifdef COMDEB printf("com:land - entry\n"); #endif if (!relat(&lval)) return (FALSE); while (db_token() == '&') { db_ntoken(); if (!relat(&rval)) return (FALSE); if (!operator(TKXAND)) return (FALSE); } *result = lval; return (TRUE); } int relat(result) int *result; { int lval,rval; int tkn; #ifdef COMDEB printf("com:relat - entry\n"); #endif if (!primary(&lval)) return (FALSE); while (db_token() <= LSS && dbv_token >= GTR) { tkn = db_ntoken(); #ifdef COMDEB printf("com:relat - tkn = %d\n",tkn); #endif if (!primary(&rval)) return (FALSE); if (!operator(tkn)) return (FALSE); } *result = lval; return (TRUE); } int primary(result) int *result; { int val; int tkn; #ifdef COMDEB printf("com:primary - entry\n"); #endif if (db_token() == '~') { tkn = db_ntoken(); if (!primary(&val)) return (FALSE); switch (tkn) { case '~': if (!operator(XNOT)) return (FALSE); break; } } else if (!factor(&val)) return (FALSE); *result = val; return (TRUE); } int factor(result) int *result; { int val; #ifdef COMDEB printf("com:factor - entry"); #endif if (db_token() == '(') { db_ntoken(); if (!expr(&val)) return (FALSE); if (db_token() != ')') { RETERR(SYNTAX) } db_ntoken(); } else if (!get_operand(&val)) return (FALSE); *result = val; return (TRUE); } int get_operand(result) int *result; { #ifdef COMDEB printf("com:getoper - entry\n"); #endif if (db_ntoken() == NUMBER) return (get_thing(result,TNUM)); else if (dbv_token == ID) return (get_attr(result)); else if (dbv_token == STRING) return (get_thing(result,TCHAR)); else { RETERR(SYNTAX) } } int get_attr(result) int *result; { struct operand *opr; char rname[RNSIZE+1],aname[ANSIZE+1]; char *aptr; int atype,alen; strncpy(aname,dbv_tstring,ANSIZE); aname[ANSIZE] = EOS; if (db_token() == '.') { db_ntoken(); strcpy(rname,aname); if (db_ntoken() != ID) { RETERR(SYNTAX) } strncpy(aname,dbv_tstring,ANSIZE); aname[ANSIZE] = EOS; if (!db_sattr(selptr,rname,aname,&atype,&aptr,&alen)) return (FALSE); } else if (!db_sattr(selptr,NULL,aname,&atype,&aptr,&alen)) return (FALSE); if ((opr = CALLOC(OPSIZE)) == NULL) { RETERR(INSMEM) } opr->o_type = ATTR; opr->o_value.ov_char.ovc_type = atype; opr->o_value.ov_char.ovc_string = aptr; opr->o_value.ov_char.ovc_length = alen; if (!oprand(opr)) { CFREE(opr); return (FALSE); } *result = atype; return (TRUE); } int get_thing(result,tipe) int *result; int tipe; { struct operand *opr; #ifdef COMDEB printf("com:getthing\n"); #endif if ((opr = CALLOC(OPSIZE)) == NULL) { RETERR(INSMEM) } opr->o_type = LITERAL; if ((opr->o_value.ov_char.ovc_string = CALLOC(strlen(dbv_tstring)+1)) == NULL) { CFREE(opr); RETERR(INSMEM) } opr->o_value.ov_char.ovc_type = tipe; strcpy(opr->o_value.ov_char.ovc_string,dbv_tstring); opr->o_value.ov_char.ovc_length = strlen(dbv_tstring); if (!oprand(opr)) { CFREE(opr->o_value.ov_char.ovc_string); CFREE(opr); return (FALSE); } *result = tipe; return (TRUE); } freelit(cptr) union codecell *cptr; { int catch; #ifdef COMDEB printf("com:freelit - entry\n"); #endif for (catch = 0; ((*cptr).c_operator != XSTOP) && (catch < CODEMAX); cptr++, catch++) { #ifdef COMDEB printf("com:freelit - op = %d, ty = %d\n",(*cptr).c_operator, (*cptr).c_operand->o_type); #endif if ((*cptr).c_operator == XPUSH) { if ((*++cptr).c_operand->o_type == LITERAL) CFREE((*cptr).c_operand->o_value.ov_char.ovc_string); CFREE((*cptr).c_operand); } } #ifdef COMDEB printf("exit\n"); #endif } r).c_operand->o_value.ov