shellsim 0.1.14__tar.gz → 0.1.16__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- {shellsim-0.1.14 → shellsim-0.1.16}/Cargo.lock +1 -1
- {shellsim-0.1.14 → shellsim-0.1.16}/Cargo.toml +1 -1
- {shellsim-0.1.14 → shellsim-0.1.16}/PKG-INFO +1 -1
- {shellsim-0.1.14 → shellsim-0.1.16}/python/native/Cargo.lock +2 -2
- {shellsim-0.1.14 → shellsim-0.1.16}/python/native/Cargo.toml +1 -1
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/compiler.rs +0 -2
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/heap.rs +6 -1
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/source/asyncio.py +182 -38
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/vm/calls.rs +1 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/vm/iteration.rs +43 -22
- {shellsim-0.1.14 → shellsim-0.1.16}/LICENSE +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/README.md +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/pyproject.toml +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/python/native/src/lib.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/python/shellsim/__init__.py +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/python/shellsim/__main__.py +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/python/shellsim/_api.py +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/python/shellsim/_cli.py +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/python/shellsim/py.typed +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/python/shellsim/python.py +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/rust-toolchain.toml +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/bin/shellsim-python.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/clock.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/commands/archives.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/commands/awk/ast.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/commands/awk/eval.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/commands/awk/lexer.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/commands/awk/parser.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/commands/awk.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/commands/builtins.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/commands/dd.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/commands/echo.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/commands/find.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/commands/fs.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/commands/git/apply.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/commands/git/commit.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/commands/git/compare.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/commands/git/config.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/commands/git/conflict.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/commands/git/diff.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/commands/git/ignore.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/commands/git/import.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/commands/git/log.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/commands/git/merge.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/commands/git/mod.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/commands/git/plumbing.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/commands/git/rebase.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/commands/git/refs.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/commands/git/repo.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/commands/git/stash.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/commands/git/switch.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/commands/git/worktree.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/commands/hashing.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/commands/makecmd.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/commands/mod.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/commands/net.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/commands/options.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/commands/patch.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/commands/pkg.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/commands/printf.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/commands/proc.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/commands/regex_compat.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/commands/rgcmd.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/commands/sed.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/commands/sort.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/commands/system.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/commands/tarcmd.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/commands/text.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/commands/unavailable.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/commands/util.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/commands/zipcmd.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/descriptors.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/exec.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/expand.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/harness.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/harness_manager.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/hashes.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/host_ingest.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/interp.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/jqcmd.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/lib.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/main.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/mcp.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/net.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/netcmd.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/process.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/pseudo_fs.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/ast.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/bytecode.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/filesystem.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/http.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/lexer.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/mapping.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/mod.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/native.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/number.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/object_model.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/parser.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/process.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/protocol.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/slice.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/source.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/argparse.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/asyncio.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/base64.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/bisect.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/collections.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/core.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/dataclasses.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/enum.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/frozen.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/functools.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/hashlib.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/heapq.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/http.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/importlib.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/itertools.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/json.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/math.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/mod.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/numpy.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/os.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/pytest.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/re.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/source/abc.py +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/source/base64.py +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/source/cmath.py +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/source/codecs.py +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/source/collections.py +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/source/complex.py +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/source/copy.py +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/source/csv.py +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/source/datetime.py +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/source/glob.py +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/source/hashlib.py +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/source/http.py +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/source/http_client.py +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/source/importlib.py +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/source/io.py +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/source/json.py +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/source/logging.py +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/source/numpy_random.py +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/source/os.py +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/source/pathlib.py +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/source/pytest.py +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/source/random.py +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/source/shutil.py +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/source/statistics.py +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/source/struct.py +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/source/subprocess.py +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/source/tempfile.py +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/source/textwrap.py +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/source/urllib.py +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/source/urllib_error.py +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/source/urllib_request.py +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/source/uuid.py +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/source/zipfile.py +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/source/zlib.py +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/string.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/struct.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/subprocess.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/sys.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/time.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/typing.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/unittest.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/vfs.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/stdlib/zlib.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/string.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/token.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/vm/dispatch.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/vm/host.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/vm/namespace.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/vm/native_runtime.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/vm/objects.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/vm/operations.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/python/vm.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/resources.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/sandbox.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/scenario.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/scheduler.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/shell.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/telemetry.rs +0 -0
- {shellsim-0.1.14 → shellsim-0.1.16}/src/vfs.rs +0 -0
|
@@ -406,7 +406,7 @@ dependencies = [
|
|
|
406
406
|
|
|
407
407
|
[[package]]
|
|
408
408
|
name = "shellsim"
|
|
409
|
-
version = "0.1.
|
|
409
|
+
version = "0.1.16"
|
|
410
410
|
dependencies = [
|
|
411
411
|
"base64",
|
|
412
412
|
"crc32fast",
|
|
@@ -427,7 +427,7 @@ dependencies = [
|
|
|
427
427
|
|
|
428
428
|
[[package]]
|
|
429
429
|
name = "shellsim-python-bindings"
|
|
430
|
-
version = "0.1.
|
|
430
|
+
version = "0.1.16"
|
|
431
431
|
dependencies = [
|
|
432
432
|
"pyo3",
|
|
433
433
|
"serde",
|
|
@@ -659,8 +659,6 @@ impl Compiler {
|
|
|
659
659
|
self.protected_regions.pop();
|
|
660
660
|
if let Some(handler_body_try) = handler_body_try {
|
|
661
661
|
self.emit(Operation::TryEnd, span);
|
|
662
|
-
self.emit(Operation::ClearException, span);
|
|
663
|
-
self.statements(finalbody.clone());
|
|
664
662
|
let handler_body_done = self.emit(Operation::Jump(usize::MAX), span);
|
|
665
663
|
let handler_body_cleanup = self.instructions.len();
|
|
666
664
|
self.patch_try_begin(handler_body_try, handler_body_cleanup);
|
|
@@ -202,13 +202,14 @@ pub enum Object {
|
|
|
202
202
|
exhausted: bool,
|
|
203
203
|
},
|
|
204
204
|
/// A suspended Python generator frame. The bytecode is immutable; the instruction pointer,
|
|
205
|
-
/// exception
|
|
205
|
+
/// exception state, and lexical scope are the complete resumable state.
|
|
206
206
|
Generator {
|
|
207
207
|
name: String,
|
|
208
208
|
code: CodeRef,
|
|
209
209
|
scope: ScopeId,
|
|
210
210
|
instruction_pointer: usize,
|
|
211
211
|
handlers: Vec<(usize, usize)>,
|
|
212
|
+
exceptions: Vec<(String, Value)>,
|
|
212
213
|
stack: Vec<Value>,
|
|
213
214
|
exhausted: bool,
|
|
214
215
|
running: bool,
|
|
@@ -1433,11 +1434,13 @@ fn trace_object(
|
|
|
1433
1434
|
}
|
|
1434
1435
|
Object::Generator {
|
|
1435
1436
|
scope,
|
|
1437
|
+
exceptions,
|
|
1436
1438
|
stack,
|
|
1437
1439
|
return_value,
|
|
1438
1440
|
..
|
|
1439
1441
|
} => {
|
|
1440
1442
|
scope_work.push(*scope);
|
|
1443
|
+
trace_values(exceptions.iter().map(|(_, value)| *value), object_work);
|
|
1441
1444
|
trace_values(stack.iter().copied(), object_work);
|
|
1442
1445
|
trace_value(*return_value, object_work);
|
|
1443
1446
|
}
|
|
@@ -1566,12 +1569,14 @@ fn modeled_size(object: &Object) -> Result<u64, String> {
|
|
|
1566
1569
|
name,
|
|
1567
1570
|
code,
|
|
1568
1571
|
handlers,
|
|
1572
|
+
exceptions,
|
|
1569
1573
|
stack,
|
|
1570
1574
|
..
|
|
1571
1575
|
} => name
|
|
1572
1576
|
.len()
|
|
1573
1577
|
.checked_add(code.instructions.len())
|
|
1574
1578
|
.and_then(|size| size.checked_add(handlers.len()))
|
|
1579
|
+
.and_then(|size| size.checked_add(exceptions.len()))
|
|
1575
1580
|
.and_then(|size| size.checked_add(stack.len()))
|
|
1576
1581
|
.ok_or("modeled object size overflow")?,
|
|
1577
1582
|
Object::Module { name, .. } => name.len(),
|
|
@@ -197,6 +197,24 @@ class Future:
|
|
|
197
197
|
self._loop._wake_waiters(self)
|
|
198
198
|
|
|
199
199
|
|
|
200
|
+
class _GatheringFuture(Future):
|
|
201
|
+
def __init__(self, children, *, loop):
|
|
202
|
+
Future.__init__(self, loop=loop)
|
|
203
|
+
self._children = children
|
|
204
|
+
self._cancel_requested = False
|
|
205
|
+
|
|
206
|
+
def cancel(self, msg=None):
|
|
207
|
+
if self._done:
|
|
208
|
+
return False
|
|
209
|
+
cancelled = False
|
|
210
|
+
for child in self._children:
|
|
211
|
+
if child.cancel(msg=msg):
|
|
212
|
+
cancelled = True
|
|
213
|
+
if cancelled:
|
|
214
|
+
self._cancel_requested = True
|
|
215
|
+
return cancelled
|
|
216
|
+
|
|
217
|
+
|
|
200
218
|
class Task:
|
|
201
219
|
def __init__(self, coroutine, loop, name=None):
|
|
202
220
|
if not _is_coroutine(coroutine):
|
|
@@ -214,6 +232,7 @@ class Task:
|
|
|
214
232
|
self._name = name
|
|
215
233
|
self._callbacks = []
|
|
216
234
|
self._cancel_requests = 0
|
|
235
|
+
self._must_cancel = False
|
|
217
236
|
self._logical_task = self
|
|
218
237
|
|
|
219
238
|
def done(self):
|
|
@@ -251,6 +270,8 @@ class Task:
|
|
|
251
270
|
def uncancel(self):
|
|
252
271
|
if self._cancel_requests:
|
|
253
272
|
self._cancel_requests -= 1
|
|
273
|
+
if not self._cancel_requests:
|
|
274
|
+
self._must_cancel = False
|
|
254
275
|
return self._cancel_requests
|
|
255
276
|
|
|
256
277
|
def add_done_callback(self, callback, context=None):
|
|
@@ -686,8 +707,12 @@ class _Loop:
|
|
|
686
707
|
self._resource_waiters = []
|
|
687
708
|
self._tasks = []
|
|
688
709
|
self._current = None
|
|
710
|
+
self._running = False
|
|
711
|
+
self._closed = False
|
|
689
712
|
|
|
690
713
|
def create_task(self, coroutine, name=None):
|
|
714
|
+
if self._closed:
|
|
715
|
+
raise RuntimeError("Event loop is closed")
|
|
691
716
|
task = Task(coroutine, self, name)
|
|
692
717
|
self._tasks.append(task)
|
|
693
718
|
self._ready.append(task)
|
|
@@ -705,6 +730,8 @@ class _Loop:
|
|
|
705
730
|
return _monotonic_ns() / 1000000000
|
|
706
731
|
|
|
707
732
|
def call_soon(self, callback, *args, context=None):
|
|
733
|
+
if self._closed:
|
|
734
|
+
raise RuntimeError("Event loop is closed")
|
|
708
735
|
handle = Handle(callback, args)
|
|
709
736
|
self._ready.append(handle)
|
|
710
737
|
return handle
|
|
@@ -713,6 +740,8 @@ class _Loop:
|
|
|
713
740
|
return self.call_soon(callback, *args, context=context)
|
|
714
741
|
|
|
715
742
|
def call_at(self, when, callback, *args, context=None):
|
|
743
|
+
if self._closed:
|
|
744
|
+
raise RuntimeError("Event loop is closed")
|
|
716
745
|
handle = TimerHandle(when, callback, args)
|
|
717
746
|
self._timers.append((int(when * 1000000000), handle))
|
|
718
747
|
return handle
|
|
@@ -726,7 +755,8 @@ class _Loop:
|
|
|
726
755
|
waiter for waiter in self._resource_waiters if waiter[0] is not task
|
|
727
756
|
]
|
|
728
757
|
task._send_value = (True, value)
|
|
729
|
-
self._ready
|
|
758
|
+
if task not in self._ready:
|
|
759
|
+
self._ready.append(task)
|
|
730
760
|
|
|
731
761
|
def _schedule_failure(self, task, error):
|
|
732
762
|
if not task._done:
|
|
@@ -734,10 +764,17 @@ class _Loop:
|
|
|
734
764
|
waiter for waiter in self._resource_waiters if waiter[0] is not task
|
|
735
765
|
]
|
|
736
766
|
task._send_value = (False, error)
|
|
737
|
-
self._ready
|
|
767
|
+
if task not in self._ready:
|
|
768
|
+
self._ready.append(task)
|
|
738
769
|
|
|
739
770
|
def _cancel(self, task):
|
|
740
|
-
if
|
|
771
|
+
if self._current is task:
|
|
772
|
+
task._must_cancel = True
|
|
773
|
+
return
|
|
774
|
+
dependency = task._waiting_on
|
|
775
|
+
if isinstance(dependency, (Task, Future)) and dependency.cancel():
|
|
776
|
+
return
|
|
777
|
+
if isinstance(dependency, _TimeoutWait) and dependency.child.cancel():
|
|
741
778
|
return
|
|
742
779
|
if not task._started:
|
|
743
780
|
task._done = True
|
|
@@ -856,8 +893,7 @@ class _Loop:
|
|
|
856
893
|
else:
|
|
857
894
|
self._schedule(task, awaited._result)
|
|
858
895
|
else:
|
|
859
|
-
|
|
860
|
-
task._waiting_on = awaited
|
|
896
|
+
task._waiting_on = awaited
|
|
861
897
|
awaited._waiters.append(task)
|
|
862
898
|
|
|
863
899
|
def _dispatch_yield(self, task, awaited):
|
|
@@ -905,30 +941,83 @@ class _Loop:
|
|
|
905
941
|
raise TypeError("object cannot be used in 'await' expression")
|
|
906
942
|
|
|
907
943
|
def run(self, coroutine):
|
|
944
|
+
if self._closed:
|
|
945
|
+
raise RuntimeError("Event loop is closed")
|
|
946
|
+
if self._running:
|
|
947
|
+
raise RuntimeError("This event loop is already running")
|
|
908
948
|
root = self.create_task(coroutine)
|
|
909
|
-
|
|
910
|
-
|
|
911
|
-
|
|
912
|
-
|
|
913
|
-
|
|
914
|
-
|
|
915
|
-
|
|
916
|
-
task.
|
|
917
|
-
|
|
918
|
-
|
|
919
|
-
|
|
920
|
-
|
|
921
|
-
|
|
922
|
-
|
|
949
|
+
self._running = True
|
|
950
|
+
try:
|
|
951
|
+
while not root.done():
|
|
952
|
+
if not self._ready:
|
|
953
|
+
self._wake_due_timers()
|
|
954
|
+
if not self._ready:
|
|
955
|
+
self._wait_for_resources()
|
|
956
|
+
task = self._ready.pop(0)
|
|
957
|
+
if isinstance(task, Handle):
|
|
958
|
+
task._run()
|
|
959
|
+
continue
|
|
960
|
+
if task._done:
|
|
961
|
+
continue
|
|
962
|
+
task._started = True
|
|
963
|
+
self._current = task
|
|
964
|
+
status, value = _step(task._coroutine, task._send_value)
|
|
965
|
+
self._current = None
|
|
966
|
+
task._send_value = None
|
|
967
|
+
if status == 1:
|
|
968
|
+
self._finish(task, value)
|
|
969
|
+
elif status == 2:
|
|
970
|
+
self._fail(task, value)
|
|
971
|
+
elif task._must_cancel:
|
|
972
|
+
task._must_cancel = False
|
|
973
|
+
self._schedule_failure(task, CancelledError())
|
|
974
|
+
else:
|
|
975
|
+
self._dispatch_yield(task, value)
|
|
976
|
+
return root.result()
|
|
977
|
+
finally:
|
|
923
978
|
self._current = None
|
|
924
|
-
|
|
925
|
-
|
|
926
|
-
|
|
927
|
-
|
|
928
|
-
|
|
929
|
-
|
|
930
|
-
|
|
931
|
-
|
|
979
|
+
self._running = False
|
|
980
|
+
|
|
981
|
+
def run_until_complete(self, awaitable):
|
|
982
|
+
async def wait_for_awaitable():
|
|
983
|
+
return await awaitable
|
|
984
|
+
|
|
985
|
+
return self.run(wait_for_awaitable())
|
|
986
|
+
|
|
987
|
+
def is_running(self):
|
|
988
|
+
return self._running
|
|
989
|
+
|
|
990
|
+
def is_closed(self):
|
|
991
|
+
return self._closed
|
|
992
|
+
|
|
993
|
+
async def shutdown_asyncgens(self):
|
|
994
|
+
return None
|
|
995
|
+
|
|
996
|
+
async def shutdown_default_executor(self, timeout=None):
|
|
997
|
+
return None
|
|
998
|
+
|
|
999
|
+
def _shutdown(self):
|
|
1000
|
+
pending = [task for task in self._tasks if not task.done()]
|
|
1001
|
+
if not pending:
|
|
1002
|
+
return
|
|
1003
|
+
for task in pending:
|
|
1004
|
+
task.cancel()
|
|
1005
|
+
|
|
1006
|
+
async def wait_for_pending():
|
|
1007
|
+
await gather(*pending, return_exceptions=True)
|
|
1008
|
+
|
|
1009
|
+
self.run(wait_for_pending())
|
|
1010
|
+
|
|
1011
|
+
def close(self):
|
|
1012
|
+
if self._running:
|
|
1013
|
+
raise RuntimeError("Cannot close a running event loop")
|
|
1014
|
+
if self._closed:
|
|
1015
|
+
return
|
|
1016
|
+
self._closed = True
|
|
1017
|
+
self._ready = []
|
|
1018
|
+
self._timers = []
|
|
1019
|
+
self._resource_waiters = []
|
|
1020
|
+
self._tasks = []
|
|
932
1021
|
|
|
933
1022
|
|
|
934
1023
|
def get_running_loop():
|
|
@@ -978,17 +1067,50 @@ async def sleep(delay, result=None):
|
|
|
978
1067
|
return result
|
|
979
1068
|
|
|
980
1069
|
|
|
981
|
-
|
|
1070
|
+
def gather(*coroutines, return_exceptions=False):
|
|
982
1071
|
tasks = [_ensure_task(coroutine) for coroutine in coroutines]
|
|
983
|
-
|
|
1072
|
+
observed = []
|
|
984
1073
|
for task in tasks:
|
|
985
|
-
|
|
986
|
-
|
|
987
|
-
|
|
1074
|
+
if task not in observed:
|
|
1075
|
+
observed.append(task)
|
|
1076
|
+
loop = get_running_loop()
|
|
1077
|
+
outer = _GatheringFuture(observed, loop=loop)
|
|
1078
|
+
if not tasks:
|
|
1079
|
+
outer.set_result([])
|
|
1080
|
+
return outer
|
|
1081
|
+
|
|
1082
|
+
results = [None for task in tasks]
|
|
1083
|
+
completed = [False for task in tasks]
|
|
1084
|
+
|
|
1085
|
+
def child_completed(child):
|
|
1086
|
+
if outer.done():
|
|
1087
|
+
return
|
|
1088
|
+
if outer._cancel_requested:
|
|
1089
|
+
if all(task.done() for task in observed):
|
|
1090
|
+
outer.set_exception(CancelledError())
|
|
1091
|
+
return
|
|
1092
|
+
if child.cancelled():
|
|
1093
|
+
if not return_exceptions:
|
|
1094
|
+
outer.set_exception(CancelledError())
|
|
1095
|
+
return
|
|
1096
|
+
result = CancelledError()
|
|
1097
|
+
elif child.exception() is not None:
|
|
988
1098
|
if not return_exceptions:
|
|
989
|
-
|
|
990
|
-
|
|
991
|
-
|
|
1099
|
+
outer.set_exception(child.exception())
|
|
1100
|
+
return
|
|
1101
|
+
result = child.exception()
|
|
1102
|
+
else:
|
|
1103
|
+
result = child.result()
|
|
1104
|
+
for index in range(len(tasks)):
|
|
1105
|
+
if tasks[index] is child:
|
|
1106
|
+
completed[index] = True
|
|
1107
|
+
results[index] = result
|
|
1108
|
+
if all(completed):
|
|
1109
|
+
outer.set_result(results)
|
|
1110
|
+
|
|
1111
|
+
for task in observed:
|
|
1112
|
+
task.add_done_callback(child_completed)
|
|
1113
|
+
return outer
|
|
992
1114
|
|
|
993
1115
|
|
|
994
1116
|
async def wait_for(awaitable, timeout):
|
|
@@ -1147,8 +1269,24 @@ def as_completed(awaitables, timeout=None):
|
|
|
1147
1269
|
yield next_result()
|
|
1148
1270
|
|
|
1149
1271
|
|
|
1150
|
-
|
|
1151
|
-
|
|
1272
|
+
def shield(awaitable):
|
|
1273
|
+
inner = _ensure_task(awaitable)
|
|
1274
|
+
if inner.done():
|
|
1275
|
+
return inner
|
|
1276
|
+
outer = get_running_loop().create_future()
|
|
1277
|
+
|
|
1278
|
+
def inner_completed(completed):
|
|
1279
|
+
if outer.done():
|
|
1280
|
+
return
|
|
1281
|
+
if completed.cancelled():
|
|
1282
|
+
outer.cancel()
|
|
1283
|
+
elif completed.exception() is not None:
|
|
1284
|
+
outer.set_exception(completed.exception())
|
|
1285
|
+
else:
|
|
1286
|
+
outer.set_result(completed.result())
|
|
1287
|
+
|
|
1288
|
+
inner.add_done_callback(inner_completed)
|
|
1289
|
+
return outer
|
|
1152
1290
|
|
|
1153
1291
|
|
|
1154
1292
|
async def create_subprocess_exec(program, *args, stdin=None, stdout=None, stderr=None,
|
|
@@ -1193,4 +1331,10 @@ def run(coroutine):
|
|
|
1193
1331
|
try:
|
|
1194
1332
|
return loop.run(coroutine)
|
|
1195
1333
|
finally:
|
|
1196
|
-
|
|
1334
|
+
try:
|
|
1335
|
+
loop._shutdown()
|
|
1336
|
+
loop.run(loop.shutdown_asyncgens())
|
|
1337
|
+
loop.run(loop.shutdown_default_executor())
|
|
1338
|
+
finally:
|
|
1339
|
+
loop.close()
|
|
1340
|
+
_running_loop = None
|
|
@@ -274,28 +274,38 @@ impl Vm<'_> {
|
|
|
274
274
|
if self.call_depth >= MAX_GENERATOR_DEPTH {
|
|
275
275
|
return Err("maximum recursion depth exceeded".into());
|
|
276
276
|
}
|
|
277
|
-
let (
|
|
278
|
-
|
|
279
|
-
|
|
280
|
-
|
|
281
|
-
|
|
282
|
-
|
|
283
|
-
|
|
284
|
-
|
|
285
|
-
|
|
286
|
-
|
|
287
|
-
|
|
288
|
-
|
|
289
|
-
|
|
290
|
-
|
|
291
|
-
|
|
292
|
-
|
|
293
|
-
|
|
294
|
-
|
|
295
|
-
|
|
296
|
-
|
|
297
|
-
|
|
298
|
-
|
|
277
|
+
let (
|
|
278
|
+
code,
|
|
279
|
+
scope,
|
|
280
|
+
instruction_pointer,
|
|
281
|
+
mut handlers,
|
|
282
|
+
exceptions,
|
|
283
|
+
frame_stack,
|
|
284
|
+
exhausted,
|
|
285
|
+
running,
|
|
286
|
+
) = match self.state.heap.get(id)?.clone() {
|
|
287
|
+
Object::Generator {
|
|
288
|
+
code,
|
|
289
|
+
scope,
|
|
290
|
+
instruction_pointer,
|
|
291
|
+
handlers,
|
|
292
|
+
exceptions,
|
|
293
|
+
stack,
|
|
294
|
+
exhausted,
|
|
295
|
+
running,
|
|
296
|
+
..
|
|
297
|
+
} => (
|
|
298
|
+
code,
|
|
299
|
+
scope,
|
|
300
|
+
instruction_pointer,
|
|
301
|
+
handlers,
|
|
302
|
+
exceptions,
|
|
303
|
+
stack,
|
|
304
|
+
exhausted,
|
|
305
|
+
running,
|
|
306
|
+
),
|
|
307
|
+
_ => return Err("object is not a generator".into()),
|
|
308
|
+
};
|
|
299
309
|
if exhausted {
|
|
300
310
|
return Ok(None);
|
|
301
311
|
}
|
|
@@ -313,11 +323,20 @@ impl Vm<'_> {
|
|
|
313
323
|
if instruction_pointer != 0 {
|
|
314
324
|
self.stack.push(sent);
|
|
315
325
|
}
|
|
326
|
+
let generator_exceptions = exceptions
|
|
327
|
+
.into_iter()
|
|
328
|
+
.map(|(kind, value)| super::RaisedException { kind, value })
|
|
329
|
+
.collect();
|
|
330
|
+
let outer_exceptions = std::mem::replace(&mut self.exception_stack, generator_exceptions);
|
|
316
331
|
self.local_scopes.push(scope);
|
|
317
332
|
self.call_depth += 1;
|
|
318
333
|
let result = self.execute_code_from(&code, instruction_pointer, &mut handlers, 0);
|
|
319
334
|
self.call_depth -= 1;
|
|
320
335
|
self.local_scopes.pop();
|
|
336
|
+
let generator_exceptions = std::mem::replace(&mut self.exception_stack, outer_exceptions)
|
|
337
|
+
.into_iter()
|
|
338
|
+
.map(|exception| (exception.kind, exception.value))
|
|
339
|
+
.collect();
|
|
321
340
|
let frame_result_stack = std::mem::take(&mut self.stack);
|
|
322
341
|
self.stack = outer_stack;
|
|
323
342
|
|
|
@@ -328,6 +347,7 @@ impl Vm<'_> {
|
|
|
328
347
|
if let Object::Generator {
|
|
329
348
|
instruction_pointer,
|
|
330
349
|
handlers: saved_handlers,
|
|
350
|
+
exceptions: saved_exceptions,
|
|
331
351
|
stack: saved_stack,
|
|
332
352
|
running,
|
|
333
353
|
..
|
|
@@ -335,6 +355,7 @@ impl Vm<'_> {
|
|
|
335
355
|
{
|
|
336
356
|
*instruction_pointer = next_instruction;
|
|
337
357
|
*saved_handlers = handlers;
|
|
358
|
+
*saved_exceptions = generator_exceptions;
|
|
338
359
|
*saved_stack = frame_result_stack;
|
|
339
360
|
*running = false;
|
|
340
361
|
}
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|