1: # include "../ingres.h" 2: # include "../symbol.h" 3: # include "../tree.h" 4: # include "qrymod.h" 5: 6: 7: /* 8: ** RANGE.C -- range table manipulation 9: ** 10: ** Defines: 11: ** declare -- declare variable 12: ** clrrange -- clear range table 13: ** mapvars -- map varno's in a tree to unique numbers 14: ** Remap[] -- a mapping from specified (preferred) varno's 15: ** to actual varno's. -1 indicates no mapping. 16: ** Presumably this cannot be set when reading an 17: ** original query tree, but can happen easily when 18: ** reading a tree from 'tree' catalog. 19: ** Rangev[] -- the range table. 20: ** 21: ** Required By: 22: ** main 23: ** treeio 24: ** 25: ** Files: 26: ** none 27: ** 28: ** Trace Flags: 29: ** 11, 12 30: ** 31: ** History: 32: ** 2/14/79 -- version 6.2 release. 33: ** 2/25/78 (eric) -- written 34: */ 35: 36: 37: int Remap[MAXVAR + 1]; 38: struct rngtab Rangev[MAXVAR + 1]; 39: /* 40: ** CLRRANGE -- clear range table(s) 41: ** 42: ** The range table (Rangev) and range table map (Remap) are 43: ** initialized in one of two ways. 44: ** 45: ** Parameters: 46: ** prim -- if TRUE, the primary range table (Rangev) 47: ** is cleared and Remap is set to be FULL (for 48: ** reading in an initial query). If FALSE, 49: ** Rangev is untouched, but Remap is cleared. 50: ** 51: ** Returns: 52: ** none 53: ** 54: ** Side Effects: 55: ** Rangev[i].rused set to FALSE for all entries. 56: ** Remap[i] set to -1 or MAXVAR + 1 for all entries. 57: ** 58: ** Requires: 59: ** Rangev 60: ** Remap 61: ** 62: ** Called By: 63: ** main 64: ** gettree 65: ** 66: ** Diagnostics: 67: ** none 68: ** 69: ** Syserrs: 70: ** none 71: */ 72: 73: clrrange(prim) 74: int prim; 75: { 76: register int i; 77: register int p; 78: 79: p = prim; 80: 81: for (i = 0; i < MAXVAR + 1; i++) 82: { 83: if (p) 84: { 85: Rangev[i].rused = FALSE; 86: Remap[i] = MAXVAR + 1; 87: } 88: else 89: Remap[i] = -1; 90: } 91: } 92: /* 93: ** DECLARE -- declare a range variable 94: ** 95: ** A range variable is declared. If possible, the preferred varno 96: ** stated is used (this is the one already in the tree). This 97: ** should always be possible when reading the original tree (and 98: ** should probably stay this way to make debugging easier). When 99: ** not possible, a new varno is chosen, and Remap[oldvarno] is 100: ** set to newvarno, so that the tree can later be patched up by 101: ** 'mapvars' (below). 102: ** 103: ** Parameters: 104: ** varno -- the preferred varno. 105: ** name -- the relation name. 106: ** stat -- the 'relstat' of this relation. 107: ** 108: ** Returns: 109: ** none 110: ** (non-local on error) 111: ** 112: ** Side Effects: 113: ** Rangev and possible Remap are updated. No Rangev 114: ** entry is ever touched if the 'rused' field 115: ** is set. 116: ** 117: ** Requires: 118: ** Rangev 119: ** Remap 120: ** 121: ** Called By: 122: ** readqry 123: ** 124: ** Trace Flags: 125: ** 11 126: ** 127: ** Diagnostics: 128: ** 3100 -- too many variables -- we have run out of 129: ** space in the range table. This "cannot happen" 130: ** when reading the original tree, but can happen 131: ** when reading another tree from the 'tree' 132: ** catalog. 133: ** 134: ** Syserrs: 135: ** %d redec -- the variable stated has been declared 136: ** twice in the range table. Actually, if reading 137: ** the original query, it means declared twice; 138: ** if reading from the 'tree' catalog, it means 139: ** declared THREE times (once in the original 140: ** query and twice in the catalog). 141: */ 142: 143: declare(varno, name, owner, stat) 144: int varno; 145: char *name; 146: char owner[2]; 147: int stat; 148: { 149: register int i; 150: register int vn; 151: register int s; 152: 153: vn = varno; 154: s = stat; 155: 156: /* check for preferred slot in range table available */ 157: if (Rangev[vn].rused) 158: { 159: /* used: check if really redeclared */ 160: if (Remap[vn] >= 0) 161: syserr("declare: %d redec", vn); 162: 163: /* try to find another slot */ 164: for (i = 0; i < MAXVAR + 1; i++) 165: if (!Rangev[i].rused) 166: break; 167: 168: if (i >= MAXVAR + 1) 169: { 170: ferror(3100, Qmode, -1, name, 0); /* too many variables */ 171: } 172: 173: Remap[vn] = i; 174: vn = i; 175: } 176: 177: /* declare variable in the guaranteed empty slot */ 178: bmove(name, Rangev[vn].relid, MAXNAME); 179: bmove(owner, Rangev[vn].rowner, 2); 180: Rangev[vn].rstat = s; 181: Rangev[vn].rused = TRUE; 182: 183: # ifdef xQTR2 184: if (tTf(11, 0)) 185: printf("declare(%d, %.12s, %.2s, %o) into slot %d\n", 186: varno, name, owner, s, vn); 187: # endif 188: # ifdef xQTR3 189: if (tTf(11, 1)) 190: printf("declare: %.12s%.2s 0%o %d\n", Rangev[vn].relid, 191: Rangev[vn].rowner, Rangev[vn].rstat, Rangev[vn].rused); 192: # endif 193: } 194: /* 195: ** MAPVARS -- remap varno's to be unique in 'tree' tree 196: ** 197: ** A tree is scanned for VAR nodes; when found, the 198: ** mapping defined in Remap[] is applied. This is done so that 199: ** varno's as defined in trees in the 'tree' catalog will be 200: ** unique with respect to varno's in the user's query tree. For 201: ** example, if the view definition uses variable 1 and the user's 202: ** query also uses variable 1, the routine 'declare' will (when 203: ** called to define the view definition varno 1) allocate a new 204: ** varno (e.g. 3) in a free slot in the range table, and put 205: ** the index of the new slot into the corresponding word of Remap; 206: ** in this example, Remap[1] == 3. This routine does the actual 207: ** mapping in the tree. 208: ** 209: ** Parameters: 210: ** tree -- pointer to tree to be remapped. 211: ** 212: ** Returns: 213: ** none 214: ** 215: ** Side Effects: 216: ** the tree pointed to by 'tree' is modified according 217: ** to Remap[]. 218: ** 219: ** Requires: 220: ** Remap -- range table mapping. 221: ** 222: ** Called By: 223: ** gettree 224: ** 225: ** Trace Flags: 226: ** 12 227: ** 228: ** Diagnostics: 229: ** none 230: ** 231: ** Syserrs: 232: ** none 233: */ 234: 235: mapvars(tree) 236: QTREE *tree; 237: { 238: register QTREE *t; 239: register int i; 240: 241: t = tree; 242: # ifdef xQTR3 243: if (tTf(12, 0) && t != NULL && t->sym.type == ROOT) 244: { 245: treepr(t, "mapvars:"); 246: for (i = 0; i < MAXVAR + 1; i++) 247: if (Rangev[i].rused && Remap[i] >= 0) 248: printf("\t%d => %d\n", i, Remap[i]); 249: } 250: # endif 251: 252: while (t != NULL) 253: { 254: /* map right subtree */ 255: mapvars(t->right); 256: 257: /* check this node */ 258: if (t->sym.type == VAR) 259: { 260: if ((i = Remap[((struct qt_var *)t)->varno]) >= 0) 261: ((struct qt_var *)t)->varno = i; 262: } 263: 264: /* map left subtree (iteratively) */ 265: t = t->left; 266: } 267: }