Ejemplo n.º 1
0
static Res NInit(Pool pool, Arena arena, PoolClass klass, ArgList args)
{
  PoolN poolN;
  Res res;

  AVER(pool != NULL);
  AVERT(Arena, arena);
  AVERT(ArgList, args);
  UNUSED(klass); /* used for debug pools only */

  res = NextMethod(Pool, NPool, init)(pool, arena, klass, args);
  if (res != ResOK)
    goto failNextInit;
  poolN = CouldBeA(NPool, pool);
  
  /* Initialize pool-specific structures. */

  SetClassOfPoly(pool, CLASS(NPool));
  AVERC(PoolN, poolN);

  return ResOK;

failNextInit:
  AVER(res != ResOK);
  return res;
}
Ejemplo n.º 2
0
static Res AMSTInit(Pool pool, Arena arena, PoolClass klass, ArgList args)
{
  AMST amst;
  AMS ams;
  Res res;

  res = NextMethod(Pool, AMSTPool, init)(pool, arena, klass, args);
  if (res != ResOK)
    return res;

  amst = CouldBeA(AMSTPool, pool);
  ams = MustBeA(AMSPool, pool);

  ams->segSize = AMSTSegSizePolicy;
  ams->segClass = AMSTSegClassGet;
  amst->failSegs = TRUE;
  amst->splits = 0;
  amst->merges = 0;
  amst->badSplits = 0;
  amst->badMerges = 0;
  amst->bsplits = 0;
  amst->bmerges = 0;

  SetClassOfPoly(pool, CLASS(AMSTPool));
  amst->sig = AMSTSig;
  AVERC(AMSTPool, amst);

  return ResOK;
}
Ejemplo n.º 3
0
static Res MFSDescribe(Inst inst, mps_lib_FILE *stream, Count depth)
{
  Pool pool = CouldBeA(AbstractPool, inst);
  MFS mfs = CouldBeA(MFSPool, pool);
  Res res;

  if (!TESTC(MFSPool, mfs))
    return ResPARAM;
  if (stream == NULL)
    return ResPARAM;

  res = NextMethod(Inst, MFSPool, describe)(inst, stream, depth);
  if (res != ResOK)
    return res;

  return WriteF(stream, depth + 2,
                "unroundedUnitSize $W\n", (WriteFW)mfs->unroundedUnitSize,
                "extendBy $W\n", (WriteFW)mfs->extendBy,
                "extendSelf $S\n", WriteFYesNo(mfs->extendSelf),
                "unitSize $W\n", (WriteFW)mfs->unitSize,
                "freeList $P\n", (WriteFP)mfs->freeList,
                "total $W\n", (WriteFW)mfs->total,
                "free $W\n", (WriteFW)mfs->free,
                "tractList $P\n", (WriteFP)mfs->tractList,
                NULL);
}
Ejemplo n.º 4
0
static Res rankBufInit(Buffer buffer, Pool pool, Bool isMutator, ArgList args)
{
  Rank rank = BUFFER_RANK_DEFAULT;
  Res res;
  ArgStruct arg;

  AVERT(ArgList, args);
  if (ArgPick(&arg, args, MPS_KEY_RANK))
    rank = arg.val.rank;
  AVERT(Rank, rank);

  /* Initialize the superclass fields first via next-method call */
  res = NextMethod(Buffer, RankBuf, init)(buffer, pool, isMutator, args);
  if (res != ResOK)
    return res;

  BufferSetRankSet(buffer, RankSetSingle(rank));

  SetClassOfPoly(buffer, CLASS(RankBuf));
  AVERC(RankBuf, buffer);
  
  EVENT4(BufferInitRank, buffer, pool, BOOLOF(buffer->isMutator), rank);

  return ResOK;
}
Ejemplo n.º 5
0
static Res amstSegInit(Seg seg, Pool pool, Addr base, Size size, ArgList args)
{
  AMSTSeg amstseg;
  AMST amst;
  Res res;

  /* Initialize the superclass fields first via next-method call */
  res = NextMethod(Seg, AMSTSeg, init)(seg, pool, base, size, args);
  if (res != ResOK)
    return res;
  amstseg = CouldBeA(AMSTSeg, seg);

  AVERT(Pool, pool);
  amst = PoolAMST(pool);
  AVERT(AMST, amst);
  /* no useful checks for base and size */

  amstseg->next = NULL;
  amstseg->prev = NULL;

  SetClassOfPoly(seg, CLASS(AMSTSeg));
  amstseg->sig = AMSTSegSig;
  AVERC(AMSTSeg, amstseg);

  return ResOK;
}
Ejemplo n.º 6
0
static void segBufFinish(Inst inst)
{
  Buffer buffer = MustBeA(Buffer, inst);
  SegBuf segbuf = MustBeA(SegBuf, buffer);
  AVER(BufferIsReset(buffer));
  segbuf->sig = SigInvalid;
  NextMethod(Inst, SegBuf, finish)(inst);
}
Ejemplo n.º 7
0
static Res MFSInit(Pool pool, Arena arena, PoolClass klass, ArgList args)
{
  Size extendBy = MFS_EXTEND_BY_DEFAULT;
  Bool extendSelf = TRUE;
  Size unitSize;
  MFS mfs;
  ArgStruct arg;
  Res res;

  AVER(pool != NULL);
  AVERT(Arena, arena);
  AVERT(ArgList, args);
  UNUSED(klass); /* used for debug pools only */
  
  ArgRequire(&arg, args, MPS_KEY_MFS_UNIT_SIZE);
  unitSize = arg.val.size;
  if (ArgPick(&arg, args, MPS_KEY_EXTEND_BY))
    extendBy = arg.val.size;
  if (ArgPick(&arg, args, MFSExtendSelf))
    extendSelf = arg.val.b;

  AVER(unitSize > 0);
  AVER(extendBy > 0);
  AVERT(Bool, extendSelf);

  res = NextMethod(Pool, MFSPool, init)(pool, arena, klass, args);
  if (res != ResOK)
    goto failNextInit;
  mfs = CouldBeA(MFSPool, pool);

  mfs->unroundedUnitSize = unitSize;

  if (unitSize < UNIT_MIN)
    unitSize = UNIT_MIN;
  unitSize = SizeAlignUp(unitSize, MPS_PF_ALIGN);
  if (extendBy < unitSize)
    extendBy = unitSize;
  extendBy = SizeArenaGrains(extendBy, arena);

  mfs->extendBy = extendBy;
  mfs->extendSelf = extendSelf;
  mfs->unitSize = unitSize;
  mfs->freeList = NULL;
  mfs->tractList = NULL;
  mfs->total = 0;
  mfs->free = 0;

  SetClassOfPoly(pool, CLASS(MFSPool));
  mfs->sig = MFSSig;
  AVERC(MFS, mfs);

  EVENT5(PoolInitMFS, pool, arena, extendBy, BOOLOF(extendSelf), unitSize);
  return ResOK;

failNextInit:
  AVER(res != ResOK);
  return res;
}
Ejemplo n.º 8
0
static Res amstSegSplit(Seg seg, Seg segHi,
                        Addr base, Addr mid, Addr limit)
{
  AMST amst;
  AMSTSeg amstseg, amstsegHi;
  Res res;

  AVERT(Seg, seg);
  AVER(segHi != NULL);  /* can't check fully, it's not initialized */
  amstseg = Seg2AMSTSeg(seg);
  amstsegHi = Seg2AMSTSeg(segHi);
  AVERT(AMSTSeg, amstseg);
  amst = PoolAMST(SegPool(seg));

  /* Split the superclass fields via direct next-method call */
  res = NextMethod(Seg, AMSTSeg, split)(seg, segHi, base, mid, limit);
  if (res != ResOK)
    goto failSuper;

  if (AMSTFailOperation(amst)) {
    amst->badSplits++;
    printf("B");
    goto failDeliberate;
  }

  /* Full initialization for segHi. */
  amstsegHi->next = amstseg->next;
  amstsegHi->prev = amstseg;
  amstsegHi->sig = AMSTSegSig;
  amstseg->next = amstsegHi;
  AVERT(AMSTSeg, amstseg);
  AVERT(AMSTSeg, amstsegHi);
  amst->splits++;
  printf("S");
  return ResOK;

failDeliberate:
  /* Call the anti-method. (see .fail) */
  res = NextMethod(Seg, AMSTSeg, merge)(seg, segHi, base, mid, limit);
  AVER(res == ResOK);
  res = ResFAIL;
failSuper:
  AVERT(AMSTSeg, amstseg);
  return res;
}
Ejemplo n.º 9
0
/* amstSegMerge -- AMSTSeg merge method
 *
 * .fail: Test proper handling of the most complex failure cases
 * by deliberately detecting failure sometimes after calling the
 * next method. We handle the error by calling the anti-method.
 * This isn't strictly safe <design/poolams#.split-merge.fail>.
 * But we assume here that we won't run out of memory when calling the
 * anti-method.
 */
