1
Fork 0
mirror of git://git.sv.gnu.org/emacs.git synced 2026-04-27 08:43:40 -07:00

Merge changes from mmdevel_gens3

Copied from Perforce
 Change: 18374
 ServerID: perforce.ravenbrook.com
This commit is contained in:
Nick Barnes 1997-06-20 16:12:58 +01:00
parent 6aa3dffe04
commit c93ef229cf
15 changed files with 462 additions and 191 deletions

View file

@ -1,12 +1,13 @@
/* impl.c.action: STRATEGIC ACTION
*
* Copyright (C) 1997 Harlequin Group, all rights reserved.
* $HopeName: MMsrc!action.c(MMdevel_action2.3) $
* $HopeName: MMsrc!action.c(trunk.2) $
*/
#include "mpm.h"
#include <float.h> /* @@@@ for DBL_MAX */
SRCID(action, "$HopeName: MMsrc!action.c(MMdevel_action2.3) $");
SRCID(action, "$HopeName: MMsrc!action.c(trunk.2) $");
/* ActionCheck -- check consistency of an Action structure */
@ -57,44 +58,18 @@ void ActionFinish(Action action)
/* Noddy collection policy -- condemn first pool found */
static Res ActionCollect(Space space)
static Res ActionCollect(Action action)
{
Ring ring, node;
Trace trace;
Res res;
Pool pool;
Space space;
ring = SpacePoolRing(space);
node = RingNext(ring);
while(node != ring) {
Ring next = RingNext(node);
space = PoolSpace(action->pool);
pool = RING_ELT(Pool, spaceRing, node);
if((pool->class->attr & AttrGC) != 0)
goto found;
node = next;
}
/* No GC-able pool found. */
return ResOK;
found:
res = TraceCreate(&trace, space);
if(res != ResOK) goto failTraceCreate;
res = TraceStart(trace, pool);
if(res != ResOK) goto failStart;
res = TraceCreate(&trace, space, action);
if(res != ResOK) return res;
return ResOK;
failStart:
/* .improve.undo-condemn: This is unsatisfactory as pools which
* successfully completed a condemn aren't given a chance to
* release any resources they may have allocated. */
TraceDestroy(trace);
failTraceCreate:
return res;
}
@ -103,15 +78,39 @@ failTraceCreate:
* This is the brain of the system. The function weighs up the
* costs and benefits of the various actions exhibited by the pools,
* and takes those which are worthwhile.
*
* @@@@ At the moment, it just launches a collection whenever it
* can.
*/
void ActionPoll(Space space)
{
Ring poolNode;
double bestBenefit;
Action bestAction;
AVERT(Space, space);
bestBenefit = -DBL_MAX;
bestAction = NULL;
if(space->busyTraces == TraceSetEMPTY)
(void)ActionCollect(space);
RING_FOR(poolNode, &space->poolRing) {
Pool pool = RING_ELT(Pool, spaceRing, poolNode);
Ring actionNode;
RING_FOR(actionNode, &pool->actionRing) {
Action action = RING_ELT(Action, poolRing, actionNode);
double benefit;
AVERT(Action, action);
benefit = PoolBenefit(action->pool, action);
if(benefit >= bestBenefit) {
bestBenefit = benefit;
bestAction = action;
}
}
}
/* @@@@ ignores failure */
if(bestBenefit > 0) {
AVER(bestAction != NULL);
(void)ActionCollect(bestAction);
}
}

View file

