Skip to content

Commit 0f10205

Browse files
committed
Rename CABI 'active' lock to 'fiber' (last rename)
1 parent 4d1030b commit 0f10205

File tree

2 files changed

+26
-25
lines changed

2 files changed

+26
-25
lines changed

design/mvp/CanonicalABI.md

Lines changed: 18 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -261,7 +261,7 @@ class ComponentInstance:
261261
pending_async_tasks: list[asyncio.Future]
262262
handles: HandleTables
263263
async_subtasks: Table[AsyncSubtask]
264-
active: asyncio.Lock
264+
fiber: asyncio.Lock
265265

266266
def __init__(self):
267267
self.may_leave = True
@@ -271,7 +271,7 @@ class ComponentInstance:
271271
self.pending_async_tasks = []
272272
self.handles = HandleTables()
273273
self.async_subtasks = Table[AsyncSubtask]()
274-
self.active = asyncio.Lock()
274+
self.fiber = asyncio.Lock()
275275
```
276276
The `may_leave` field is used below to track whether the instance may call a
277277
lowered import to prevent optimization-breaking cases of reentrance during
@@ -289,16 +289,16 @@ The `async_subtasks` field is used below to track and assign an `i32` index to
289289
each active async-lowered call in progress that has been made by this
290290
`ComponentInstance`.
291291

292-
Finally, the `active` field is used below to restrict the switching of Python
292+
Finally, the `fiber` field is used below to restrict the switching of Python
293293
coroutines (`async def` functions) to only occur at specific points (such as
294294
when a task blocks on `task.wait` or when an `async callback`-lifted export
295295
call returns to its event loop to wait for an event. Thus, the calls to
296-
`active.acquire()` and `active.release()` in the Python code below point to
296+
`fiber.acquire()` and `fiber.release()` in the Python code below point to
297297
where the runtime may switch between concurrent tasks. Without this
298298
`asyncio.Lock`, Python's normal `asyncio` semantics would allow switching
299299
between concurrent tasks at *every* spec-internal `await`, which would lead to
300300
multi-threading-like interleaving between concurrent tasks. (Alternatively, if
301-
Python had standard-library fibers, they could have been used instead of
301+
Python had standard-library [fibers], they could have been used instead of
302302
`asyncio`, obviating the need for this `Lock`.)
303303

304304
One `HandleTables` object is stored per `ComponentInstance` and is defined as:
@@ -495,12 +495,12 @@ for a component export called directly by the host, or else the current task
495495
when the calling component called into this component. The `caller` field is
496496
used by the following two methods to prevent a component from being reentered
497497
(enforcing the [component invariant]) in a way that is well-defined even in the
498-
presence of async calls). (The `active.acquire()` call in `enter()` is
498+
presence of async calls). (The `fiber.acquire()` call in `enter()` is
499499
described above and here ensures that concurrent export calls do not
500500
arbitrarily interleave.)
501501
```python
502502
async def enter(self):
503-
await self.inst.active.acquire()
503+
await self.inst.fiber.acquire()
504504
self.trap_if_on_the_stack(self.inst)
505505

506506
def trap_if_on_the_stack(self, inst):
@@ -558,9 +558,9 @@ guarded to be `0` in `Task.exit` (below) to ensure [structured concurrency].
558558
self.events.put_nowait(subtask)
559559

560560
async def wait(self):
561-
self.inst.active.release()
561+
self.inst.fiber.release()
562562
subtask = await self.events.get()
563-
await self.inst.active.acquire()
563+
await self.inst.fiber.acquire()
564564
return self.process_event(subtask)
565565

566566
def process_event(self, subtask):
@@ -579,7 +579,7 @@ should not have to create an actual queue; instead it should be possible to
579579
embed a "next ready" linked list in the elements of the `async_subtasks` table
580580
(noting the `enqueued` guard above ensures that a subtask can be enqueued at
581581
most once). The implementation of `wait` releases and reacquires the
582-
instance-wide `active` lock to specify that `wait` is a point where the runtime
582+
instance-wide `fiber` lock to specify that `wait` is a point where the runtime
583583
can switch to another task running in the same component instance or start a
584584
new task in response to an incoming export call.
585585

@@ -598,20 +598,20 @@ the runtime to switch to another ready task, but without blocking on I/O (as
598598
emulated in the Python code here by awaiting a `sleep(0)`).
599599
```python
600600
async def yield_(self):
601-
self.inst.active.release()
601+
self.inst.fiber.release()
602602
await asyncio.sleep(0)
603-
await self.inst.active.acquire()
603+
await self.inst.fiber.acquire()
604604
```
605605

