void BtreeBuilder<V>::buildNextLevel(DiskLoc loc) { int levels = 1; while( 1 ) { if( loc.btree<V>()->tempNext().isNull() ) { // only 1 bucket at this level. we are done. getDur().writingDiskLoc(idx.head) = loc; break; } levels++; DiskLoc upLoc = BtreeBucket<V>::addBucket(idx); DiskLoc upStart = upLoc; BtreeBucket<V> *up = upLoc.btreemod<V>(); DiskLoc xloc = loc; while( !xloc.isNull() ) { if ( getDur().commitIfNeeded() ) { b = cur.btreemod<V>(); up = upLoc.btreemod<V>(); } BtreeBucket<V> *x = xloc.btreemod<V>(); Key k; DiskLoc r; x->popBack(r,k); bool keepX = ( x->n != 0 ); DiskLoc keepLoc = keepX ? xloc : x->nextChild; if ( ! up->_pushBack(r, k, ordering, keepLoc) ) { // current bucket full DiskLoc n = BtreeBucket<V>::addBucket(idx); up->setTempNext(n); upLoc = n; up = upLoc.btreemod<V>(); up->pushBack(r, k, ordering, keepLoc); } DiskLoc nextLoc = x->tempNext(); // get next in chain at current level if ( keepX ) { x->parent = upLoc; } else { if ( !x->nextChild.isNull() ) { DiskLoc ll = x->nextChild; ll.btreemod<V>()->parent = upLoc; //(x->nextChild.btreemod<V>())->parent = upLoc; } x->deallocBucket( xloc, idx ); } xloc = nextLoc; } loc = upStart; mayCommitProgressDurably(); } if( levels > 1 ) log(2) << "btree levels: " << levels << endl; }
void BtreeBuilder<V>::buildNextLevel(DiskLoc loc, bool mayInterrupt) { int levels = 1; while( 1 ) { if( _getBucket(loc)->tempNext().isNull() ) { // only 1 bucket at this level. we are done. _btreeState->setHead( loc ); break; } levels++; DiskLoc upLoc = BtreeBucket<V>::addBucket(_btreeState); DiskLoc upStart = upLoc; BtreeBucket<V> *up = _getModifiableBucket( upLoc ); DiskLoc xloc = loc; while( !xloc.isNull() ) { killCurrentOp.checkForInterrupt( !mayInterrupt ); if ( getDur().commitIfNeeded() ) { b = _getModifiableBucket( cur ); up = _getModifiableBucket( upLoc ); } BtreeBucket<V> *x = _getModifiableBucket( xloc ); Key k; DiskLoc r; x->popBack(r,k); bool keepX = ( x->n != 0 ); DiskLoc keepLoc = keepX ? xloc : x->nextChild; if ( ! up->_pushBack(r, k, _btreeState->ordering(), keepLoc) ) { // current bucket full DiskLoc n = BtreeBucket<V>::addBucket(_btreeState); up->setTempNext(n); upLoc = n; up = _getModifiableBucket( upLoc ); up->pushBack(r, k, _btreeState->ordering(), keepLoc); } DiskLoc nextLoc = x->tempNext(); // get next in chain at current level if ( keepX ) { x->parent = upLoc; } else { if ( !x->nextChild.isNull() ) { DiskLoc ll = x->nextChild; _getModifiableBucket(ll)->parent = upLoc; //(x->nextChild.btreemod<V>())->parent = upLoc; } x->deallocBucket( _btreeState, xloc ); } xloc = nextLoc; } loc = upStart; mayCommitProgressDurably(); } if( levels > 1 ) { LOG(2) << "btree levels: " << levels << endl; } }