@ -1,6 +1,6 @@
/* impl.c.amcss: POOL CLASS AMC STRESS TEST
*
* $HopeName: MMsrc!amcss.c(trunk.13) $
* $HopeName: MMsrc!amcss.c(trunk.14) $
* Copyright (C) 1996 Harlequin Group, all rights reserved
*/
@ -21,7 +21,7 @@
#define NR_EXACT_ROOTS 50
#define NR_AMBIG_ROOTS 50
#define FIELDS_MAX 2000
#define OBJECTS 40000
#define COLLECTIONS 10
#define OBJNULL ((mps_addr_t)0xDECEA5ED)
static mps_pool_t pool;
@ -80,7 +80,7 @@ static void *test(void *arg, size_t s)
collections = 0;
for(i=0; i<OBJECTS; ++i) {
while(collections < COLLECTIONS) {
unsigned c;
size_t r;

View file

@ -1,6 +1,6 @@
# ==== SECOND COMMON FRAGMENT FOR PLATFORMS USING MV AND NMAKE
#
# $HopeName: MMsrc!commpost.nmk(trunk.3) $
# $HopeName: MMsrc!commpost.nmk(trunk.4) $
# Copyright(C) 1997 Harlequin Group, all rights reserved
#
# DESCRIPTION
@ -15,14 +15,14 @@
all: mpmss.exe amcss.exe dwstress.exe lockutnt.exe lockcov.exe \
mpsicv.exe poolncv.exe locv.exe qs.exe mpm.lib weakcv.exe \
mpmconft.exe finalcv.exe
mpmconft.exe finalcv.exe awlut.exe
# Convenience targets
# %%TARGET: Add a pseudo-target for the new part
dwstress.exe amcss.exe lockutnt.exe lockcov.exe \
mpmss.exe protcv.exe mpsicv.exe poolncv.exe locv.exe qs.exe \
weakcv.exe mpmconft.exe finalcv.exe \
weakcv.exe mpmconft.exe finalcv.exe awlut.exe \
mpm.lib mmdw.lib mmsw.lib poolawl.lib:
!IFDEF VARIETY
$(MAKE) /nologo /f $(PFM).nmk TARGET=$@ variety
@ -113,6 +113,10 @@ $(PFM)\$(VARIETY)\poolncv.exe: $(PFM)\$(VARIETY)\poolncv.obj \
$(PFM)\$(VARIETY)\locv.exe: $(PFM)\$(VARIETY)\locv.obj \
$(MPMOBJ) $(PLINTHOBJ) $(TESTLIBOBJ) $(LOOBJ)
$(PFM)\$(VARIETY)\awlut.exe: $(PFM)\$(VARIETY)\awlut.obj \
$(PFM)/$(VARIETY)/fmtdy.obj \
$(MPMOBJ) $(PLINTHOBJ) $(TESTLIBOBJ) $(LOOBJ) $(AWLOBJ)
$(PFM)\$(VARIETY)\mpm.lib: $(MPMOBJ)
$(ECHO) $@
$(LIBMAN) $(LIBFLAGS) /OUT:$@ $**

View file

@ -1,7 +1,7 @@
/* impl.h.config: MPS CONFIGURATION
*
* Copyright (C) 1997 Harlequin Group, all rights reserved.
* $HopeName: MMsrc!config.h(trunk.8) $
* $HopeName: MMsrc!config.h(trunk.9) $
*/
#ifndef config_h
@ -79,12 +79,15 @@
#elif defined(CONFIG_PROD_DYLAN)
#define MPS_PROD_DYLAN
#define ARENA_SIZE ((Size)1<<30)
#define AMC_SIZE_LIMIT ((Size)64<<20) /* experimentally reasonable limit */
#elif defined(CONFIG_PROD_MPS)
#define MPS_PROD_MPS
#ifdef MPS_OS_S7
#define ARENA_SIZE ((Size)2<<20)
#define AMC_SIZE_LIMIT ARENA_SIZE
#else
#define ARENA_SIZE ((Size)64<<20)
#define AMC_SIZE_LIMIT ARENA_SIZE
#endif /* MPS_OS_S7 */
#else
#error "No target product configured."

View file

@ -1,6 +1,6 @@
/* impl.h.mpm: MEMORY POOL MANAGER DEFINITIONS
*
* $HopeName: MMsrc!mpm.h(trunk.30) $
* $HopeName: MMsrc!mpm.h(trunk.31) $
* Copyright (C) 1997 The Harlequin Group Limited. All rights reserved.
*/
@ -261,13 +261,16 @@ extern Res PoolCreateV(Pool *poolReturn, Space space,
extern void PoolDestroy(Pool pool);
extern Res PoolAlloc(Addr *pReturn, Pool pool, Size size);
extern void PoolFree(Pool pool, Addr old, Size size);
extern Res PoolCondemn(Pool pool, Trace trace, Seg seg);
extern Res PoolTraceBegin(Pool pool, Trace trace, Action action);
extern Res PoolCondemn(Pool pool, Trace trace, Seg seg, Action action);
extern void PoolGrey(Pool pool, Trace trace, Seg seg);
extern Res PoolScan(ScanState ss, Pool pool, Seg seg);
extern Res (PoolFix)(Pool pool, ScanState ss, Seg seg, Addr *refIO);
#define PoolFix(pool, ss, seg, refIO) \
((*(pool)->class->fix)(pool, ss, seg, refIO))
extern void PoolReclaim(Pool pool, Trace trace, Seg seg);
extern void PoolTraceEnd(Pool pool, Trace trace, Action action);
extern double PoolBenefit(Pool pool, Action action);
extern void PoolTrivFinish(Pool pool);
extern Res PoolNoAlloc(Addr *pReturn, Pool pool, Size size);
@ -286,12 +289,17 @@ extern void PoolNoBufferEmpty(Pool pool, Buffer buffer);
extern void PoolTrivBufferEmpty(Pool pool, Buffer buffer);
extern Res PoolNoDescribe(Pool pool, mps_lib_FILE *stream);
extern Res PoolTrivDescribe(Pool pool, mps_lib_FILE *stream);
extern Res PoolNoCondemn(Pool pool, Trace trace, Seg seg);
extern Res PoolNoTraceBegin(Pool pool, Trace trace, Action action);
extern Res PoolTrivTraceBegin(Pool pool, Trace trace, Action action);
extern Res PoolNoCondemn(Pool pool, Trace trace, Seg seg, Action action);
extern void PoolNoGrey(Pool pool, Trace trace, Seg seg);
extern void PoolTrivGrey(Pool pool, Trace trace, Seg seg);
extern Res PoolNoScan(ScanState ss, Pool pool, Seg seg);
extern Res PoolNoFix(Pool pool, ScanState ss, Seg seg, Ref *refIO);
extern void PoolNoReclaim(Pool pool, Trace trace, Seg seg);
extern void PoolNoTraceEnd(Pool pool, Trace trace, Action action);
extern void PoolTrivTraceEnd(Pool pool, Trace trace, Action action);
extern double PoolNoBenefit(Pool pool, Action action);
/* Trace Interface -- see impl.c.trace */
@ -315,15 +323,15 @@ extern Bool TraceIdCheck(TraceId id);
extern Bool TraceSetCheck(TraceSet ts);
extern Bool TraceCheck(Trace trace);
extern Res TraceCreate(Trace *traceReturn, Space space);
extern Res TraceCreate(Trace *traceReturn, Space space, Action action);
extern void TraceDestroy(Trace trace);
extern Res TraceStart(Trace trace, Pool pool);
extern Res TracePoll(Trace trace);
extern void TraceAccess(Space space, Seg seg, AccessSet mode);
extern Res TraceFix(ScanState ss, Ref *refIO);
extern void TraceSegGreyen(Space space, Seg seg, TraceSet ts);
extern void TraceSetSummary(Space space, Seg seg, RefSet summary);
extern Size TraceGreyEstimate(Space space, RefSet refSet);
/* Equivalent to impl.h.mps MPS_SCAN_BEGIN */

View file

@ -1,6 +1,6 @@
/* impl.h.mpmst: MEMORY POOL MANAGER DATA STRUCTURES
*
* $HopeName: MMsrc!mpmst.h(trunk.24) $
* $HopeName: MMsrc!mpmst.h(trunk.25) $
* Copyright (C) 1997 The Harlequin Group Limited. All rights reserved.
*
* .readership: MM developers.
@ -92,11 +92,14 @@ typedef struct PoolClassStruct {
PoolBufferFillMethod bufferFill;
PoolBufferEmptyMethod bufferEmpty;
PoolBufferFinishMethod bufferFinish;
PoolTraceBeginMethod traceBegin;
PoolCondemnMethod condemn; /* condemn (some or all) objects */
PoolGreyMethod grey; /* grey non-white objects */
PoolScanMethod scan; /* find references during tracing */
PoolFixMethod fix; /* referent reachable during tracing */
PoolReclaimMethod reclaim; /* reclaim dead objects after tracing */
PoolTraceEndMethod traceEnd;
PoolBenefitMethod benefit;
PoolDescribeMethod describe; /* describe the contents of the pool */
Sig endSig; /* .class.end-sig */
} PoolClassStruct;
@ -577,6 +580,7 @@ typedef struct TraceStruct {
Sig sig; /* design.mps.sig */
TraceId ti; /* index into TraceSets */
Space space; /* owning space */
Action action; /* the action that launched the trace */
RefSet white; /* superset of refs in white set */
TraceState state; /* current state of trace */
Size interval; /* polling interval */
@ -621,6 +625,7 @@ typedef struct SpaceStruct {
Size pollThreshold; /* see impl.c.mpsi.poll and SpacePoll */
Bool insidePoll; /* prevent recursive polling, see SpacePoll */
Size actionInterval; /* see SpacePoll */
double allocTime; /* "time" in allocated bytes */
/* arena fields (impl.c.arena*) */
ArenaStruct arenaStruct; /* the arena */

View file

@ -1,6 +1,6 @@
/* impl.h.mpmtypes: MEMORY POOL MANAGER TYPES
*
* $HopeName: MMsrc!mpmtypes.h(trunk.23) $
* $HopeName: MMsrc!mpmtypes.h(trunk.24) $
* Copyright (C) 1997 The Harlequin Group Limited. All rights reserved.
*
* .readership: MM developers.
@ -76,30 +76,29 @@ typedef struct ActionStruct *Action; /* design.mps.action */
/* Pool*Method -- see design.mps.class-interface */
typedef Res (*PoolInitMethod) (Pool pool, va_list arg);
typedef void (*PoolFinishMethod) (Pool pool);
typedef Res (*PoolAllocMethod) (Addr *pReturn, Pool pool,
Size size);
typedef void (*PoolFreeMethod) (Pool pool, Addr old, Size size);
typedef Res (*PoolBufferInitMethod) (Pool pool, Buffer buf);
typedef void (*PoolBufferFinishMethod) (Pool pool, Buffer buf);
typedef Res (*PoolBufferFillMethod) (Seg *segReturn,
Addr *baseReturn, Addr *limitReturn,
Pool pool, Buffer buffer, Size size);
typedef void (*PoolBufferEmptyMethod) (Pool pool, Buffer buffer);
typedef Res (*PoolDescribeMethod) (Pool pool, mps_lib_FILE
*stream);
typedef Res (*PoolCondemnMethod) (Pool pool, Trace trace,
Seg seg);
typedef void (*PoolGreyMethod) (Pool pool, Trace trace,
Seg seg);
typedef Res (*PoolScanMethod) (ScanState ss, Pool pool,
Seg seg);
typedef Res (*PoolFixMethod) (Pool pool, ScanState ss,
Seg seg,
Ref *refIO);
typedef void (*PoolReclaimMethod) (Pool pool, Trace trace,
Seg seg);
typedef Res (*PoolInitMethod)(Pool pool, va_list arg);
typedef void (*PoolFinishMethod)(Pool pool);
typedef Res (*PoolAllocMethod)(Addr *pReturn, Pool pool, Size size);
typedef void (*PoolFreeMethod)(Pool pool, Addr old, Size size);
typedef Res (*PoolBufferInitMethod)(Pool pool, Buffer buf);
typedef void (*PoolBufferFinishMethod)(Pool pool, Buffer buf);
typedef Res (*PoolBufferFillMethod)(Seg *segReturn,
Addr *baseReturn, Addr *limitReturn,
Pool pool, Buffer buffer, Size size);
typedef void (*PoolBufferEmptyMethod)(Pool pool, Buffer buffer);
typedef Res (*PoolDescribeMethod)(Pool pool, mps_lib_FILE *stream);
typedef Res (*PoolTraceBeginMethod)(Pool pool, Trace trace,
Action action);
typedef Res (*PoolCondemnMethod)(Pool pool, Trace trace,
Seg seg, Action action);
typedef void (*PoolGreyMethod)(Pool pool, Trace trace, Seg seg);
typedef Res (*PoolScanMethod)(ScanState ss, Pool pool, Seg seg);
typedef Res (*PoolFixMethod)(Pool pool, ScanState ss, Seg seg,
Ref *refIO);
typedef void (*PoolReclaimMethod)(Pool pool, Trace trace, Seg seg);
typedef void (*PoolTraceEndMethod)(Pool pool, Trace trace,
Action action);
typedef double (*PoolBenefitMethod)(Pool pool, Action action);
/* Format*Method -- see design.mps.format-interface */
@ -247,20 +246,51 @@ typedef int WriteFC; /* Promoted */
*/
/* EVent ... */
#define EventEventTime ((EventType)0xEF213E99) /* TIME */
#define EventSpaceCreate ((EventType)0xEF5BCC6E) /* SPaCe CREate */
#define EventSpaceDestroy ((EventType)0xEF5BCDE5) /* SPaCe DEStroy */
#define EventPoolInit ((EventType)0xEFB07141) /* POoL INIt */
#define EventPoolFinish ((EventType)0xEFB07F14) /* POoL FINish */
#define EventPoolAlloc ((EventType)0xEFB07A77) /* POoL ALLoc */
#define EventPoolFree ((EventType)0xEFB07F6E) /* POoL FREe */
#define EventArenaCreate ((EventType)0xEFA64C6E) /* AReNa CREate */
#define EventArenaDestroy ((EventType)0xEFA64DE5) /* AReNa DEStroy */
#define EventSegAlloc ((EventType)0xEF5E9A77) /* SEG ALLoc */
#define EventSegFree ((EventType)0xEF5E9F6E) /* SEG FREe */
#define EventVMCreate ((EventType)0xEFF3C6EA) /* VM CREAte */
#define EventVMDestroy ((EventType)0xEFF3DE52) /* VM DESTroy */
#define EventVMMap ((EventType)0xEFF33AB9) /* VM MAP */
#define EventVMUnmap ((EventType)0xEFF3043B) /* VM UNMaP */
#define EventEventTime ((EventType)0xEF213E99) /* TIME */
#define EventSpaceCreate ((EventType)0xEF5BCC6E) /* SPaCe CREate */
#define EventSpaceDestroy ((EventType)0xEF5BCDE5) /* SPaCe DEStroy */
#define EventPoolInit ((EventType)0xEFB07141) /* POoL INIt */
#define EventPoolFinish ((EventType)0xEFB07F14) /* POoL FINish */
#define EventPoolAlloc ((EventType)0xEFB07A77) /* POoL ALLoc */
#define EventPoolFree ((EventType)0xEFB07F6E) /* POoL FREe */
#define EventArenaCreate ((EventType)0xEFA64C6E) /* AReNa CREate */
#define EventArenaDestroy ((EventType)0xEFA64DE5) /* AReNa DEStroy */
#define EventSegAlloc ((EventType)0xEF5E9A77) /* SEG ALLoc */
#define EventSegFree ((EventType)0xEF5E9F6E) /* SEG FREe */
#define EventAMCGenCreate ((EventType)0xEFA3C94C) /* AMC GeN Create */
#define EventAMCGenDestroy ((EventType)0xEFA3C94D) /* AMC GeN Destroy */
#define EventAMCInit ((EventType)0xEFA3C141) /* AMC INIt */
#define EventAMCFinish ((EventType)0xEFA3CF14) /* AMC FINish */
#define EventAMCBufferInit ((EventType)0xEFA3CBF1) /* AMC BuFfer Init */
#define EventAMCBufferFill ((EventType)0xEFA3CBFF) /* AMC BuFfer Fill */
#define EventAMCBufferEmpty ((EventType)0xEFA3CBFE) /* AMC BuFfer Empty */
#define EventAMCTraceBegin ((EventType)0xEFA3C26B) /* AMC TRace Begin */
#define EventAMCCondemn ((EventType)0xEFA3CC04) /* AMC CONdemn */
#define EventAMCScanBegin ((EventType)0xEFA3C5CB) /* AMC SCan Begin */
#define EventAMCScanEnd ((EventType)0xEFA3C5CE) /* AMC SCan End */
#define EventAMCFix ((EventType)0xEFA3CF18) /* AMC FIX */
#define EventAMCFixAmbig ((EventType)0xEFA3CF8A) /* AMC FiX Ambig */
#define EventAMCFixForward ((EventType)0xEFA3CF8F) /* AMC FiX Forward */
#define EventAMCReclaim ((EventType)0xEFA3C6EC) /* AMC REClaim */
#define EventAMCTraceEnd ((EventType)0xEFA3C26E) /* AMC TRace End */
#define EventTraceStart ((EventType)0xEF26AC52) /* TRACe STart */
#define EventTraceCreate ((EventType)0xEF26ACC6) /* TRACe CReate */
#define EventTraceDestroy ((EventType)0xEF26ACDE) /* TRACe DEstroy */
#define EventTraceSegGreyen ((EventType)0xEF26A599) /* TRAce SeG Greyen */
#define EventTraceFlipBegin ((EventType)0xEF26AF7B) /* TRAce FLip Begin */
#define EventTraceFlipEnd ((EventType)0xEF26AF7E) /* TRAce FLip End */
#define EventTraceReclaim ((EventType)0xEF26A6EC) /* TRAce REClaim */
#define EventTraceScan ((EventType)0xEF26AC5C) /* TRACe SCan */
#define EventTraceAccess ((EventType)0xEF26AACC) /* TRAce ACCess */
#define EventTracePoll ((EventType)0xEF26AB01) /* TRAce POLl */
#define EventTraceFix ((EventType)0xEF26AF18) /* TRAce FIX */
#define EventTraceFixSeg ((EventType)0xEF26AF85) /* TRAce FiX Seg */
#define EventTraceFixWhite ((EventType)0xEF26AF83) /* TRAce FiX White */
#define EventTraceScanArea ((EventType)0xEF26A5CA) /* TRAce SCan Area */
#define EventTraceScanAreaTagged ((EventType)0xEF26A5C2) /* TRAce SCan area Tagged */
#define EventVMCreate ((EventType)0xEFF3C6EA) /* VM CREAte */
#define EventVMDestroy ((EventType)0xEFF3DE52) /* VM DESTroy */
#define EventVMMap ((EventType)0xEFF33AB9) /* VM MAP */
#define EventVMUnmap ((EventType)0xEFF3043B) /* VM UNMaP */
#endif /* mpmtypes_h */

View file

@ -1,6 +1,6 @@
/* impl.c.pool: POOL IMPLEMENTATION
*
* $HopeName: MMsrc!pool.c(trunk.28) $
* $HopeName: MMsrc!pool.c(trunk.29) $
* Copyright (C) 1997 The Harlequin Group Limited. All rights reserved.
*
* This is the implementation of the generic pool interface. The
@ -12,7 +12,7 @@
#include "mpm.h"
SRCID(pool, "$HopeName: MMsrc!pool.c(trunk.28) $");
SRCID(pool, "$HopeName: MMsrc!pool.c(trunk.29) $");
Bool PoolClassCheck(PoolClass class)
@ -32,11 +32,14 @@ Bool PoolClassCheck(PoolClass class)
CHECKL(FUNCHECK(class->bufferFill));
CHECKL(FUNCHECK(class->bufferEmpty));
CHECKL(FUNCHECK(class->bufferFinish));
CHECKL(FUNCHECK(class->traceBegin));
CHECKL(FUNCHECK(class->condemn));
CHECKL(FUNCHECK(class->grey));
CHECKL(FUNCHECK(class->scan));
CHECKL(FUNCHECK(class->fix));
CHECKL(FUNCHECK(class->reclaim));
CHECKL(FUNCHECK(class->traceEnd));
CHECKL(FUNCHECK(class->benefit));
CHECKL(FUNCHECK(class->describe));
CHECKL(class->endSig == PoolClassSig);
return TRUE;
@ -247,14 +250,26 @@ void PoolFree(Pool pool, Addr old, Size size)
EVENT3(PoolFree, (Word)pool, (Word)old, (Word)size);
}
Res PoolCondemn(Pool pool, Trace trace, Seg seg)
Res PoolTraceBegin(Pool pool, Trace trace, Action action)
{
AVERT(Pool, pool);
AVERT(Trace, trace);
AVERT(Action, action);
AVER(trace->action == action);
AVER(action->pool == pool);
AVER(pool->space == trace->space);
return (*pool->class->traceBegin)(pool, trace, action);
}
Res PoolCondemn(Pool pool, Trace trace, Seg seg, Action action)
{
AVERT(Pool, pool);
AVERT(Trace, trace);
AVERT(Seg, seg);
AVERT(Action, action);
AVER(pool->space == trace->space);
AVER(seg->pool == pool);
return (*pool->class->condemn)(pool, trace, seg);
return (*pool->class->condemn)(pool, trace, seg, action);
}
void PoolGrey(Pool pool, Trace trace, Seg seg)
@ -325,6 +340,26 @@ void PoolReclaim(Pool pool, Trace trace, Seg seg)
(*pool->class->reclaim)(pool, trace, seg);
}
void PoolTraceEnd(Pool pool, Trace trace, Action action)
{
AVERT(Pool, pool);
AVERT(Trace, trace);
AVERT(Action, action);
AVER(trace->action == action);
AVER(action->pool == pool);
AVER(pool->space == trace->space);
(*pool->class->traceEnd)(pool, trace, action);
}
double PoolBenefit(Pool pool, Action action)
{
AVERT(Pool, pool);
AVERT(Action, action);
AVER(action->pool == pool);
return (*pool->class->benefit)(pool, action);
}
Res PoolDescribe(Pool pool, mps_lib_FILE *stream)
{
@ -612,11 +647,35 @@ Res PoolTrivDescribe(Pool pool, mps_lib_FILE *stream)
return WriteF(stream, " No class-specific description available.\n", NULL);
}
Res PoolNoCondemn(Pool pool, Trace trace, Seg seg)
Res PoolNoTraceBegin(Pool pool, Trace trace, Action action)
{
AVERT(Pool, pool);
AVERT(Trace, trace);
AVERT(Action, action);
AVER(trace->action == action);
AVER(action->pool == pool);
AVER(pool->space == trace->space);
NOTREACHED;
return ResUNIMPL;
}
Res PoolTrivTraceBegin(Pool pool, Trace trace, Action action)
{
AVERT(Pool, pool);
AVERT(Trace, trace);
AVERT(Action, action);
AVER(trace->action == action);
AVER(action->pool == pool);
AVER(pool->space == trace->space);
return ResOK;
}
Res PoolNoCondemn(Pool pool, Trace trace, Seg seg, Action action)
{
AVERT(Pool, pool);
AVERT(Trace, trace);
AVERT(Seg, seg);
AVERT(Action, action);
NOTREACHED;
return ResUNIMPL;
}
@ -675,3 +734,33 @@ void PoolNoReclaim(Pool pool, Trace trace, Seg seg)
AVERT(Seg, seg);
NOTREACHED;
}
void PoolNoTraceEnd(Pool pool, Trace trace, Action action)
{
AVERT(Pool, pool);
AVERT(Trace, trace);
AVERT(Action, action);
AVER(trace->action == action);
AVER(action->pool == pool);
AVER(pool->space == trace->space);
NOTREACHED;
}
void PoolTrivTraceEnd(Pool pool, Trace trace, Action action)
{
AVERT(Pool, pool);
AVERT(Trace, trace);
AVERT(Action, action);
AVER(trace->action == action);
AVER(action->pool == pool);
AVER(pool->space == trace->space);
}
double PoolNoBenefit(Pool pool, Action action)
{
AVERT(Pool, pool);
AVERT(Action, action);
AVER(action->pool == pool);
NOTREACHED;
return (double)0;
}

View file

@ -1,6 +1,6 @@
/* impl.c.poolawl: AUTOMATIC WEAK LINKED POOL CLASS
*
* $HopeName: MMsrc!poolawl.c(trunk.3) $
* $HopeName: MMsrc!poolawl.c(trunk.4) $
* Copyright (C) 1997 The Harlequin Group Limited. All rights reserved.
*
* READERSHIP
@ -16,7 +16,7 @@
#include "mpm.h"
#include "mpscawl.h"
SRCID(poolawl, "$HopeName: MMsrc!poolawl.c(trunk.3) $");
SRCID(poolawl, "$HopeName: MMsrc!poolawl.c(trunk.4) $");
#define AWLSig ((Sig)0x519b7a37) /* SIGPooLAWL */
@ -26,6 +26,8 @@ typedef struct AWLStruct {
PoolStruct poolStruct;
Format format;
Shift alignShift;
ActionStruct actionStruct;
double lastCollected;
Sig sig;
} AWLStruct, *AWL;
@ -50,6 +52,8 @@ static Bool AWLGroupCheck(AWLGroup group);
#define PoolPoolAWL(pool) \
PARENT(AWLStruct, poolStruct, (pool))
#define ActionAWL(action) PARENT(AWLStruct, actionStruct, action)
static void AWLGroupDestroy(AWLGroup group)
{
@ -192,6 +196,8 @@ static Res AWLInit(Pool pool, va_list arg)
AVERT(Format, format);
awl->format = format;
awl->alignShift = SizeLog2(pool->alignment);
ActionInit(&awl->actionStruct, pool);
awl->lastCollected = PoolSpace(pool)->allocTime;
awl->sig = AWLSig;
AVERT(AWL, awl);
@ -223,6 +229,7 @@ static void AWLFinish(Pool pool)
AWLGroupDestroy(group);
node = next;
}
ActionFinish(&awl->actionStruct);
}
@ -307,7 +314,7 @@ static void AWLBufferEmpty(Pool pool, Buffer buffer)
}
static Res AWLCondemn(Pool pool, Trace trace, Seg seg)
static Res AWLCondemn(Pool pool, Trace trace, Seg seg, Action action)
{
Count bits;
AWL awl;
@ -322,13 +329,16 @@ static Res AWLCondemn(Pool pool, Trace trace, Seg seg)
awl = PoolPoolAWL(pool);
AVERT(AWL, awl);
AVERT(Action, action);
AVER(awl == ActionAWL(action));
group = (AWLGroup)seg->p;
AVERT(AWLGroup, group);
bits = SegSize(PoolSpace(pool), seg) >> awl->alignShift;
BTResRange(group->mark, 0, bits);
seg->white = TraceSetAdd(seg->white, trace->ti);
return ResOK;
}
@ -566,6 +576,40 @@ static void AWLReclaim(Pool pool, Trace trace, Seg seg)
BTResRange(group->mark, 0, bits);
}
static Res AWLTraceBegin(Pool pool, Trace trace, Action action)
{
AWL awl;
AVERT(Pool, pool);
awl = PoolPoolAWL(pool);
AVERT(AWL, awl);
AVERT(Trace, trace);
AVERT(Action, action);
AVER(awl == ActionAWL(action));
awl->lastCollected = PoolSpace(pool)->allocTime;
return ResOK;
}
/* @@@@ completely made-up benefit calculation: each AWL pool gradually
* becomes a better candidate for collection as allocation goes
* by. Starting a trace on a pool makes it a bad candidate. nickb
* 1997-06-19 */
static double AWLBenefit(Pool pool, Action action)
{
AWL awl;
AVERT(Pool, pool);
awl = PoolPoolAWL(pool);
AVERT(AWL, awl);
AVERT(Action, action);
AVER(awl == ActionAWL(action));
return (PoolSpace(pool)->allocTime - awl->lastCollected) - 10*1024*1024.0;
}
struct PoolClassStruct PoolClassAWLStruct = {
PoolClassSig,
"AWL",
@ -580,11 +624,14 @@ struct PoolClassStruct PoolClassAWLStruct = {
AWLBufferFill,
AWLBufferEmpty,
PoolTrivBufferFinish,
AWLTraceBegin,
AWLCondemn,
AWLGrey,
AWLScan,
AWLFix,
AWLReclaim,
PoolTrivTraceEnd,
AWLBenefit,
PoolTrivDescribe,
PoolClassSig
};
@ -602,6 +649,8 @@ static Bool AWLCheck(AWL awl)
CHECKD(Pool, &awl->poolStruct);
CHECKL(awl->poolStruct.class == &PoolClassAWLStruct);
CHECKL(1uL << awl->alignShift == awl->poolStruct.alignment);
CHECKD(Action, &awl->actionStruct);
CHECKL(awl->poolStruct.space->allocTime >= awl->lastCollected);
return TRUE;
}

View file

@ -1,6 +1,6 @@
/* impl.c.poolmfs: MANUAL FIXED SMALL UNIT POOL
*
* $HopeName: MMsrc!poolmfs.c(MMdevel_bufferscan.2) $
* $HopeName: MMsrc!poolmfs.c(trunk.18) $
* Copyright (C) 1997 The Harlequin Group Limited. All rights reserved.
*
* This is the implementation of the MFS pool class.
@ -35,7 +35,7 @@
#include "mpm.h"
#include "poolmfs.h"
SRCID(poolmfs, "$HopeName: MMsrc!poolmfs.c(MMdevel_bufferscan.2) $");
SRCID(poolmfs, "$HopeName: MMsrc!poolmfs.c(trunk.18) $");
/* == Round up ==
@ -275,11 +275,14 @@ static PoolClassStruct PoolClassMFSStruct = {
PoolNoBufferFill, /* bufferFill */
PoolNoBufferEmpty, /* bufferEmpty */
PoolNoBufferFinish, /* bufferFinish */
PoolNoTraceBegin, /* traceBegin */
PoolNoCondemn, /* condemn */
PoolNoGrey, /* grey */
PoolNoScan, /* scan */
PoolNoFix, /* fix */
PoolNoReclaim, /* reclaim */
PoolNoTraceEnd, /* traceEnd */
PoolNoBenefit, /* benefit */
MFSDescribe, /* describe */
PoolClassSig /* impl.h.mpmst.class.end-sig */
};

