diff --git a/mps/manual/wiki/apguide.html b/mps/manual/wiki/apguide.html new file mode 100644 index 00000000000..e83466cb940 --- /dev/null +++ b/mps/manual/wiki/apguide.html @@ -0,0 +1,1143 @@ + + + + +
+This wiki article contains incomplete and informal notes about the MPS, the precursor to more formal documentation. Not confidential. Readership: MPS users and developers.
+ +Notes on getting started with GC -- Garbage Collection.
+ +The client can choose how to format its objects, but the MPS will +sometimes need to ask the client some questions about an object, such +as:
+For each type of question, the client must provide a function that gives
+the answer. These functions are called "format methods", and are
+collected together into a "format"
+(mps_fmt_t). Usually the client developer writes these functions,
+calls "mps_fmt_create_..." to
+collect them into a format, and passes this format to the MPS as an
+argument to mps_pool_create().
A client's format code is 'special'. It is called at special times (eg. +when handling an interrupt), and is quite restricted in what it is +allowed to do. Format code is often on the critical path for memory +management operations. The full requirement for a format is +complicated; see documentation in the Reference Manual. But +here's a simplified overview:
+ +No format is required for an object in a non-scanned, non-collectable +pool -- the MPS never needs to know the internal details of objects in +these pools.
+ +For collectable and/or scannable pools, the client's format code +generally needs to support three types of object:
+A forwarding object is a placeholder that the MPS uses when it has moved +the object that used to be there. ('Normal' client code never sees +these forwarding objects; only client format code does).
+ +A padding object is a 'dummy' object that the MPS uses when there is not +enough room (eg. at the end of a memory page) to put a real client +object.
+ +The client must be able to distinguish between these three types +of object. To guarantee this, client code MUST initialize +memory obtained from the MPS (by mps_alloc or mps_reserve) BEFORE it +makes any other call into the MPS from that thread (including the call to +mps_commit). Here, "initialize" means at least enough initialization +that the client's format code handles the object correctly, including +whether it is a client object, a forwarding object, or a padding object. +[See also protocol.mps.format.rel.ap. RHSK 2006-06-02]
+ +Indicate the size of a collectable client object:
+List all references from this object to (other) collectable objects:
+Move this client object (obsolete, see below):
+Create/use a forwarding object (used by an incremental moving pool after moving a client object):
+Create a padding object:
+The Copy method is obsolete, and is never called. The MPS just uses
+mps_lib_memcpy() to copy the bytes to the new location.
+It knows how many bytes to copy by using the Skip method.
Historical notes: The original justification for Copy was:
+... but this didn't happen with actual clients, and the interface +to the copy method didn't pass the skip-size (which the MPS has +already determined by calling Skip) and so didn't allow an efficient +copy method to be written. So it was dropped, in 1998 or earlier. +The only place this memcpy currently occurs is in poolamc.c, in +AMCFix() (and now AMCHeaderFix() too).
+ +There are notes on this change at +design/trace/#fix.nocopy.
+ +There are several different ways to package-up the format methods -- these different ways are called 'variants'. MPS currently supports four format variants. The creation functions for these are:
+ + +It's a bit messy -- sorry.
+ ++//info.ravenbrook.com/project/mps/import/2001-09-27/mminfo/doc/impl/h/mps/index.txt#1 + 307 /* Root Creation and Destruction + 308 * + 309 * mps_root_create creates the most general type of root: a scanning + 310 * function with two closure elements, p and s. + 311 * + 312 * mps_root_create_table creates a root from a block of memory which + 313 * contains a contiguous array of references. Pages containing table + 314 * roots may be protected by the MPS if MPS_RM_PROT is set in the + 315 * root mode. + 316 * + 317 * mps_root_create_fmt creates a root from a block of memory which + 318 * contains formatted objects. Pages containing fmt roots may be + 319 * protected by the MPS if MPS_RM_PROT is set in the root mode. + 320 * + 321 * mps_root_create_reg creates a root which will be used to scan + 322 * the registers of a thread. (Often it will scan the stack, too.) + 323 */ ++ + + +
These notes on Protection and incremental collection were written + by RHSK between 2006-06-15 and 2006-06-15, following research and + discussion with RB and DRJ.
+ +The MPS can set operating-system read- or write-barriers on certain + pages. When client tries to use this protected memory, the MPS + interrupts and does just enough garbage-collection to allow the + client to see this page.
+ +On Windows, currently, these barriers are implemented using SEH -- Structured Exception Handling.
+ ++ + + ++//info.ravenbrook.com/mail/2006/05/17/11-03-54/0.txt +"chat with DRJ RB RHSK about work for Configura, and other MPS issues" +... +MPS should be part of runtime for a language. +One necessary part is SEH: + - required once per thread; + - AND required on foreign function calls inward. +Otherwise, + 1. some foreign C++ might steal our exception; + 2. this might be a thread we've never seen before +(In fact, client need to have a bit standard of code that works out +if the MPS has seen this thread before. It must call this code on +every inbound call from foreign code.) DRJ: "Dylan does this". +There's a bunch of assumes about compiled code, ABI etc, play nice +with sighandler etc. +Might be poss for GR to geneerate code that doesn't use SEH if he +wasn't using MPS. + +MPS has a requirement that you use this extremely poorly documented +SEH interface. +2 improvements: + 1. better documentation for this + 2. try to make the MPS *not* require SEH + +job001360 -- SEH +
These notes on Allocation Points were written by RHSK between + 2006-06-07 and 2006-06-22, following research and discussion with + RB and NB. + Warning: the text in this User's Guide + is preliminary, but believed to be 'conservatively correct'. + In other words, I think if you follow these guidelines, your code + will be correct, and will not violate the current or future + definitions of the MPS ap protocol. But this is not (yet) an + accurate statement of the MPS ap protocol. RHSK 2006-06-13.
+ +[Note: some constraints + may be mentioned only here, and not yet in other places they + should be mentioned, such as the Reference Manual. + Notably, the client's obligation to ensure there are no exact + references to a failed new-object, before it calls mps_ap_trip, + is suspected to be new. RHSK 2006-06-13]
+ +Allocation points are an MPS protocol that the client uses to + allocate memory with low overhead, and low synchronization + cost (with an asynchronous collector and with other threads).
+ +The allocation point protocol is designed to work with + incremental collections and multi-threaded clients. + (And even if your particular client is + single-threaded and non-incremental, + for the purposes of using allocation points + it's easiest to assume you are coding for this case).
+ +The assumption is that, between any + two client instructions, the MPS can interrupt you, move + objects around (if they are in a moving pool) and collect + garbage. To cope with this, allocating is a two-step process.
+ +Important: + .assume.ambig-workspace: + this User's Guide + assumes that you have declared your stack and registers to + be a root that is ambiguously scanned, using mps_root_create_reg + and passing the mps_stack_scan_ambig function to it. + This is the simplest way to write a client. + Other scenarios are possible, but are not yet documented here.
+ +
+ Note: This document explains the protocol in terms of the
+ pre-packaged macros
+ mps_reserve and mps_commit,
+ but this is a simplification.
+ The MPS allocation point protocol is actually designed as
+ binary protocol, defined at the level of atomic machine operations.
+ The precise specification of the binary protocol is beyond the
+ scope of this document.
The rest of this Allocation Points User's Guide contains the following sub-sections:
+To create an allocation point in a pool,
+ call mps_ap_create.
+ This may require additional arguments, depending on the pool
+ class. See pool class documentation.
An allocation point MUST NOT be used by more + than one thread. (Each thread must have its own allocation point or + points).
+ +Destroy an allocation point with mps_ap_destroy.
When the client is building (creating and formatting) a new + object, you can think of it as being 'in a race' with the MPS. + The object is 'under + construction', and the MPS cannot manage it in the normal way. + So the client should build the object quickly, and then + commit it to MPS management. Rarely, the MPS has to move other + objects around right in the middle of this build phase: that's + a (small) price you pay for having an asynchronous collector. + If this happens, the MPS will tell the client that it has 'lost the + race'. Objects have moved around, and the new object is invalid. + The client must start building it again from scratch.
+ +The client starts building the new object with
+ mps_reserve, and
+ marks it complete by calling mps_commit.
+ Almost always, mps_commit succeeds. But if the
+ client did not complete the object in time, then
+ mps_commit fails (returns 0).
This is how the client should build a new object:
+mps_reserve some memory,mps_commit the new object to MPS management;If commit succeeds, the object is complete, and immediately + becomes just a normal allocated object. + The client may write a reference to the + new object into some older object (thereby connecting the + new object into the client's graph of objects).
+ +If commit fails, the new object no longer exists: + the data has gone and any references that used to refer to it + are now dangling pointers. + The client should simply try to build the + object again.
+ +In pseudo-code, the standard allocation point idiom is:
+ ++ ++ do + mps_reserve + initialize new object + make an ambiguous reference to new object + while (! mps_commit) + link new object into my object graph +
(Do not worry about getting stuck in this loop: + commit usually fails at most once per collection, + so it is very rare for commit to fail even once, + let alone twice).
+ +In C, this typically looks like this:
+ ++ +int make_object(mps_ap_t ap, object *parent) +{ + void *p; + object *neo = NULL; + + do { + if (mps_reserve(&p, ap, SIZE_OBJECT) != MPS_RES_OK) { + goto fail_make_object; + } + /* Build the new object */ + neo = p; + neo->formatcode = FORMAT_CLIENT; /* (not fwd or pad) */ + neo->type = TYPE_OBJECT; + neo->size = SIZE_OBJECT; + neo->parent = parent; + neo->family = parent->family; + neo->child = NULL; + /* neo (ambiguous reference) preserves the new object */ + } while (! mps_commit(ap, p, SIZE_OBJECT)); + + /* Success: link the new object into my object graph */ + parent->child = neo; + return TRUE; + +fail_make_object: + return FALSE; /* out of memory, etc */ +} +
Note that, throughout this User's Guide, we assume that
+ the stack and registers are declared as ambiguous roots
+ (.assume.ambig-workspace)
+ which means that the neo pointer
+ keeps the new object alive for us.
The rest of this User's Guide goes through these steps in more + detail.
+ + +The MPS is a moving garbage collector: it supports + preserve-by-copying pools, whose objects are 'mobile'. + Whenever the MPS moves an object, it will ensure that + all managed references are updated to point to the + new location -- and this happens instantaneously as far + as the client sees it.
+ +The client should assume that, between any pair of + instructions, the MPS may 'shake' this graph, moving + all the mobile objects, and updating all the managed + references.
+ +Any parts of the graph that are no longer connected + (no longer reachable from declared roots) may be collected, + and the memory that those objects occupied may be unmapped, + or re-used for different objects.
+ +The client usually takes care to ensure that all the + references it + holds are managed. To be managed, the reference must be + in a declared root (such as a scanned stack or a global variable), + or in a formatted object that is reachable from a root.
+ +It is okay for a careful client to hold unmanaged references, + but:
+Call mps_reserve, passing the size of the
+ new object you wish to create.
+ The size must be aligned to the pool alignment.
+ This is in contrast to mps_alloc, which (for some pools) allows
+ unaligned sizes.
[Normally, use mps_reserve
+ (the lower-case C macro).
+ But if you are using a weak compiler that does not detect common
+ subexpressions, you may find that using
+ MPS_RESERVE_BLOCK (functionally identical) generates
+ faster code.
+ Or it may generate slower code. It depends on your compiler, and
+ you will have to conduct tests to find out.]
mps_reserve returns a reference to a piece
+ of new memory for the client to build a new object in.
+ During this build, the MPS pins the piece of memory, and
+ treats it as raw data.
"Pinned" means: it will not move, be collected, be unmapped, + or anything like that. You may keep an unmanaged reference to + it at this time.
+ +"Raw data" means two things:
+ +Firstly, "raw data" means that any references stored IN the + new object are unmanaged. This means:
+Secondly, "raw data" means that any references TO the new + object are treated like other references to unmanaged memory:
+The client will typically do all these things:
+However, during the build, there are a couple of restrictions:
+Once the client has stored a reference IN the new object, + it MUST NOT read it out again — + any reference stored in the new object is unmanaged, + and may have become stale.
+ +(Actually, the restriction is: the moment a reference to an + existing mobile object is written into the new object, that + reference (in the new object) may become stale. And you'd better + not use (dereference) a stale reference. And you'd better not + write it into any exactly-scanned cell (such as in an existing + object). + Reading it into an ambiguously-scanned cell (such as an ambiguously + scanned register or stack cell) is okay as long as you don't + dereference it. + Writing it back into another part of the new object is okay too. + Just don't trust it to be a valid reference.)
+The client MUST NOT store a reference TO the + new object in any exactly-scanned place.
+ +[Note: this is in fact possible, but the + protocol for doing it is more complex, and beyond the scope of + this guide. RHSK 2006-06-22]
+ +This means the client should NOT connect the new object into + the graph of managed objects during the build.
+Before the end of the build phase:
+Optionally, for improved robustness to bugs, consider initialising + all parts of the new object, including parts that are not + yet being used to store useful data (such as a string buffer). + You might want to make this compile-time switchable, for debugging.
+ +++ + +If you leave these unused parts + uninitialised, they may contain data that + looks like a valid object -- this is called a "spoof object". + (This might be the 'ghost' of a previous object, or just random + junk that happens to look like a valid object).
+ +This is completely legal: spoof objects + do not cause a problem for the MPS.
+ ++ However, this might leave you with less safety margin than you + want, especially when developing a new client. + If there were to be a bug in your code (or indeed in + the MPS) that resulted in a bogus exact reference to this spoof, + it might go undetected, + and arbitrary corruption might occur before the bug came to light. + So, consider filling these as-yet unused parts with specially + chosen dummy values, at least as an option for debugging. + Choose dummy values that your format code will recognise as + not permitted at the start of a valid formatted object. + You will then detect bogus exact references more promptly.
+ +[RHSK 2006-06-15: + In poolamc, these ghosts will be forwarding pointers, + and they will usually get unmapped (though + unless we use zeroed / secure / etc VM they may get mapped-in + again intact). + But if the tract is nailed they won't even get unmapped. + And ghost forwarding pointers are just as bad news as any other + spoof. + There's currently no format method "destroy". If there was, + we could call it in the reclaim phase, to allow format code to + safely mark these ghosts as dead. Actually, perhaps that's a + valid use of the 'pad' method? + ]
+
When you call mps_commit, it will either fail or succeed.
Almost always, mps_commit succeeds.
+ If it succeeds, that means:
Occasionally but rarely, mps_commit fails.
+ This means:
mps_commit returns;If commit fails, the client usually tries making the object again + (although this is not required: it is allowed to just give up!). + This is why the standard allocation point idiom has a + do...while loop.
+ + +Here are some examples of mistakes to avoid:
+ ++ +The example below is INCORRECT. + +typedef struct object_s { + int formatcode; /* FORMAT_CLIENT, _FWD, or _PAD */ + int type; + size_t size; + struct object_s *family; + struct object_s *parent; + struct object_s *child; +} object; + +int make_object(mps_ap_t ap, object *parent) +{ + void *p; + object *neo = NULL; + + do { + if (mps_reserve(&p, ap, SIZE_OBJECT) != MPS_RES_OK) { + goto fail_make_object; + } + /* Build the new object */ + neo = p; + neo->formatcode = FORMAT_CLIENT; + neo->type = TYPE_OBJECT; + neo->size = SIZE_OBJECT; + neo->parent = parent; + neo->family = neo->parent->family; /*--- incorrect-1 ---*/ + parent->child = neo; /*--- incorrect-2 ---*/ + + /* neo (ambiguous reference) preserves the new object */ + } while (! mps_commit(ap, p, SIZE_OBJECT)); + + neo->child = NULL; /*--- incorrect-3 ---*/ + return TRUE; + +fail_make_object: + return FALSE; /* out of memory, etc */ +} + +The example above is INCORRECT. +
Incorrect-1: do not read references from the new object.
+ Dereferencing neo->parent is illegal.
+ (The code may use parent->family).
Incorrect-2: making an exact reference to the new object is illegal. + (The code should only do this after a successful commit).
+ +Incorrect-3: the child slot (in this example) is
+ exactly scanned, and it MUST be initialised before the call to
+ commit.
+ (The code shown is initialising it too late).
The synchronization issues are a little tricky. This following + notes on these issues were written by RHSK between + 2006-06-12 and 2006-06-12.
+ +The MPS allocation point protocol is a binary protocol. You don't + have to use the mps_reserve and mps_commit macros, but they are + conventional and useful pre-packaged implementations. + I'm using them as an example of correct protocol, referring to + mps.h#17. + It looks like this:
+ +#define mps_reserve(_p_o, _mps_ap, _size) \
+ ((char *)(_mps_ap)->alloc + (_size) > (char *)(_mps_ap)->alloc && \
+ (char *)(_mps_ap)->alloc + (_size) <= (char *)(_mps_ap)->limit ? \
+ ((_mps_ap)->alloc = \
+ (mps_addr_t)((char *)(_mps_ap)->alloc + (_size)), \
+ *(_p_o) = (_mps_ap)->init, \
+ MPS_RES_OK) : \
+ mps_ap_fill(_p_o, _mps_ap, _size))
+
+#define mps_commit(_mps_ap, _p, _size) \
+ ((_mps_ap)->init = (_mps_ap)->alloc, \
+ (_mps_ap)->limit != 0 || mps_ap_trip(_mps_ap, _p, _size))
+
+
+Abstractly, the mutator code has a cycle of four operations on the + allocation point:
+The normal cycle is Lr A I Lc.
+ +After Lr, the mutator checks that A + size <= Lr. If this fails, + then the mutator does mps_ap_fill instead of A. So Lr mps_ap_fill I Lc + is also a valid cycle.
+ +After Lc, the mutator checks that Lc != 0. If this fails, the + mutator will call mps_ap_trip before beginning a new cycle. So + Lr A I Lc mps_ap_trip is also a valid cycle.
+ +The mutator cannot interrupt the + collector.
+ +The collector can interrupt the mutator (between any + two mutator instructions). The collector can only see the A, I, + and mps_ap_trip (if present) operations; Lr and Lc are invisible + to it.
+ +If the ap is not going to trip, the collector sees two + equivalence classes:
+If the ap is going to trip, the collector sees four + equivalence classes:
+The collector has two responsibilities:
+Let's see what's required for a mutator that promises to make no + exact references to the new object until Lc succeeds, + and promises to have at least one ambiguous reference to the + new object when it sets I.
+ +Consider a flip -- f1 -- in state A.
+ +The collector at f1 sees (A), and recognises that the I..A region + is unmanaged memory. + The object is never going to be valid, + because it may contain stale references from before the flip, and the + collector can't fix them.
+ +The f1 collector writes L = 0, tripping the allocation + point, and the rest of this collection is easy. + The FIX responsibility is easy: + all references to the new object are ambiguous, so the + collector can fix them or not -- it + doesn't matter. + For SCAN, the collector must not scan the new object + (because it is not yet formatted), so + it must not scan the buffered pool beyond I.
+ +Further collections at this point are idempotent.
+ +Now, suppose the mutator then restarts, but only gets as far + as (I Lc) before we have a second collection and a + second flip -- f2.
+ +For FIX, f2 can fix or not -- it still doesn't matter.
+ +But for SCAN, f2 MUST NOT scan the new object. + Why not?
+ +The mutator's format code will be okay: the fact + that I is set tells f2 that the object + is fully formatted.
+ +But there is a problem: the object may contain stale exact + references -- unfixed references from before f1. + These stale exact references will be bogus. + Opinions differ on the implications of bogus exact references. + See the next section for a discussion.
+ +Additionally, the collector is not obliged to scan the + object: this object is dead! + The mutator will later notice that Lr == 0 and realise the object + is invalid. The mutator is not relying + on this object to keep anything else alive.
+ +It is easy to avoid scanning the invalid object: + the first flip in state (A), f1, must record the value of I. + Call the recorded pointer If1. + Collections must not scan beyond If1. + If1 remains set until the mutator calls mps_ap_trip, + which resets If1 to 0. + [Note: I have not checked whether the MPS + records and uses If1 -- RHSK 2006-06-12]
+ +Tucker said:
++ +I believe the collector must be prepared to deal + with exact dangling pointers anyways, so this complex + mechanism is unnecessary. + [//info.ravenbrook.com/project/mps/mail/1997/05/12/12-46/1.txt:X-MMInfo-Tag: mail.ptw.1997-05-12.12-46(1)] +
I'm not convinced.
+ +Fixing a bogus exact reference is bad news. + The worst case is spoofing: + Imagine the bogus exact reference points at part of a + JPEG that just happens to look like a validly formatted + object. + If this JPEG is in the middle of an object in a moving MPS + pool, fixing the bogus exact reference will overwrite a portion + of the JPEG with a forwarding object. + It gets worse: the spoof object is preserved and will later be + scanned, producing more bogus exact references! + For "JPEG", you can substitute "encrypted string".
+ +The only safe way to cope with such a bogus reference is for + Fix to verify that the reference points to the start of a real + object, which it could do by iterating the format skip method + from some known point in the pool.
+ +The consequences of fixing a bogus exact + reference may be:
+Also, more arcanely, I wonder whether there's a problem if the + referent violates the tri-colour invariant (when scanning at + black)? Does the MPS care about this, or does it 'safely' just + cause more conservatism? Does MPS detect and flag this in + debug versions? Could it?
+ +If MPS or format code detects a bogus exact reference, it could + assert, and/or to fix them to a canonical special value.
+ +Some possible contracts between mutator and collector:
+For an all-exact mode of use, mutator must make an exact pointer +before setting I=A, and must keep it at least until it after +it has read Lc to see whther the commit succeeded.
+ +So, some additions to the AP User's Guide, in the section on mps_reserve:
+ +++ +Secondly, "raw data" means that any references TO the new + object are treated like other references to unmanaged memory. + [.belief.refs-to-uninit-safe: + We're 'sure', but I need to check this. What does Fix + actually do with a pointer into the init-alloc zone? We + hope it ignores it. RHSK 2006-06-09] + Because of this, you are permitted to connect the new object + into your graph of managed objects immediately. The MPS gives + you these guarantees:
++
+- the new object is pinned (won't move), so references to it + that you write in old objects won't become stale at this time + (but see
+mps_commitbelow!)- although the new object is 'reachable' by these references, + at this stage (while I < A) the MPS knows it + is not yet managed, and will not try to preserve it;
+- the MPS will not call the client's format code to answer + questions about the new object.
+
And to the section on mps_commit:
+++ +When this happens the client should take care to clear up any + managed references to the (now vanished) new object.
+ +[But there's a hole here, before the client does this. + Are managed (aka scanned) references TO + it still safe? They were safe during building + (by .belief.refs-to-uninit-safe). But now the AP pointers have + gone away. Are they still safe? + Clearly, if they are only RankAMBIG, they are safe. + What if they are RankEXACT? + RHSK 2006-06-09]
+ +[Discussion with RB 2006-06-09: yes, that's a problem for exact + references. Must not make any exact refs to a new object. And + unmanaged refs are not sufficient, because they won't preserve the + new object during commit. So must make at least one ambiguous + ref to new object before calling commit. That's the truth + currently. There are various ways to solve this to allow + purely-exact mutators. For instance, + keep the old init..alloc address-space flagged as a zombie zone, + until some communication with mutator (perhaps another reserve + from same AP?) indicates that mutator has removed all those + pesky exact refs to the now-dead ex-new object. RHSK 2006-06-09]
+
See issues with unmanaged workspace for + a discussion of the "abort" phase, which we need to define + for allocation points.
+ +The MPS needs to keep the buffer mapped for some time -- + until the mutator has stopped writing into it. + The MPS needs to remember If1 forever. + The MPS needs to remember the rest of the + about-to-be-detached buffer structure for some time -- + when is the MPS permitted to detach the buffer?
+ +Keeping the buffer mapped consumes resource. + There must be a contract with the mutator about when the + MPS is permitted to free it. +
+ +We could define the protocol such that there is a window: + after the mutator discovers that it has lost the race, but + while the collector is still remembering that this object + is invalid. The mutator could use this window to null-out + exact references to the new object.
+ +This window could be after Lc and before calling mps_ap_trip. + During this time, + the collector must keep the new object as pinned unmanaged + memory. By calling mps_ap_trip, the mutator promises that + it has nulled-out any exact references to the new object, + and the collector in mps_ap_trip may unmap the memory or + safely re-use it without fear of spoofing.
+ +Or, we could leave the window open until mps_ap_fill is + called. We just need to define it.
+ +Perhaps the collector wants to flip even when the ap is not + at (A). Need to analyse synchronization issues here.
+ ++ 2006-06-02 RHSK Created. + 2006-06-02 RHSK Introduction to MPS Formats + 2006-06-06 RHSK Formats: clarify explanation of methods, copy method is + obsolete, mention format variants. + 2006-06-09 RHSK Allocation points: how it's supposed to be, from RB 2006-06-09. + 2006-06-09 RHSK Allocation points: must make at least one ambiguous ref + and no exact refs to new object before calling commit. + 2006-06-12 RHSK Allocation points: minor edits for clarity. + 2006-06-12 RHSK Allocation point internals: Scenario; A mutator with + ambiguous references only (to the new object); How + bad is a bogus exact reference?; quick notes on: with + exact refs; flipping at other times. + 2006-06-13 RHSK Allocation point user's guide: Tidy; clarify-- not yet complete. + Distinguish it from section on AP internals. + 2006-06-14 RHSK Roots -- User's Guide: bare bones: root variants. + Allocation point user's guide: standard reserve-commit + idiom: corrections, and now assume ambiguous reg+stack: + transitioning to this assumption. + Add .talk.RB.2006-06-13 about standard r-c idiom + Add .talk.RB.2006-06-14 about Modes of use of MPS, + and Promises to not flip (single-threaded). + Add .think.RHSK.2006-06-14 about how we could support + unscanned reg+stack, even with multi-threaded, moving + collector. + 2006-06-15 RHSK Allocation Points: clarifications and further notes + into User Guide and Internals, including initializing + as-yet unused parts of new objects to reduce spoofing. + 2006-06-15 RHSK Brief notes on Protection and incremental collection. + 2006-06-22 RHSK Move rough notes .talk.RB.2006-06-13 etc elsewhere. + Make AP User Guide consistently .assume.ambig-workspace, + moving notes to APInternals; add Intro and Mistakes; + check example code. ++ + +
This document is copyright © 2006 Ravenbrook Limited. All rights reserved. This is an open source license. Contact Ravenbrook for commercial licensing options.
+ +Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met:
+ +This software is provided by the copyright holders and contributors "as is" and any express or implied warranties, including, but not limited to, the implied warranties of merchantability, fitness for a particular purpose, or non-infringement, are disclaimed. In no event shall the copyright holders and contributors be liable for any direct, indirect, incidental, special, exemplary, or consequential damages (including, but not limited to, procurement of substitute goods or services; loss of use, data, or profits; or business interruption) however caused and on any theory of liability, whether in contract, strict liability, or tort (including negligence or otherwise) arising in any way out of the use of this software, even if advised of the possibility of such damage.
+ + +