The first two changes close a scoped memory leak. If an AEH uses the default initial memory area, 1.0.1's semantic 17 will prevent that memory area from ever returning to a zero reference count. In the case of a thread, the reference count could return to zero if and only if the thread is started and terminates.
This set of changes primarily revises semantic 17 so being an initial memory area is only a source of non-zero reference if it is not the default initial memory area. This closes the above leak.
In Memory Semantics, add the following definitions
For purposes of scoped memory reference counting, the following are treated as execution contexts:
RealtimeThread
objects that have been started and have not terminated,AsyncEventHandler
objects that are currently in a released state,AsyncEvent
objects that are bound to happenings,Timer
objects that have been started and have not been destroyed,The initial memory area for a schedulable object is a non-default initial memory area if it is not the memory area where the schedulable object was created.
In Memory Semantic 17, change
17. Each instance of the class ScopedMemory or its subclasses must maintain a reference count which is greater than zero if and only if either:
For purposes of this semantic the following are treated as execution contexts:
To
17. Each instance of the class ScopedMemory
or its subclasses must maintain a reference count which is greater than zero if and only if either:
RealtimeThread
and it terminates; or elseNote that this change has two elements: the definition of an execution context has been moved to the definitions section, and "initial memory area" has been changed to "non-default initial memory area" in the second bullet of semantic 17.
Finalization of non-default initial memory areas can trigger a paradox in the specification. Semantic 17 triggers finalization when an initial memory area's reference count to goes to zero because the SO is de-allocated, and semantic 19 requires that finalizers in the initial memory area are executed by the SO leaving the initial memory area. In several cases, there will be no SO that can be viewed as leaving the initial memory area. Consider, for instance, the initial memory area of a real-time thread that has never been started and is being de-allocated.
This set of changes separates assignment of the initial memory's parent from incrementing its reference count. The updated semantics only support a non-zero reference count when an activation can be associated with the initial memory area. This separation lets start() and fire() continue to work without the risk of a scope cycle exception, but the joinAndEnter() methods now risk a scope cycle exception because that method can see the case where the reference count is zero but the scope has a parent.
For simplicity, change 5 is expressed based on the specification after change 2.
In the Memory Management Chapter, at the end of the definitions section, add:
An AsyncEventHandler is fireable if it is:
Change semantic 11 from
11. Instances of ScopedMemory have special semantics including definition of parent. If a ScopedMemory object is not in use, it has no parent scope. When a ScopedMemory object becomes in use, its parent is the nearest ScopedMemory object outside it on the current scope stack. If there is no outside ScopedMemory object in the current scope stack, the parent is the primordial scope which is not actually a memory area, but only a marker that constrains the parentage of ScopedMemory objects
to
11. Instances of ScopedMemory have special semantics including definition of parent. If a ScopedMemory object is neither in use nor the initial memory area for a schedulable object, it has no parent scope.
Change semantic 17 from
17. Each instance of the class ScopedMemory
or its subclasses must maintain a reference count which is greater than zero if and only if either:
RealtimeThread
and it terminates; or elseto
17. Each instance of the class ScopedMemory or its subclasses must maintain a reference count which is greater than zero if and only if either:
AsyncEventHandler
.Add to the end of semantic 19
If finalizers are executed because a RealtimeThread terminates or an AsyncEventHandler becomes non-fireable, that RealtimeThread or AsyncEventHandler is considered in control of the scope and must execute the finalizers.
Change the last clause of the pseudo-code for constructing an SO from
if ima != cma
push ima on new scope stack --
which may throw ScopedCycleException
to
if ima != cma
set the parent of ima --
which may throw ScopedCycleException
Add
ScopedCycleException - Thrown if this invocation would
break the single parent rule.
To the two ScopedMemory joinAndEnter methods that do not take a high-resolution time parameter.
In the Asynchrony Chapter, AsyncEventHandler class, handleAsyncEvent() method, third paragraph of description, add
unless this AsyncEventHandler becomes unfireable.