View file

@ -2,7 +2,7 @@
*
* MANUAL RANK GUARDIAN POOL
*
* $HopeName: MMsrc!poolmrg.c(MMdevel_bufferscan.2) $
* $HopeName: MMsrc!poolmrg.c(trunk.9) $
* Copyright (C) 1997 The Harlequin Group Limited. All rights reserved.
*
* READERSHIP
@ -28,7 +28,7 @@
#include "mpm.h"
#include "poolmrg.h"
SRCID(poolmrg, "$HopeName: MMsrc!poolmrg.c(MMdevel_bufferscan.2) $");
SRCID(poolmrg, "$HopeName: MMsrc!poolmrg.c(trunk.9) $");
#define MRGSig ((Sig)0x519369B0) /* SIGnature MRG POol */
@ -415,11 +415,14 @@ static PoolClassStruct PoolClassMRGStruct = {
PoolNoBufferFill, /* bufferFill */
PoolNoBufferEmpty, /* bufferEmpty */
PoolNoBufferFinish, /* bufferFinish */
PoolNoTraceBegin, /* traceBegin */
PoolNoCondemn, /* condemn */
PoolTrivGrey, /* grey */
MRGScan, /* scan */
PoolNoFix, /* fix */
PoolNoReclaim, /* reclaim */
PoolNoTraceEnd, /* traceEnd */
PoolNoBenefit, /* benefit */
MRGDescribe, /* describe */
PoolClassSig /* impl.h.mpmst.class.end-sig */
};

