1: # include "../ingres.h" 2: # include "../tree.h" 3: # include "../symbol.h" 4: # include "../access.h" 5: # include "decomp.h" 6: 7: 8: /** 9: ** usubr.c 10: ** 11: ** utility routines to handle setting up params, etc for DBU calls 12: **/ 13: 14: 15: 16: /* 17: * generate domain names, formats 18: */ 19: domnam(lnp, pre) 20: struct querytree **lnp; 21: char *pre; 22: { 23: 24: register char suf, *n, **p; 25: char name[MAXNAME]; 26: 27: suf = '1'; 28: for (n=name; *n++= *pre++;); 29: *n = '\0'; 30: n--; 31: for (p=(char **)lnp; *p; p++) 32: { 33: *n = suf++; 34: setp(name); 35: setp(format(*p)); 36: } 37: return; 38: } 39: 40: 41: /* 42: ** Parameter buffer for use in calling dbu routines. 43: ** The buffer is manipulated by setp() and initp(). 44: ** It is interrogated by call_dbu(). 45: */ 46: 47: char *Pv[PARGSIZE]; /* array of pointers to parameters */ 48: char Pbuffer[PBUFSIZE]; /* space for actual parameters */ 49: 50: int Pcount; /* next free char in Pbuffer */ 51: int Pc; /* number of parameters */ 52: 53: initp() 54: 55: /* 56: ** Init parameter buffer to have no params. 57: */ 58: 59: { 60: Pc = 0; 61: Pcount = 0; 62: } 63: 64: 65: setp(s) 66: char *s; 67: 68: /* 69: ** Copy the paramer s into the parameter buffer. 70: */ 71: 72: { 73: register char *r, *p; 74: register int i; 75: 76: r = s; 77: i = Pcount; 78: p = &Pbuffer[i]; 79: 80: /* copy parameter */ 81: Pv[Pc++] = p; 82: while (*p++ = *r++) 83: i++; 84: 85: Pcount = ++i; 86: 87: /* check for overflow */ 88: if (i > PBUFSIZE || Pc >= PARGSIZE) 89: syserr("setp overflow chars=%d,args=%d", i, Pc); 90: } 91: 92: /* 93: * gets format in ascii from RESDOM or AOP node 94: */ 95: char * 96: format(p) 97: struct querytree *p; 98: { 99: 100: static char buf[10]; 101: register char *b; 102: 103: b = buf; 104: 105: *b++ = ((struct qt_var *)p)->frmt; 106: itoa(((struct qt_var *)p)->frml & I1MASK, b); 107: return(buf); 108: } 109: 110: 111: /* 112: * makes list of nodes (depth first) 113: */ 114: lnode(nod, lnodv, count) 115: struct querytree *nod, *lnodv[]; 116: int count; 117: { 118: register struct querytree *q; 119: register int i; 120: 121: i = count; 122: q = nod; 123: 124: if (q && q->sym.type != TREE) 125: { 126: i = lnode(q->left, lnodv, i); 127: lnodv[i++] = q; 128: } 129: return(i); 130: } 131: 132: 133: 134: 135: dstr_rel(relnum) 136: int relnum; 137: 138: /* 139: ** Immediately destroys the relation if it is an _SYS 140: */ 141: 142: { 143: initp(); 144: dstr_mark(relnum); 145: dstr_flush(0); 146: } 147: 148: 149: dstr_mark(relnum) 150: int relnum; 151: 152: /* 153: ** Put relation on list of relations to be 154: ** destroyed. A call to initp() must be 155: ** made before any calls to dstr_mark(). 156: ** 157: ** A call to dstr_flush() will actually have 158: ** the relations exterminated 159: */ 160: 161: { 162: register char *p; 163: char *rnum_convert(); 164: 165: if (rnum_temp(relnum)) 166: { 167: p = rnum_convert(relnum); 168: # ifdef xDTR1 169: if (tTf(3, 4)) 170: printf("destroying %s\n", p); 171: # endif 172: setp(p); 173: specclose(relnum); /* guarantee that relation is closed and descriptor destroyed */ 174: rnum_remove(relnum); 175: } 176: } 177: 178: 179: dstr_flush(errflag) 180: int errflag; 181: 182: /* 183: ** call destroy if any relations are 184: ** in the parameter vector 185: */ 186: 187: { 188: if (Pc) 189: call_dbu(mdDESTROY, errflag); 190: } 191: 192: 193: mak_t_rel(tree, prefix, rnum) 194: struct querytree *tree; 195: char *prefix; 196: int rnum; 197: 198: /* 199: ** Make a temporary relation to match 200: ** the target list of tree. 201: ** 202: ** If rnum is positive, use it as the relation number, 203: ** Otherwise allocate a new one. 204: */ 205: 206: { 207: char *lnodv[MAXDOM + 1]; 208: register int i, relnum; 209: 210: initp(); 211: setp("0"); /* initial relstat field */ 212: relnum = rnum < 0 ? rnum_alloc() : rnum; 213: setp(rnum_convert(relnum)); 214: lnodv[lnode(tree->left, lnodv, 0)] = 0; 215: domnam(lnodv, prefix); 216: 217: call_dbu(mdCREATE, FALSE); 218: return (relnum); 219: } 220: 221: 222: struct querytree **mksqlist(tree, var) 223: struct querytree *tree; 224: int var; 225: { 226: register struct querytree **sq; 227: register int i; 228: static struct querytree *sqlist[MAXRANGE]; 229: 230: sq = sqlist; 231: for (i = 0; i < MAXRANGE; i++) 232: *sq++ = 0; 233: 234: sqlist[var] = tree; 235: return (sqlist); 236: } 237: 238: 239: 240: 241: long rel_pages(tupcnt, width) 242: long tupcnt; 243: int width; 244: { 245: register int tups_p_page; 246: 247: tups_p_page = (PGSIZE - 12) / (width + 2); 248: return ((tupcnt + tups_p_page - 1) / tups_p_page); 249: }