|
|
1.1 ! root 1: #include "cbt.h" ! 2: #include "pr.h" ! 3: ! 4: typedef union { ! 5: ndaddr na; ! 6: lfaddr la; ! 7: } addr; ! 8: static char splitting[MXHT+1]; ! 9: extern bfile *curbf; ! 10: extern ndaddr oldnode(), newnode(); ! 11: extern char *malloc(); ! 12: ! 13: extern long brecwrite(); ! 14: ! 15: bwrite(bf, key, rec) mbuf key, rec; bfile *bf; ! 16: { addr u; ! 17: int n; ! 18: if(bf == NULL) ! 19: return(EOF); ! 20: if(!bf->rdwrt) { ! 21: errno = BNOWRITE; ! 22: return(EOF); ! 23: } ! 24: if(notran(bf)) ! 25: return(EOF); ! 26: if(key.mlen > MAXKLEN) ! 27: return(EOF); ! 28: if(!treeonly(bf)) { ! 29: u.la.llen = rec.mlen; ! 30: u.la.lloc = brecwrite(rec); ! 31: if(u.la.lloc == EOF) ! 32: return(EOF); ! 33: } ! 34: if(desce(bf, key, (private *)NULL) == EOF) ! 35: return(EOF); ! 36: n = xinsert(0, key, u); ! 37: (void) bseek(bf, key); ! 38: return(n); ! 39: } ! 40: ! 41: fixpath(bf) ! 42: bfile *bf; ! 43: { addr u; ! 44: hdr *b; ! 45: int i, n, j; ! 46: for(i = 0; i < bf->height; i++) { ! 47: if(!mustwrite(bf, i)) ! 48: continue; ! 49: n = bf->loc[i]; ! 50: if((u.na = oldnode(i)) == EOF) ! 51: return(EOF); ! 52: b = bf->path[i+1]; ! 53: for(j = 0; j <= b->kcnt; j++) ! 54: if(*ndadr(b, j) == n) ! 55: break; ! 56: if(j > b->kcnt){ /* curtains, the parent doesn't point to us */ ! 57: errno = BFATAL; ! 58: return(EOF); ! 59: } ! 60: *ndadr(b, j) = u.na; ! 61: mustwrite(bf, i + 1) = 1; ! 62: } ! 63: return(0); ! 64: } ! 65: ! 66: xinsert(lev, key, u) mbuf key; addr u; ! 67: { private x; ! 68: int n, dellen; ! 69: hdr *b = curbf->path[lev]; ! 70: char ba[NDSZ], bb[NDSZ]; ! 71: dkey *dx, *dy; ! 72: if(splitting[lev]) ! 73: if(desce(curbf, key, (private *)NULL) == EOF) ! 74: return(EOF); ! 75: n = xscan(b, key, &x); ! 76: if(x.match == FOUND) { ! 77: if(treeonly(curbf)) ! 78: return(FOUND); ! 79: else if(lev) ! 80: *ndadr(b, n) = u.na; ! 81: else ! 82: *lfadr(b, n) = u.la; ! 83: mustwrite(curbf, lev) = 1; ! 84: return(FOUND); ! 85: } ! 86: dx = (dkey *)ba; ! 87: dy = (dkey *)bb; ! 88: dellen = newx(&x, key, dx, dy); ! 89: if(lev) ! 90: dellen += sizeof(ndaddr); ! 91: else if(!treeonly(curbf)) ! 92: dellen += sizeof(lfaddr); ! 93: if(dellen > nfree(b)) { ! 94: if(nsplit(lev) == EOF) ! 95: return(EOF); ! 96: splitting[lev] = 1; ! 97: n = xinsert(lev, key, u); ! 98: splitting[lev] = 0; ! 99: return(n); ! 100: } ! 101: addaddr(b, n, u); ! 102: newkeys(b, &x, dx, dy); ! 103: b->kcnt++; ! 104: nfree(b) -= dellen; ! 105: mustwrite(curbf, lev) = 1; ! 106: return(NOTFOUND); ! 107: } ! 108: ! 109: newx(x, key, c, d) private *x; mbuf key; dkey *c, *d; ! 110: { int i, j; ! 111: if(x->match != EOF) ! 112: c->dcom = x->ocom; ! 113: else c->dcom = x->ncom; ! 114: i = key.mlen - c->dcom; ! 115: c->dlen = DKEYSZ + i; ! 116: mvgbt(c->dkey, key.mdata + c->dcom, i); ! 117: if(x->match == EOF) ! 118: return(c->dlen); ! 119: j = x->ncom - x->d->dcom; ! 120: d->dcom = x->ncom; ! 121: d->dlen = x->d->dlen - j; ! 122: mvgbt(d->dkey, x->d->dkey + j, d->dlen - DKEYSZ); ! 123: return(c->dlen - j); ! 124: } ! 125: ! 126: addaddr(b, n, u) ! 127: hdr *b; ! 128: addr u; ! 129: { ! 130: if(b->hlev) { ! 131: mvgbt((char *)ndadr(b, b->kcnt + 1), ! 132: (char *)ndadr(b, b->kcnt), ! 133: sizeof(ndaddr) * (b->kcnt + 1 - n) ); ! 134: *ndadr(b, n) = u.na; ! 135: return; ! 136: } ! 137: if(treeonly(curbf)) ! 138: return; ! 139: mvgbt((char *)lfadr(b, b->kcnt), (char *)lfadr(b, b->kcnt - 1), ! 140: sizeof(lfaddr) * (b->kcnt - n)); ! 141: *lfadr(b, n) = u.la; ! 142: } ! 143: ! 144: newkeys(b, x, c, d) ! 145: hdr *b; ! 146: private *x; ! 147: dkey *c, *d; ! 148: { int n; ! 149: char *ffree; ! 150: if(b->hlev) ! 151: ffree = (char *)ndadr(b, b->kcnt) - nfree(b); ! 152: else if(treeonly(curbf)) ! 153: ffree = (char *)&nfree(b) - nfree(b); ! 154: else ! 155: ffree = (char *)lfadr(b, b->kcnt - 1) - nfree(b); ! 156: if(x->match != EOF) { ! 157: n = c->dlen + d->dlen; ! 158: n -= x->d->dlen; ! 159: mvgbt((char *)x->d + n, (char *)x->d, ffree - (char *)x->d); ! 160: mvgbt((char *)x->d, (char *)c, c->dlen); ! 161: mvgbt((char *)x->d + c->dlen, (char *)d, d->dlen); ! 162: } ! 163: else if(b->kcnt > 0) ! 164: mvgbt((char *)x->d + x->d->dlen, (char *)c, c->dlen); ! 165: else ! 166: mvgbt((char *)x->d, (char *)c, c->dlen); ! 167: } ! 168: ! 169: nsplit(lev) ! 170: { dkey *tod, *fromd; ! 171: char prefix[MAXKLEN + 10]; ! 172: hdr *b = curbf->path[lev]; ! 173: mbuf key; ! 174: addr u; ! 175: union { ! 176: lfaddr *la; ! 177: ndaddr *na; ! 178: } from, to; ! 179: int mvd, x, i, count, n; ! 180: hdr *ha; ! 181: char a[NDSZ]; ! 182: ! 183: x = (NDSZ - sizeof(hdr) - sizeof(trailer)) / 2; ! 184: ha = (hdr *) a; ! 185: mvd = count = 0; ! 186: tod = (dkey *)(ha + 1); ! 187: fromd = (dkey *)(b + 1); ! 188: if(lev == 0) { ! 189: to.la = lfadr(ha, 0); ! 190: from.la = lfadr(b, 0); ! 191: } ! 192: else { ! 193: to.na = ndadr(ha, 0); ! 194: from.na = ndadr(b, 0); ! 195: } ! 196: *ha = *b; ! 197: n = (b->kcnt + 1)/2; ! 198: if(lev && b->kcnt - n <= 1) ! 199: n--; ! 200: for(; count < n && mvd <= x; count++) { ! 201: mvgbt((char *)tod, (char *)fromd, fromd->dlen); ! 202: mvd += fromd->dlen; ! 203: tod = (dkey *)((char *)tod + fromd->dlen); ! 204: fromd = (dkey *)((char *)fromd + fromd->dlen); ! 205: if(lev) { ! 206: *to.na-- = *from.na--; ! 207: mvd += sizeof(ndaddr); ! 208: } ! 209: else if(!treeonly(curbf)) { ! 210: *to.la-- = *from.la--; ! 211: mvd += sizeof(lfaddr); ! 212: } ! 213: } ! 214: if(lev) { /* another pointer for non-leaves */ ! 215: *to.na-- = *from.na--; ! 216: mvd += sizeof(ndaddr); ! 217: } ! 218: ha->kcnt = count; ! 219: nfree(ha) = NDSZ - sizeof(hdr) - sizeof(trailer) - mvd; ! 220: /* if lev == 0, we promote the last key, else the next key */ ! 221: key.mlen = lastkey(ha, prefix); ! 222: if(lev) { ! 223: mvgbt(prefix + fromd->dcom, fromd->dkey, fromd->dlen - DKEYSZ); ! 224: key.mlen = fromd->dcom + fromd->dlen - DKEYSZ; ! 225: count++; ! 226: fromd = (dkey *)((char *)fromd + fromd->dlen); ! 227: } ! 228: u.na = newnode(ha); ! 229: if(u.na == EOF) { /* error while splitting */ ! 230: curbf->fatal++; ! 231: return(EOF); ! 232: } ! 233: key.mdata = prefix; ! 234: /* other half */ ! 235: if(lev == 0) ! 236: to.la = lfadr(ha, 0); ! 237: else ! 238: to.na = ndadr(ha, 0); ! 239: tod = (dkey *)(ha + 1); ! 240: tod->dcom = 0; ! 241: tod->dlen = fromd->dlen + fromd->dcom; ! 242: mvgbt(tod->dkey, prefix, fromd->dcom); ! 243: mvgbt(tod->dkey + fromd->dcom, fromd->dkey, fromd->dlen - DKEYSZ); ! 244: mvd = tod->dlen; ! 245: fromd = (dkey *)((char *)fromd + fromd->dlen); ! 246: tod = (dkey *)((char *)tod + tod->dlen); ! 247: if(lev) { ! 248: *to.na-- = *from.na--; ! 249: mvd += sizeof(ndaddr); ! 250: } ! 251: else if(!treeonly(curbf)) { ! 252: *to.la-- = *from.la--; ! 253: mvd += sizeof(lfaddr); ! 254: } ! 255: count++; ! 256: for(i = 1; count < b->kcnt; i++, count++) { ! 257: mvgbt((char *)tod, (char *)fromd, fromd->dlen); ! 258: mvd += fromd->dlen; ! 259: tod = (dkey *)((char *)tod + tod->dlen); ! 260: fromd = (dkey *)((char *)fromd + fromd->dlen); ! 261: if(lev) { ! 262: *to.na-- = *from.na--; ! 263: mvd += sizeof(ndaddr); ! 264: } ! 265: else if(!treeonly(curbf)) { ! 266: *to.la-- = *from.la--; ! 267: mvd += sizeof(lfaddr); ! 268: } ! 269: ! 270: } ! 271: if(lev) { ! 272: *to.na-- = *from.na--; ! 273: mvd += sizeof(ndaddr); ! 274: } ! 275: ha->kcnt = i; ! 276: nfree(ha) = NDSZ - sizeof(hdr) - sizeof(trailer) - mvd; ! 277: mvgbt((char *)b, (char *)ha, NDSZ); ! 278: mustwrite(curbf, lev) = 1; ! 279: if(lev < curbf->height) { ! 280: if(xinsert(lev + 1, key, u) == EOF) { ! 281: curbf->fatal++; ! 282: return(EOF); ! 283: } ! 284: } ! 285: else ! 286: return(newroot(u, key, b)); ! 287: return(0); ! 288: } ! 289: ! 290: newroot(u, key, b) ! 291: addr u; ! 292: mbuf key; ! 293: hdr *b; ! 294: { hdr *x; ! 295: dkey *d; ! 296: if(curbf->height >= MXHT) { ! 297: errno = BTALL; ! 298: curbf->fatal++; ! 299: return(EOF); ! 300: } ! 301: if((x = curbf->path[b->hlev + 1] = (hdr *)malloc(NDSZ)) == NULL) { ! 302: errno = BNOMEM; ! 303: curbf->fatal++; ! 304: return(EOF); ! 305: } ! 306: *x = *b; ! 307: x->hlev++; ! 308: d = (dkey *)(x + 1); ! 309: d->dlen = DKEYSZ + key.mlen; ! 310: d->dcom = 0; ! 311: mvgbt(d->dkey, key.mdata, key.mlen); ! 312: *ndadr(x, 0) = u.na; ! 313: *ndadr(x, 1) = curbf->loc[b->hlev] = newnode(b); ! 314: x->kcnt = 1; ! 315: nfree(x) = NDSZ - sizeof(hdr) - sizeof(trailer) - DKEYSZ ! 316: - key.mlen - 2 * sizeof(ndaddr); ! 317: mustwrite(curbf, ++curbf->height) = 1; ! 318: return(0); ! 319: } ! 320: ! 321: lastkey(b, s) ! 322: hdr *b; ! 323: char *s; ! 324: { int i, n; ! 325: dkey *p; ! 326: p = (dkey *)(b + 1); ! 327: for(n = i = 0; i < b->kcnt; i++) { ! 328: mvgbt(s + p->dcom, p->dkey, p->dlen - DKEYSZ); ! 329: n = p->dlen + p->dcom - DKEYSZ; ! 330: p = (dkey *)((char *) p + p->dlen); ! 331: } ! 332: return(n); ! 333: } ! 334: ! 335: static struct D { struct D *a; char *b;} VER = {&VER,"\n82/10/9:bwrite.c\n"}; ! 336: /*0010010000010101*/
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.