View file

@ -1,6 +1,6 @@
/* impl.c.poolmv: MANUAL VARIABLE POOL
*
* $HopeName: MMsrc!poolmv.c(MMdevel_bufferscan.2) $
* $HopeName: MMsrc!poolmv.c(trunk.20) $
* Copyright (C) 1997 The Harlequin Group Limited. All rights reserved.
*
* **** RESTRICTION: This pool may not allocate from the arena control
@ -37,7 +37,7 @@
#include "poolmfs.h"
#include "mpscmv.h"
SRCID(poolmv, "$HopeName: MMsrc!poolmv.c(trunk.19) $");
SRCID(poolmv, "$HopeName: MMsrc!poolmv.c(trunk.20) $");
#define BLOCKPOOL(mv) (MFSPool(&(mv)->blockPoolStruct))
@ -619,11 +619,14 @@ static PoolClassStruct PoolClassMVStruct = {
PoolTrivBufferFill, /* bufferFill */
PoolTrivBufferEmpty, /* bufferEmpty */
PoolTrivBufferFinish, /* bufferFinish */
PoolNoTraceBegin, /* traceBegin */
PoolNoCondemn, /* condemn */
PoolNoGrey, /* mark */
PoolNoScan, /* scan */
PoolNoFix, /* fix */
PoolNoReclaim, /* relcaim */
PoolNoTraceEnd, /* traceEnd */
PoolNoBenefit, /* benefit */
MVDescribe, /* describe */
PoolClassSig /* impl.h.mpmst.class.end-sig */
};