606606
Lastly, when a task exists, the runtime enforces the guard conditions mentioned
607-
above and releases the `active` lock, allowing other tasks to start or make
607+
above and releases the `fiber` lock, allowing other tasks to start or make
608608
progress.
609609
```python
610610
def exit(self):
611611
assert(self.events.empty())
612612
trap_if(self.borrow_count != 0)
613613
trap_if(self.num_async_subtasks != 0)
614-
self.inst.active.release()
614+
self.inst.fiber.release()
615615
```
616616

617617
While `canon_lift` creates `Task`s, `canon_lower` creates `Subtask` objects:
@@ -2100,10 +2100,10 @@ the caller can know whether it can reclaim the parameter and result memory
21002100
buffers) and delivering subsequent progress events to the calling task via the
21012101
`AsyncSubtask` `start` and `return_` methods (defined above).
21022102

2103-
Note that the async case does *not* release or reacquire the `active` lock
2103+
Note that the async case does *not* release or reacquire the `fiber` lock
21042104
since (due to the `trap_if_on_stack` reentrance guard in `Task.enter`) the
21052105
`callee` is necessarily in another component instance (which has a separate
2106-
`active` lock). This allows fine-grained inter-component task interleaving (up
2106+
`fiber` lock). This allows fine-grained inter-component task interleaving (up
21072107
to and including preemptive multithreading) which doesn't break regular async
21082108
codes' assumptions due to the component shared-nothing model. This also means
21092109
that an async import calls are *not* allowed to switch to another task in the
@@ -2311,7 +2311,7 @@ async def canon_task_wait(task, ptr):
23112311
The `trap_if` ensures that, when a component uses a `callback` all events flow
23122312
through the event loop at the base of the stack.
23132313

2314-
Note that `task.wait` releases and reacquires the `active` lock and thus
2314+
Note that `task.wait` releases and reacquires the `fiber` lock and thus
23152315
`canon_task_wait` allows the runtime to switch to another active task in the
23162316
current component instance. Note also that `task.wait` can be called from a
23172317
sync-lifted `SyncTask` so that even fully synchronous code can make concurrent
@@ -2457,6 +2457,7 @@ def canon_thread_hw_concurrency():
24572457
[Unicode Code Point]: https://unicode.org/glossary/#code_point
24582458
[Surrogate]: https://unicode.org/faq/utf_bom.html#utf16-2
24592459
[Name Mangling]: https://en.wikipedia.org/wiki/Name_mangling
2460+
[Fibers]: https://en.wikipedia.org/wiki/Fiber_(computer_science)
24602461
[Asyncify]: https://emscripten.org/docs/porting/asyncify.html
24612462

24622463
[`import_name`]: https://clang.llvm.org/docs/AttributeReference.html#import-name

design/mvp/canonical-abi/definitions.py

Lines changed: 8 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -299,7 +299,7 @@ class ComponentInstance:
299299
pending_async_tasks: list[asyncio.Future]
300300
handles: HandleTables
301301
async_subtasks: Table[AsyncSubtask]
302-
active: asyncio.Lock
302+
fiber: asyncio.Lock
303303

304304
def __init__(self):
305305
self.may_leave = True
@@ -309,7 +309,7 @@ def __init__(self):
309309
self.pending_async_tasks = []
310310
self.handles = HandleTables()
311311
self.async_subtasks = Table[AsyncSubtask]()
312-
self.active = asyncio.Lock()
312+
self.fiber = asyncio.Lock()
313313

314314
class HandleTables:
315315
rt_to_table: MutableMapping[ResourceType, Table[HandleElem]]
@@ -411,7 +411,7 @@ def __init__(self, opts, inst, caller):
411411
self.num_async_subtasks = 0
412412

413413
async def enter(self):
414-
await self.inst.active.acquire()
414+
await self.inst.fiber.acquire()
415415
self.trap_if_on_the_stack(self.inst)
416416

417417
def trap_if_on_the_stack(self, inst):
@@ -442,9 +442,9 @@ def async_subtask_made_progress(self, subtask):
442442
self.events.put_nowait(subtask)
443443

444444
async def wait(self):
445-
self.inst.active.release()
445+
self.inst.fiber.release()
446446
subtask = await self.events.get()
447-
await self.inst.active.acquire()
447+
await self.inst.fiber.acquire()
448448
return self.process_event(subtask)
449449

450450
def process_event(self, subtask):
@@ -461,15 +461,15 @@ def poll(self):
461461
return self.process_event(self.events.get_nowait())
462462

463463
async def yield_(self):
464-
self.inst.active.release()
464+
self.inst.fiber.release()
465465
await asyncio.sleep(0)
466-
await self.inst.active.acquire()
466+
await self.inst.fiber.acquire()
467467

468468
def exit(self):
469469
assert(self.events.empty())
470470
trap_if(self.borrow_count != 0)
471471
trap_if(self.num_async_subtasks != 0)
472-
self.inst.active.release()
472+
self.inst.fiber.release()
473473

474474
class Subtask(CallContext):
475475
lenders: list[HandleElem]

0 commit comments

Comments
 (0)