static Res amstSegMerge(Seg seg, Seg segHi,
                        Addr base, Addr mid, Addr limit)
{
  AMST amst;
  AMSTSeg amstseg, amstsegHi;
  Res res;

  AVERT(Seg, seg);
  AVERT(Seg, segHi);
  amstseg = Seg2AMSTSeg(seg);
  amstsegHi = Seg2AMSTSeg(segHi);
  AVERT(AMSTSeg, amstseg);
  AVERT(AMSTSeg, amstsegHi);
  amst = PoolAMST(SegPool(seg));

  /* Merge the superclass fields via direct next-method call */
  res = NextMethod(Seg, AMSTSeg, merge)(seg, segHi, base, mid, limit);
  if (res != ResOK)
    goto failSuper;

  if (AMSTFailOperation(amst)) {
    amst->badMerges++;
    printf("D");
    goto failDeliberate;
  }

  amstseg->next = amstsegHi->next;
  amstsegHi->sig = SigInvalid;
  AVERT(AMSTSeg, amstseg);
  amst->merges++;
  printf("M");
  return ResOK;

failDeliberate:
  /* Call the anti-method (see .fail) */
  res = NextMethod(Seg, AMSTSeg, split)(seg, segHi, base, mid, limit);
  AVER(res == ResOK);
  res = ResFAIL;
failSuper:
  AVERT(AMSTSeg, amstseg);
  AVERT(AMSTSeg, amstsegHi);
  return res;
}
Ejemplo n.º 10
0
static void NFinish(Inst inst)
{
  Pool pool = MustBeA(AbstractPool, inst);
  PoolN poolN = MustBeA(NPool, pool);

  /* Finish pool-specific structures. */
  UNUSED(poolN);

  NextMethod(Inst, NPool, finish)(inst);
}
Ejemplo n.º 11
0
static void MFSFinish(Inst inst)
{
  Pool pool = MustBeA(AbstractPool, inst);
  MFS mfs = MustBeA(MFSPool, pool);

  MFSFinishTracts(pool, MFSTractFreeVisitor, UNUSED_POINTER);

  mfs->sig = SigInvalid;

  NextMethod(Inst, MFSPool, finish)(inst);
}
Ejemplo n.º 12
0
static Res NDescribe(Inst inst, mps_lib_FILE *stream, Count depth)
{
  Pool pool = CouldBeA(AbstractPool, inst);
  PoolN poolN = CouldBeA(NPool, pool);
  Res res;

  res = NextMethod(Inst, NPool, describe)(inst, stream, depth);
  if (res != ResOK)
    return res;

  /* This is where you'd output some information about pool fields. */
  UNUSED(poolN);

  return ResOK;
}
Ejemplo n.º 13
0
static void amstSegFinish(Inst inst)
{
  Seg seg = MustBeA(Seg, inst);
  AMSTSeg amstseg = MustBeA(AMSTSeg, seg);

  AVERT(AMSTSeg, amstseg);

  if (amstseg->next != NULL)
    amstseg->next->prev = NULL;
  if (amstseg->prev != NULL)
    amstseg->prev->next = NULL;

  amstseg->sig = SigInvalid;
  /* finish the superclass fields last */
  NextMethod(Inst, AMSTSeg, finish)(inst);
}
Ejemplo n.º 14
0
static Res SegAbsInit(Seg seg, Pool pool, Addr base, Size size, ArgList args)
{
  Arena arena;
  Addr addr, limit;
  Tract tract;
  
  AVER(seg != NULL);
  AVERT(Pool, pool);
  arena = PoolArena(pool);
  AVER(AddrIsArenaGrain(base, arena));
  AVER(SizeIsArenaGrains(size, arena));
  AVERT(ArgList, args);

  NextMethod(Inst, Seg, init)(CouldBeA(Inst, seg));

  limit = AddrAdd(base, size);
  seg->limit = limit;
  seg->rankSet = RankSetEMPTY;
  seg->white = TraceSetEMPTY;
  seg->nailed = TraceSetEMPTY;
  seg->grey = TraceSetEMPTY;
  seg->pm = AccessSetEMPTY;
  seg->sm = AccessSetEMPTY;
  seg->defer = WB_DEFER_INIT;
  seg->depth = 0;
  seg->queued = FALSE;
  seg->firstTract = NULL;
  RingInit(SegPoolRing(seg));
  
  TRACT_FOR(tract, addr, arena, base, limit) {
    AVERT(Tract, tract);
    AVER(TractP(tract) == NULL);
    AVER(!TractHasSeg(tract));
    AVER(TractPool(tract) == pool);
    AVER(TractWhite(tract) == TraceSetEMPTY);
    TRACT_SET_SEG(tract, seg);
    if (addr == base) {
      AVER(seg->firstTract == NULL);
      seg->firstTract = tract;
    }
    AVER(seg->firstTract != NULL);
  }
Ejemplo n.º 15
0
static void AMSTFinish(Inst inst)
{
  Pool pool = MustBeA(AbstractPool, inst);
  AMST amst = MustBeA(AMSTPool, pool);

  AVERT(AMST, amst);

  amst->sig = SigInvalid;

  printf("\nDestroying pool, having performed:\n");
  printf("    %"PRIuLONGEST" splits          (S)\n", (ulongest_t)amst->splits);
  printf("    %"PRIuLONGEST" merges          (M)\n", (ulongest_t)amst->merges);
  printf("    %"PRIuLONGEST" aborted splits  (B)\n", (ulongest_t)amst->badSplits);
  printf("    %"PRIuLONGEST" aborted merges  (D)\n", (ulongest_t)amst->badMerges);
  printf("  which included:\n");
  printf("    %"PRIuLONGEST" buffered splits (C)\n", (ulongest_t)amst->bsplits);
  printf("    %"PRIuLONGEST" buffered merges (J)\n", (ulongest_t)amst->bmerges);

  NextMethod(Inst, AMSTPool, finish)(inst);
}
Ejemplo n.º 16
0
static Res segBufDescribe(Inst inst, mps_lib_FILE *stream, Count depth)
{
  Buffer buffer = CouldBeA(Buffer, inst);
  SegBuf segbuf = CouldBeA(SegBuf, buffer);
  Res res;

  if (!TESTC(SegBuf, segbuf))
    return ResPARAM;
  if (stream == NULL)
    return ResPARAM;

  res = NextMethod(Inst, SegBuf, describe)(inst, stream, depth);
  if (res != ResOK)
    return res;

  return WriteF(stream, depth + 2,
                "Seg     $P\n", (WriteFP)segbuf->seg,
                "rankSet $U\n", (WriteFU)segbuf->rankSet,
                NULL);
}
Ejemplo n.º 17
0
static Res segBufInit(Buffer buffer, Pool pool, Bool isMutator, ArgList args)
{
  SegBuf segbuf;
  Res res;

  /* Initialize the superclass fields first via next-method call */
  res = NextMethod(Buffer, SegBuf, init)(buffer, pool, isMutator, args);
  if (res != ResOK)
    return res;
  segbuf = CouldBeA(SegBuf, buffer);

  segbuf->seg = NULL;
  segbuf->rankSet = RankSetEMPTY;

  SetClassOfPoly(buffer, CLASS(SegBuf));
  segbuf->sig = SegBufSig;
  AVERC(SegBuf, segbuf);

  EVENT3(BufferInitSeg, buffer, pool, BOOLOF(buffer->isMutator));
  return ResOK;
}
Ejemplo n.º 18
0
static Res BufferAbsDescribe(Inst inst, mps_lib_FILE *stream, Count depth)
{
  Buffer buffer = CouldBeA(Buffer, inst);
  Res res;

  if (!TESTC(Buffer, buffer))
    return ResPARAM;
  if (stream == NULL)
    return ResPARAM;

  res = NextMethod(Inst, Buffer, describe)(inst, stream, depth);
  if (res != ResOK)
    return res;

  return WriteF(stream, depth + 2,
                "serial $U\n", (WriteFU)buffer->serial,
                "Arena $P\n",       (WriteFP)buffer->arena,
                "Pool $P\n",        (WriteFP)buffer->pool,
                buffer->isMutator ? "Mutator" : "Internal", " Buffer\n",
                "mode $C$C$C$C (TRANSITION, LOGGED, FLIPPED, ATTACHED)\n",
                (WriteFC)((buffer->mode & BufferModeTRANSITION) ? 't' : '_'),
                (WriteFC)((buffer->mode & BufferModeLOGGED)     ? 'l' : '_'),
                (WriteFC)((buffer->mode & BufferModeFLIPPED)    ? 'f' : '_'),
                (WriteFC)((buffer->mode & BufferModeATTACHED)   ? 'a' : '_'),
                "fillSize $U\n",    (WriteFU)buffer->fillSize,
                "emptySize $U\n",   (WriteFU)buffer->emptySize,
                "alignment $W\n",   (WriteFW)buffer->alignment,
                "base $A\n",        (WriteFA)buffer->base,
                "initAtFlip $A\n",  (WriteFA)buffer->initAtFlip,
                "init $A\n",        (WriteFA)buffer->ap_s.init,
                "alloc $A\n",       (WriteFA)buffer->ap_s.alloc,
                "limit $A\n",       (WriteFA)buffer->ap_s.limit,
                "poolLimit $A\n",   (WriteFA)buffer->poolLimit,
                "alignment $W\n",   (WriteFW)buffer->alignment,
                "rampCount $U\n",   (WriteFU)buffer->rampCount,
                NULL);
}
Ejemplo n.º 19
0
/* AMSTBufferFill -- the pool class buffer fill method
 *
 * Calls next method - but possibly splits or merges the chosen
 * segment.
 *
 * .merge: A merge is performed when the next method returns the
 * entire segment, this segment had previously been split from the
 * segment below, and the segment below is appropriately similar
 * (i.e. not already attached to a buffer and similarly coloured)
 *
 * .split: If we're not merging, a split is performed if the next method
 * returns the entire segment, and yet lower half of the segment would
 * meet the request.
 */
static Res AMSTBufferFill(Addr *baseReturn, Addr *limitReturn,
                          Pool pool, Buffer buffer, Size size)
{
  Addr base, limit;
  Arena arena;
  AMS ams;
  AMST amst;
  Bool b;
  Seg seg;
  AMSTSeg amstseg;
  Res res;

  AVERT(Pool, pool);
  AVER(baseReturn != NULL);
  AVER(limitReturn != NULL);
  /* other parameters are checked by next method */
  arena = PoolArena(pool);
  ams = PoolAMS(pool);
  amst = PoolAMST(pool);

  /* call next method */
  res = NextMethod(Pool, AMSTPool, bufferFill)(&base, &limit, pool, buffer, size);
  if (res != ResOK)
    return res;

  b = SegOfAddr(&seg, arena, base);
  AVER(b);
  amstseg = Seg2AMSTSeg(seg);

  if (SegLimit(seg) == limit && SegBase(seg) == base) {
    if (amstseg->prev != NULL) {
      Seg segLo = AMSTSeg2Seg(amstseg->prev);
      if (!SegHasBuffer(segLo) &&
          SegGrey(segLo) == SegGrey(seg) &&
          SegWhite(segLo) == SegWhite(seg)) {
        /* .merge */
        Seg mergedSeg;
        Res mres;

        AMSUnallocateRange(ams, seg, base, limit);
        mres = SegMerge(&mergedSeg, segLo, seg);
        if (ResOK == mres) { /* successful merge */
          AMSAllocateRange(ams, mergedSeg, base, limit);
          /* leave range as-is */
        } else {            /* failed to merge */
          AVER(amst->failSegs); /* deliberate fails only */
          AMSAllocateRange(ams, seg, base, limit);
        }
      }

    } else {
      Size half = SegSize(seg) / 2;
      if (half >= size && SizeIsArenaGrains(half, arena)) {
        /* .split */
        Addr mid = AddrAdd(base, half);
        Seg segLo, segHi;
        Res sres;
        AMSUnallocateRange(ams, seg, mid, limit);
        sres = SegSplit(&segLo, &segHi, seg, mid);
        if (ResOK == sres) { /* successful split */
          limit = mid;  /* range is lower segment */
        } else {            /* failed to split */
          AVER(amst->failSegs); /* deliberate fails only */
          AMSAllocateRange(ams, seg, mid, limit);
        }

      }
    }
  }

  *baseReturn = base;
  *limitReturn = limit;
  return ResOK;
}
Ejemplo n.º 20
0
static Res MVTInit(Pool pool, Arena arena, PoolClass klass, ArgList args)
{
  Size align = MVT_ALIGN_DEFAULT;
  Size minSize = MVT_MIN_SIZE_DEFAULT;
  Size meanSize = MVT_MEAN_SIZE_DEFAULT;
  Size maxSize = MVT_MAX_SIZE_DEFAULT;
  Count reserveDepth = MVT_RESERVE_DEPTH_DEFAULT;
  Count fragLimit = MVT_FRAG_LIMIT_DEFAULT;
  Size reuseSize, fillSize;
  Count abqDepth;
  MVT mvt;
  Res res;
  ArgStruct arg;

  AVER(pool != NULL);
  AVERT(Arena, arena);
  AVERT(ArgList, args);
  UNUSED(klass); /* used for debug pools only */

  if (ArgPick(&arg, args, MPS_KEY_ALIGN))
    align = arg.val.align;
  if (ArgPick(&arg, args, MPS_KEY_MIN_SIZE))
    minSize = arg.val.size;
  if (ArgPick(&arg, args, MPS_KEY_MEAN_SIZE))
    meanSize = arg.val.size;
  if (ArgPick(&arg, args, MPS_KEY_MAX_SIZE))
    maxSize = arg.val.size;
  if (ArgPick(&arg, args, MPS_KEY_MVT_RESERVE_DEPTH))
    reserveDepth = arg.val.count;
  if (ArgPick(&arg, args, MPS_KEY_MVT_FRAG_LIMIT)) {
    /* pending complete fix for job003319 */
    AVER(0 <= arg.val.d);
    AVER(arg.val.d <= 1);
    fragLimit = (Count)(arg.val.d * 100);
  }

  AVERT(Align, align);
  /* This restriction on the alignment is necessary because of the use
     of a Freelist to store the free address ranges in low-memory
     situations. <design/freelist#.impl.grain.align>. */
  AVER(AlignIsAligned(align, FreelistMinimumAlignment));
  AVER(align <= ArenaGrainSize(arena));
  AVER(0 < minSize);
  AVER(minSize <= meanSize);
  AVER(meanSize <= maxSize);
  AVER(reserveDepth > 0);
  AVER(fragLimit <= 100);
  /* TODO: More parameter checks possible? */

  /* see <design/poolmvt#.arch.parameters> */
  fillSize = SizeArenaGrains(maxSize, arena);
  /* see <design/poolmvt#.arch.fragmentation.internal> */
  reuseSize = 2 * fillSize;
  abqDepth = (reserveDepth * meanSize + reuseSize - 1) / reuseSize;
  /* keep the abq from being useless */
  if (abqDepth < 3)
    abqDepth = 3;

  res = NextMethod(Pool, MVTPool, init)(pool, arena, klass, args);
  if (res != ResOK)
    goto failNextInit;
  mvt = CouldBeA(MVTPool, pool);

  res = LandInit(MVTFreePrimary(mvt), CLASS(CBSFast), arena, align, mvt,
                 mps_args_none);
  if (res != ResOK)
    goto failFreePrimaryInit;
 
  res = LandInit(MVTFreeSecondary(mvt), CLASS(Freelist), arena, align,
                 mvt, mps_args_none);
  if (res != ResOK)
    goto failFreeSecondaryInit;
  
  MPS_ARGS_BEGIN(foArgs) {
    MPS_ARGS_ADD(foArgs, FailoverPrimary, MVTFreePrimary(mvt));
    MPS_ARGS_ADD(foArgs, FailoverSecondary, MVTFreeSecondary(mvt));
    res = LandInit(MVTFreeLand(mvt), CLASS(Failover), arena, align, mvt,
                   foArgs);
  } MPS_ARGS_END(foArgs);
  if (res != ResOK)
    goto failFreeLandInit;

  res = ABQInit(arena, MVTABQ(mvt), (void *)mvt, abqDepth, sizeof(RangeStruct));
  if (res != ResOK)
    goto failABQInit;

  pool->alignment = align;
  pool->alignShift = SizeLog2(pool->alignment);
  mvt->reuseSize = reuseSize;
  mvt->fillSize = fillSize;
  mvt->abqOverflow = FALSE;
  mvt->minSize = minSize;
  mvt->meanSize = meanSize;
  mvt->maxSize = maxSize;
  mvt->fragLimit = fragLimit;
  mvt->splinter = FALSE;
  mvt->splinterBase = (Addr)0;
  mvt->splinterLimit = (Addr)0;
 
  /* accounting */
  mvt->size = 0;
  mvt->allocated = 0;
  mvt->available = 0;
  mvt->availLimit = 0;
  mvt->unavailable = 0;
 
  /* meters*/
  METER_INIT(mvt->segAllocs, "segment allocations", (void *)mvt);
  METER_INIT(mvt->segFrees, "segment frees", (void *)mvt);
  METER_INIT(mvt->bufferFills, "buffer fills", (void *)mvt);
  METER_INIT(mvt->bufferEmpties, "buffer empties", (void *)mvt);
  METER_INIT(mvt->poolFrees, "pool frees", (void *)mvt);
  METER_INIT(mvt->poolSize, "pool size", (void *)mvt);
  METER_INIT(mvt->poolAllocated, "pool allocated", (void *)mvt);
  METER_INIT(mvt->poolAvailable, "pool available", (void *)mvt);
  METER_INIT(mvt->poolUnavailable, "pool unavailable", (void *)mvt);
  METER_INIT(mvt->poolUtilization, "pool utilization", (void *)mvt);
  METER_INIT(mvt->finds, "ABQ finds", (void *)mvt);
  METER_INIT(mvt->overflows, "ABQ overflows", (void *)mvt);
  METER_INIT(mvt->underflows, "ABQ underflows", (void *)mvt);
  METER_INIT(mvt->refills, "ABQ refills", (void *)mvt);
  METER_INIT(mvt->refillPushes, "ABQ refill pushes", (void *)mvt);
  METER_INIT(mvt->returns, "ABQ returns", (void *)mvt);
  METER_INIT(mvt->perfectFits, "perfect fits", (void *)mvt);
  METER_INIT(mvt->firstFits, "first fits", (void *)mvt);
  METER_INIT(mvt->secondFits, "second fits", (void *)mvt);
  METER_INIT(mvt->failures, "failures", (void *)mvt);
  METER_INIT(mvt->emergencyContingencies, "emergency contingencies",
             (void *)mvt);
  METER_INIT(mvt->fragLimitContingencies,
             "fragmentation limit contingencies", (void *)mvt);
  METER_INIT(mvt->contingencySearches, "contingency searches", (void *)mvt);
  METER_INIT(mvt->contingencyHardSearches,
             "contingency hard searches", (void *)mvt);
  METER_INIT(mvt->splinters, "splinters", (void *)mvt);
  METER_INIT(mvt->splintersUsed, "splinters used", (void *)mvt);
  METER_INIT(mvt->splintersDropped, "splinters dropped", (void *)mvt);
  METER_INIT(mvt->sawdust, "sawdust", (void *)mvt);
  METER_INIT(mvt->exceptions, "exceptions", (void *)mvt);
  METER_INIT(mvt->exceptionSplinters, "exception splinters", (void *)mvt);
  METER_INIT(mvt->exceptionReturns, "exception returns", (void *)mvt);

  SetClassOfPoly(pool, CLASS(MVTPool));
  mvt->sig = MVTSig;
  AVERC(MVT, mvt);
  
  EVENT6(PoolInitMVT, pool, minSize, meanSize, maxSize,
               reserveDepth, fragLimit);

  return ResOK;

failABQInit:
  LandFinish(MVTFreeLand(mvt));
failFreeLandInit:
  LandFinish(MVTFreeSecondary(mvt));
failFreeSecondaryInit:
  LandFinish(MVTFreePrimary(mvt));
failFreePrimaryInit:
  NextMethod(Inst, MVTPool, finish)(MustBeA(Inst, pool));
failNextInit:
  AVER(res != ResOK);
  return res;
}