View file

@ -1,6 +1,6 @@
/* impl.c.pooln: NULL POOL
*
* $HopeName: MMsrc!pooln.c(MMdevel_bufferscan.2) $
* $HopeName: MMsrc!pooln.c(trunk.12) $
* Copyright(C) 1997 The Harlequin Group Limited. All rights reserved.
*
* This is the implementation of the null pool class. Begin null it
@ -10,7 +10,7 @@
#include "mpm.h"
#include "pooln.h"
SRCID(pooln, "$HopeName: MMsrc!pooln.c(MMdevel_bufferscan.2) $");
SRCID(pooln, "$HopeName: MMsrc!pooln.c(trunk.12) $");
typedef struct PoolNStruct {
@ -148,7 +148,7 @@ static Res NDescribe(Pool pool, mps_lib_FILE *stream)
return ResOK;
}
static Res NCondemn(Pool pool, Trace trace, Seg seg)
static Res NCondemn(Pool pool, Trace trace, Seg seg, Action action)
{
PoolN poolN;
@ -158,8 +158,11 @@ static Res NCondemn(Pool pool, Trace trace, Seg seg)
AVERT(Trace, trace);
AVERT(Seg, seg);
AVERT(Action, action);
NOTREACHED; /* pool doesn't have any actions */
return ResOK;
return ResUNIMPL;
}
static void NGrey(Pool pool, Trace trace, Seg seg)
@ -231,11 +234,14 @@ static PoolClassStruct PoolClassNStruct = {
NBufferFill, /* bufferFill */
NBufferEmpty, /* bufferEmpty */
NBufferFinish, /* bufferFinish */
PoolNoTraceBegin, /* traceBegin */
NCondemn, /* condemn */
NGrey, /* grey */
NScan, /* scan */
NFix, /* fix */
NReclaim, /* reclaim */
PoolNoTraceEnd, /* traceEnd */
PoolNoBenefit, /* benefit */
NDescribe, /* describe */
PoolClassSig /* impl.h.mpmst.class.end-sig */
};

