Spaces:
Running
Running
Download demo/execution.py from ejschwartz/decompile-verify: direct link, hf CLI and curl.
- Browser
- Download file 2.67 kB
-
https://huggingface.co/spaces/ejschwartz/decompile-verify/resolve/main/demo/execution.py
- Command line
-
hf download hf://spaces/ejschwartz/decompile-verify/demo/execution.py
-
curl -L -o execution.py https://huggingface.co/spaces/ejschwartz/decompile-verify/resolve/main/demo/execution.py
2.67 kB
| """Run verification in an interruptible process.""" | |
| from contextlib import closing | |
| import multiprocessing | |
| import os | |
| import signal | |
| import tempfile | |
| def _verify_worker(task, connection, directory, recipe=None): | |
| # Compilers inherit this group so cancellation also stops child processes. | |
| os.setsid() | |
| tempfile.tempdir = directory | |
| from verifier import replay, verify | |
| try: | |
| if recipe is not None: | |
| connection.send(("report", replay(task, recipe))) | |
| else: | |
| with closing(verify(task, stream=True)) as reports: | |
| for report in reports: | |
| connection.send(("report", report)) | |
| connection.send(("done", None)) | |
| except Exception as error: | |
| connection.send(("error", str(error))) | |
| finally: | |
| connection.close() | |
| def verification_reports(task, *, cancelled=None, recipe=None, _worker=_verify_worker): | |
| """Stream results until completion or cancellation.""" | |
| if cancelled is not None and cancelled.is_set(): | |
| return | |
| context = multiprocessing.get_context("spawn") | |
| receiver, sender = context.Pipe(duplex=False) | |
| with tempfile.TemporaryDirectory(prefix="verify-request-") as directory: | |
| args = (task, sender, directory) if recipe is None else (task, sender, directory, recipe) | |
| process = context.Process(target=_worker, args=args) | |
| started = False | |
| try: | |
| process.start() | |
| started = True | |
| sender.close() | |
| while True: | |
| if cancelled is not None and cancelled.is_set(): | |
| return | |
| # Poll briefly so cancellation can stop a blocked worker. | |
| if not receiver.poll(0.1): | |
| continue | |
| if cancelled is not None and cancelled.is_set(): | |
| return | |
| try: | |
| kind, value = receiver.recv() | |
| except EOFError as error: | |
| raise ValueError("Verification worker exited without a result") from error | |
| if kind == "done": | |
| return | |
| if kind == "error": | |
| raise ValueError(value) | |
| yield value | |
| finally: | |
| sender.close() | |
| receiver.close() | |
| if started: | |
| # Kill the group even when the worker has exited but a child remains. | |
| try: | |
| os.killpg(process.pid, signal.SIGKILL) | |
| except ProcessLookupError: | |
| if process.is_alive(): | |
| process.kill() | |
| process.join() | |
| process.close() | |