View file

@ -1,12 +1,12 @@
/* impl.c.trace: GENERIC TRACER IMPLEMENTATION
*
* $HopeName: MMsrc!trace.c(trunk.25) $
* $HopeName: MMsrc!trace.c(trunk.26) $
* Copyright (C) 1997 The Harlequin Group Limited. All rights reserved.
*/
#include "mpm.h"
SRCID(trace, "$HopeName: MMsrc!trace.c(trunk.25) $");
SRCID(trace, "$HopeName: MMsrc!trace.c(trunk.26) $");
/* ScanStateCheck -- check consistency of a ScanState object */
@ -94,78 +94,6 @@ Bool TraceCheck(Trace trace)
}
/* TraceCreate -- create a Trace object
*
* Allocates and initializes a new Trace object with a TraceId
* which is not currently active.
*
* Returns ResLIMIT if there aren't any available trace IDs.
*
* Trace objects are allocated directly from a small array in the
* space structure which is indexed by the TraceId. This is so
* that it's always possible to start a trace (provided there's
* a free TraceId) even if there's no available memory.
*
* This code is written to be adaptable to allocating Trace
* objects dynamically.
*/
Res TraceCreate(Trace *traceReturn, Space space)
{
TraceId ti;
Trace trace;
AVER(TRACE_MAX == 1); /* .single-collection */
AVER(traceReturn != NULL);
AVERT(Space, space);
/* Find a free trace ID */
for(ti = 0; ti < TRACE_MAX; ++ti)
if(!TraceSetIsMember(space->busyTraces, ti))
goto found;
return ResLIMIT; /* no trace IDs available */
found:
trace = SpaceTrace(space, ti);
space->busyTraces = TraceSetAdd(space->busyTraces, ti);
trace->space = space;
trace->white = RefSetEMPTY;
trace->ti = ti;
trace->state = TraceINIT;
trace->interval = (Size)4096; /* @@@@ should be progress control */
trace->sig = TraceSig;
AVERT(Trace, trace);
*traceReturn = trace;
return ResOK;
}
/* TraceDestroy -- destroy a trace object
*
* Finish and deallocate a Trace object, freeing up a TraceId.
*
* This code does not allow a Trace to be destroyed while it is
* active. It would be possible to allow this, but the colours
* of segments etc. would need to be reset to black.
*/
void TraceDestroy(Trace trace)
{
AVERT(Trace, trace);
AVER(trace->state == TraceFINISHED);
trace->sig = SigInvalid;
trace->space->busyTraces =
TraceSetDel(trace->space->busyTraces, trace->ti);
trace->space->flippedTraces =
TraceSetDel(trace->space->flippedTraces, trace->ti);
}
/* TraceStart -- condemn a set of objects and start collection
*
* TraceStart should be passed a trace with state TraceINIT, i.e.
@ -177,21 +105,25 @@ void TraceDestroy(Trace trace)
* it easy to destroy traces half-way through.
*/
Res TraceStart(Trace trace, Pool pool)
static Res TraceStart(Trace trace, Action action)
{
Res res;
Ring ring, node;
Space space;
Seg seg;
Pool pool;
AVERT(Trace, trace);
AVERT(Pool, pool);
AVER((pool->class->attr & AttrGC) != 0);
AVERT(Action, action);
AVER((action->pool->class->attr & AttrGC) != 0);
AVER(trace->state == TraceINIT);
AVER(trace->white == RefSetEMPTY);
/* Identify the condemned set and turn it white. */
space = trace->space;
pool = action->pool;
EVENT3(TraceStart, trace, pool, action);
ring = PoolSegRing(pool);
node = RingNext(ring);
while(node != ring) {
@ -202,7 +134,7 @@ Res TraceStart(Trace trace, Pool pool)
/* Give the pool the opportunity to turn the segment white. */
/* If it fails, unwind. */
res = PoolCondemn(pool, trace, seg);
res = PoolCondemn(pool, trace, seg, action);
if(res != ResOK) goto failCondemn;
/* Add the segment to the approximation of the white set the */
@ -289,6 +221,99 @@ failCondemn:
}
/* TraceCreate -- create a Trace object
*
* Allocates and initializes a new Trace object with a TraceId
* which is not currently active.
*
* Returns ResLIMIT if there aren't any available trace IDs.
*
* Trace objects are allocated directly from a small array in the
* space structure which is indexed by the TraceId. This is so
* that it's always possible to start a trace (provided there's
* a free TraceId) even if there's no available memory.
*
* This code is written to be adaptable to allocating Trace
* objects dynamically.
*/
Res TraceCreate(Trace *traceReturn, Space space, Action action)
{
TraceId ti;
Trace trace;
Res res;
AVER(TRACE_MAX == 1); /* .single-collection */
AVER(traceReturn != NULL);
AVERT(Space, space);
AVERT(Action, action);
/* Find a free trace ID */
for(ti = 0; ti < TRACE_MAX; ++ti)
if(!TraceSetIsMember(space->busyTraces, ti))
goto found;
return ResLIMIT; /* no trace IDs available */
found:
trace = SpaceTrace(space, ti);
space->busyTraces = TraceSetAdd(space->busyTraces, ti);
trace->space = space;
trace->action = action;
trace->white = RefSetEMPTY;
trace->ti = ti;
trace->state = TraceINIT;
trace->interval = (Size)4096; /* @@@@ should be progress control */
trace->sig = TraceSig;
AVERT(Trace, trace);
res = PoolTraceBegin(action->pool, trace, action);
if(res != ResOK) goto failBegin;
res = TraceStart(trace, action);
if(res != ResOK) goto failStart;
*traceReturn = trace;
EVENT4(TraceCreate, space, action, trace, ti);
return ResOK;
failStart:
PoolTraceEnd(action->pool, trace, action);
failBegin:
trace->sig = SigInvalid;
space->busyTraces = TraceSetDel(space->busyTraces, ti);
return res;
}
/* TraceDestroy -- destroy a trace object
*
* Finish and deallocate a Trace object, freeing up a TraceId.
*
* This code does not allow a Trace to be destroyed while it is
* active. It would be possible to allow this, but the colours
* of segments etc. would need to be reset to black.
*/
void TraceDestroy(Trace trace)
{
AVERT(Trace, trace);
AVER(trace->state == TraceFINISHED);
PoolTraceEnd(trace->action->pool, trace, trace->action);
trace->sig = SigInvalid;
trace->space->busyTraces =
TraceSetDel(trace->space->busyTraces, trace->ti);
trace->space->flippedTraces =
TraceSetDel(trace->space->flippedTraces, trace->ti);
EVENT1(TraceDestroy, trace);
}
/* TraceSetGreyen -- turn a segment more grey
*
* Adds the trace set ts to the greyness of the segment and adjusts
@ -311,6 +336,7 @@ void TraceSegGreyen(Space space, Seg seg, TraceSet ts)
TraceSetInter(grey, space->flippedTraces) != TraceSetEMPTY)
ShieldRaise(space, seg, AccessREAD);
seg->grey = grey;
EVENT3(TraceSegGreyen, space, seg, ts);
}
@ -395,6 +421,8 @@ static Res TraceFlip(Trace trace)
AVER(trace->state == TraceUNFLIPPED);
EVENT2(TraceFlipBegin, trace, space);
TraceFlipBuffers(space);
/* Update location dependency structures. white is */
@ -453,6 +481,8 @@ static Res TraceFlip(Trace trace)
ss.sig = SigInvalid; /* just in case */
EVENT2(TraceFlipEnd, trace, space);
ShieldResume(space);
return ResOK;
@ -467,6 +497,8 @@ static void TraceReclaim(Trace trace)
AVERT(Trace, trace);
AVER(trace->state == TraceRECLAIM);
EVENT1(TraceReclaim, trace);
space = trace->space;
if(SegFirst(&seg, space)) {
Addr base;
@ -552,6 +584,8 @@ static Res TraceScan(TraceSet ts, Rank rank,
/* The reason for scanning a segment is that it's grey. */
AVER(TraceSetInter(ts, seg->grey) != TraceSetEMPTY);
EVENT5(TraceScan, ts, rank, space, seg, &ss);
ss.rank = rank;
ss.traces = ts;
ss.fix = TraceFix;
@ -608,6 +642,8 @@ void TraceAccess(Space space, Seg seg, AccessSet mode)
AVERT(Seg, seg);
UNUSED(mode);
EVENT3(TraceAccess, space, seg, mode);
if((mode & seg->sm & AccessREAD) != 0) { /* read barrier? */
/* In this case, the segment must be grey for a trace which is */
/* flipped. */
@ -675,6 +711,8 @@ Res TracePoll(Trace trace)
space = trace->space;
EVENT2(TracePoll, trace, space);
switch(trace->state) {
case TraceUNFLIPPED: {
res = TraceFlip(trace);
@ -704,6 +742,23 @@ Res TracePoll(Trace trace)
}
/* TraceGreyEstimate -- estimate amount of grey stuff
*
* This function returns an estimate of the total size (in bytes)
* of objects which would need to be scanned in order to find
* all references to a certain RefSet.
*
* @@@@ This currently assumes that it's everything in the world.
* @@@@ Should factor in the size of the roots, especially if the stack
* is currently very deep.
*/
Size TraceGreyEstimate(Space space, RefSet refSet)
{
return ArenaCommitted(space);
}
Res TraceFix(ScanState ss, Ref *refIO)
{
Ref ref;
@ -714,8 +769,11 @@ Res TraceFix(ScanState ss, Ref *refIO)
AVER(refIO != NULL);
ref = *refIO;
EVENT4(TraceFix, ss, refIO, ref, ss->rank);
if(SegOfAddr(&seg, ss->space, ref)) {
EVENT1(TraceFixSeg, seg);
if(TraceSetInter(seg->white, ss->traces) != TraceSetEMPTY) {
EVENT0(TraceFixWhite);
pool = seg->pool;
return PoolFix(pool, ss, seg, refIO);
}
@ -744,6 +802,8 @@ Res TraceScanArea(ScanState ss, Addr *base, Addr *limit)
AVER(limit != NULL);
AVER(base < limit);
EVENT3(TraceScanArea, ss, base, limit);
TRACE_SCAN_BEGIN(ss) {
p = base;
loop:
@ -790,6 +850,8 @@ Res TraceScanAreaMasked(ScanState ss, Addr *base, Addr *limit, Word mask)
AVER(limit != NULL);
AVER(base < limit);
EVENT3(TraceScanAreaTagged, ss, base, limit);
TRACE_SCAN_BEGIN(ss) {
p = base;
loop:

View file

@ -1,6 +1,6 @@
/* impl.c.vmnt: VIRTUAL MEMORY MAPPING FOR WIN32
*
* $HopeName: MMsrc!vmnt.c(trunk.15) $
* $HopeName: MMsrc!vmw3.c(trunk.17) $
* Copyright (C) 1995 Harlequin Group, all rights reserved
*
* Design: design.mps.vm
@ -55,7 +55,7 @@
#include <windows.h>
SRCID(vmnt, "$HopeName: MMsrc!vmnt.c(trunk.15) $");
SRCID(vmnt, "$HopeName: MMsrc!vmw3.c(trunk.17) $");
#define SpaceVM(space) (&(space)->arenaStruct.vmStruct)
@ -135,6 +135,8 @@ Res VMCreate(Space *spaceReturn, Size size, Addr base)
AVERT(VM, vm);
EVENT4(VMCreate, vm, space, vm->base, vm->limit);
*spaceReturn = space;
return ResOK;
}
@ -159,6 +161,7 @@ void VMDestroy(Space space)
b = VirtualFree((LPVOID)space, (DWORD)0, MEM_RELEASE);
AVER(b != 0);
EVENT1(VMDestroy, vm);
}
@ -219,6 +222,8 @@ Res VMMap(Space space, Addr base, Addr limit)
vm->mapped += AddrOffset(base, limit);
EVENT3(VMMap, vm, base, limit);
return ResOK;
}
@ -242,4 +247,6 @@ void VMUnmap(Space space, Addr base, Addr limit)
b = VirtualFree((LPVOID)base, (DWORD)AddrOffset(base, limit), MEM_DECOMMIT);
AVER(b != 0); /* .assume.free.success */
vm->mapped -= AddrOffset(base, limit);
EVENT3(VMUnmap, vm, base, limit);
}