shrinkray 25.12.26.2__py3-none-any.whl → 25.12.27.0__py3-none-any.whl
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.
- shrinkray/__main__.py +14 -14
- shrinkray/passes/sat.py +6 -6
- shrinkray/reducer.py +6 -2
- shrinkray/state.py +10 -10
- shrinkray/subprocess/client.py +2 -2
- shrinkray/subprocess/worker.py +32 -23
- shrinkray/tui.py +25 -15
- shrinkray/work.py +11 -8
- {shrinkray-25.12.26.2.dist-info → shrinkray-25.12.27.0.dist-info}/METADATA +1 -1
- {shrinkray-25.12.26.2.dist-info → shrinkray-25.12.27.0.dist-info}/RECORD +14 -14
- {shrinkray-25.12.26.2.dist-info → shrinkray-25.12.27.0.dist-info}/WHEEL +0 -0
- {shrinkray-25.12.26.2.dist-info → shrinkray-25.12.27.0.dist-info}/entry_points.txt +0 -0
- {shrinkray-25.12.26.2.dist-info → shrinkray-25.12.27.0.dist-info}/licenses/LICENSE +0 -0
- {shrinkray-25.12.26.2.dist-info → shrinkray-25.12.27.0.dist-info}/top_level.txt +0 -0
shrinkray/__main__.py
CHANGED
|
@@ -271,20 +271,20 @@ def main(
|
|
|
271
271
|
if not backup:
|
|
272
272
|
backup = filename + os.extsep + "bak"
|
|
273
273
|
|
|
274
|
-
state_kwargs: dict[str, Any] =
|
|
275
|
-
input_type
|
|
276
|
-
in_place
|
|
277
|
-
test
|
|
278
|
-
timeout
|
|
279
|
-
base
|
|
280
|
-
parallelism
|
|
281
|
-
filename
|
|
282
|
-
formatter
|
|
283
|
-
trivial_is_error
|
|
284
|
-
seed
|
|
285
|
-
volume
|
|
286
|
-
clang_delta_executable
|
|
287
|
-
|
|
274
|
+
state_kwargs: dict[str, Any] = {
|
|
275
|
+
"input_type": input_type,
|
|
276
|
+
"in_place": in_place,
|
|
277
|
+
"test": test,
|
|
278
|
+
"timeout": timeout,
|
|
279
|
+
"base": os.path.basename(filename),
|
|
280
|
+
"parallelism": parallelism,
|
|
281
|
+
"filename": filename,
|
|
282
|
+
"formatter": formatter,
|
|
283
|
+
"trivial_is_error": trivial_is_error,
|
|
284
|
+
"seed": seed,
|
|
285
|
+
"volume": volume,
|
|
286
|
+
"clang_delta_executable": clang_delta_executable,
|
|
287
|
+
}
|
|
288
288
|
|
|
289
289
|
state: ShrinkRayState[Any]
|
|
290
290
|
ui: ShrinkRayUI[Any]
|
shrinkray/passes/sat.py
CHANGED
|
@@ -165,14 +165,14 @@ async def renumber_variables(problem: ReductionProblem[SAT]) -> None:
|
|
|
165
165
|
result: SAT = []
|
|
166
166
|
for clause in sat:
|
|
167
167
|
new_clause: Clause = sorted(
|
|
168
|
-
|
|
169
|
-
|
|
168
|
+
{
|
|
169
|
+
(
|
|
170
170
|
(renumbering[lit] if lit > 0 else -renumbering[-lit])
|
|
171
171
|
if abs(lit) in renumbering
|
|
172
172
|
else lit
|
|
173
|
-
|
|
174
|
-
|
|
175
|
-
|
|
173
|
+
)
|
|
174
|
+
for lit in clause
|
|
175
|
+
}
|
|
176
176
|
)
|
|
177
177
|
if len(set(map(abs, new_clause))) == len(new_clause):
|
|
178
178
|
result.append(new_clause)
|
|
@@ -290,7 +290,7 @@ class BooleanEquivalence(UnionFind[int]):
|
|
|
290
290
|
|
|
291
291
|
def find(self, value: int) -> int:
|
|
292
292
|
if not value:
|
|
293
|
-
raise ValueError("Invalid variable
|
|
293
|
+
raise ValueError(f"Invalid variable {value!r}")
|
|
294
294
|
return super().find(value)
|
|
295
295
|
|
|
296
296
|
def merge(self, left: int, right: int) -> None:
|
shrinkray/reducer.py
CHANGED
|
@@ -59,7 +59,9 @@ class Reducer[T](ABC):
|
|
|
59
59
|
# Optional pass statistics tracking (implemented by ShrinkRay)
|
|
60
60
|
pass_stats: "PassStatsTracker | None" = attrs.field(default=None, init=False)
|
|
61
61
|
# Optional current pass tracking (implemented by ShrinkRay)
|
|
62
|
-
current_reduction_pass: "ReductionPass[T] | None" = attrs.field(
|
|
62
|
+
current_reduction_pass: "ReductionPass[T] | None" = attrs.field(
|
|
63
|
+
default=None, init=False
|
|
64
|
+
)
|
|
63
65
|
|
|
64
66
|
@contextmanager
|
|
65
67
|
def backtrack(self, restart: T) -> Generator[None, None, None]:
|
|
@@ -192,7 +194,9 @@ class ShrinkRay(Reducer[bytes]):
|
|
|
192
194
|
# Pass control: disabled passes and skip functionality
|
|
193
195
|
disabled_passes: set[str] = attrs.Factory(set)
|
|
194
196
|
_skip_requested: bool = attrs.field(default=False, init=False)
|
|
195
|
-
_current_pass_scope: "trio.CancelScope | None" = attrs.field(
|
|
197
|
+
_current_pass_scope: "trio.CancelScope | None" = attrs.field(
|
|
198
|
+
default=None, init=False
|
|
199
|
+
)
|
|
196
200
|
_passes_were_skipped: bool = attrs.field(default=False, init=False)
|
|
197
201
|
|
|
198
202
|
def disable_pass(self, pass_name: str) -> None:
|
shrinkray/state.py
CHANGED
|
@@ -105,12 +105,12 @@ class ShrinkRayState[TestCase](ABC):
|
|
|
105
105
|
else:
|
|
106
106
|
command = self.test
|
|
107
107
|
|
|
108
|
-
kwargs: dict[str, Any] =
|
|
109
|
-
universal_newlines
|
|
110
|
-
preexec_fn
|
|
111
|
-
cwd
|
|
112
|
-
check
|
|
113
|
-
|
|
108
|
+
kwargs: dict[str, Any] = {
|
|
109
|
+
"universal_newlines": False,
|
|
110
|
+
"preexec_fn": os.setsid,
|
|
111
|
+
"cwd": cwd,
|
|
112
|
+
"check": False,
|
|
113
|
+
}
|
|
114
114
|
if self.input_type.enabled(self._InputType.stdin) and not os.path.isdir(
|
|
115
115
|
working
|
|
116
116
|
):
|
|
@@ -562,10 +562,10 @@ class ShrinkRayDirectoryState(ShrinkRayState[dict[str, bytes]]):
|
|
|
562
562
|
sorted((k, shortlex(v)) for k, v in test_case.items()),
|
|
563
563
|
)
|
|
564
564
|
|
|
565
|
-
return
|
|
566
|
-
sort_key
|
|
567
|
-
size
|
|
568
|
-
|
|
565
|
+
return {
|
|
566
|
+
"sort_key": dict_sort_key,
|
|
567
|
+
"size": dict_size,
|
|
568
|
+
}
|
|
569
569
|
|
|
570
570
|
def new_reducer(
|
|
571
571
|
self, problem: ReductionProblem[dict[str, bytes]]
|
shrinkray/subprocess/client.py
CHANGED
|
@@ -4,7 +4,7 @@ import asyncio
|
|
|
4
4
|
import sys
|
|
5
5
|
import traceback
|
|
6
6
|
import uuid
|
|
7
|
-
from collections.abc import
|
|
7
|
+
from collections.abc import AsyncGenerator
|
|
8
8
|
from typing import Any
|
|
9
9
|
|
|
10
10
|
from shrinkray.subprocess.protocol import (
|
|
@@ -200,7 +200,7 @@ class SubprocessClient:
|
|
|
200
200
|
traceback.print_exc()
|
|
201
201
|
return Response(id="", error="Failed to skip pass")
|
|
202
202
|
|
|
203
|
-
async def get_progress_updates(self) ->
|
|
203
|
+
async def get_progress_updates(self) -> AsyncGenerator[ProgressUpdate, None]:
|
|
204
204
|
"""Yield progress updates as they arrive."""
|
|
205
205
|
while not self._completed:
|
|
206
206
|
try:
|
shrinkray/subprocess/worker.py
CHANGED
|
@@ -4,6 +4,7 @@ import os
|
|
|
4
4
|
import sys
|
|
5
5
|
import time
|
|
6
6
|
import traceback
|
|
7
|
+
from contextlib import aclosing
|
|
7
8
|
from typing import Any, Protocol
|
|
8
9
|
|
|
9
10
|
import trio
|
|
@@ -25,6 +26,7 @@ class InputStream(Protocol):
|
|
|
25
26
|
|
|
26
27
|
def __aiter__(self) -> "InputStream": ...
|
|
27
28
|
async def __anext__(self) -> bytes | bytearray: ...
|
|
29
|
+
async def aclose(self) -> None: ...
|
|
28
30
|
|
|
29
31
|
|
|
30
32
|
class OutputStream(Protocol):
|
|
@@ -88,12 +90,13 @@ class ReducerWorker:
|
|
|
88
90
|
stream = trio.lowlevel.FdStream(os.dup(sys.stdin.fileno()))
|
|
89
91
|
|
|
90
92
|
buffer = b""
|
|
91
|
-
async
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
93
|
+
async with aclosing(stream) as aiter:
|
|
94
|
+
async for chunk in aiter:
|
|
95
|
+
buffer += chunk
|
|
96
|
+
while b"\n" in buffer:
|
|
97
|
+
line, buffer = buffer.split(b"\n", 1)
|
|
98
|
+
if line:
|
|
99
|
+
await self.handle_line(line.decode("utf-8"))
|
|
97
100
|
|
|
98
101
|
async def handle_line(self, line: str) -> None:
|
|
99
102
|
"""Handle a single command line."""
|
|
@@ -124,7 +127,9 @@ class ReducerWorker:
|
|
|
124
127
|
case "skip_pass":
|
|
125
128
|
return self._handle_skip_pass(request.id)
|
|
126
129
|
case _:
|
|
127
|
-
return Response(
|
|
130
|
+
return Response(
|
|
131
|
+
id=request.id, error=f"Unknown command: {request.command}"
|
|
132
|
+
)
|
|
128
133
|
|
|
129
134
|
async def _handle_start(self, request_id: str, params: dict) -> Response:
|
|
130
135
|
"""Start the reduction process."""
|
|
@@ -181,20 +186,20 @@ class ReducerWorker:
|
|
|
181
186
|
if clang_delta_path:
|
|
182
187
|
clang_delta_executable = ClangDelta(clang_delta_path)
|
|
183
188
|
|
|
184
|
-
state_kwargs: dict[str, Any] =
|
|
185
|
-
input_type
|
|
186
|
-
in_place
|
|
187
|
-
test
|
|
188
|
-
timeout
|
|
189
|
-
base
|
|
190
|
-
parallelism
|
|
191
|
-
filename
|
|
192
|
-
formatter
|
|
193
|
-
trivial_is_error
|
|
194
|
-
seed
|
|
195
|
-
volume
|
|
196
|
-
clang_delta_executable
|
|
197
|
-
|
|
189
|
+
state_kwargs: dict[str, Any] = {
|
|
190
|
+
"input_type": input_type,
|
|
191
|
+
"in_place": in_place,
|
|
192
|
+
"test": test,
|
|
193
|
+
"timeout": timeout,
|
|
194
|
+
"base": os.path.basename(filename),
|
|
195
|
+
"parallelism": parallelism,
|
|
196
|
+
"filename": filename,
|
|
197
|
+
"formatter": formatter,
|
|
198
|
+
"trivial_is_error": trivial_is_error,
|
|
199
|
+
"seed": seed,
|
|
200
|
+
"volume": volume,
|
|
201
|
+
"clang_delta_executable": clang_delta_executable,
|
|
202
|
+
}
|
|
198
203
|
|
|
199
204
|
if os.path.isdir(filename):
|
|
200
205
|
files = [os.path.join(d, f) for d, _, fs in os.walk(filename) for f in fs]
|
|
@@ -263,7 +268,9 @@ class ReducerWorker:
|
|
|
263
268
|
|
|
264
269
|
if self.reducer is not None and hasattr(self.reducer, "disable_pass"):
|
|
265
270
|
self.reducer.disable_pass(pass_name)
|
|
266
|
-
return Response(
|
|
271
|
+
return Response(
|
|
272
|
+
id=request_id, result={"status": "disabled", "pass_name": pass_name}
|
|
273
|
+
)
|
|
267
274
|
return Response(id=request_id, error="Reducer does not support pass control")
|
|
268
275
|
|
|
269
276
|
def _handle_enable_pass(self, request_id: str, params: dict) -> Response:
|
|
@@ -281,7 +288,9 @@ class ReducerWorker:
|
|
|
281
288
|
|
|
282
289
|
if self.reducer is not None and hasattr(self.reducer, "enable_pass"):
|
|
283
290
|
self.reducer.enable_pass(pass_name)
|
|
284
|
-
return Response(
|
|
291
|
+
return Response(
|
|
292
|
+
id=request_id, result={"status": "enabled", "pass_name": pass_name}
|
|
293
|
+
)
|
|
285
294
|
return Response(id=request_id, error="Reducer does not support pass control")
|
|
286
295
|
|
|
287
296
|
def _handle_skip_pass(self, request_id: str) -> Response:
|
shrinkray/tui.py
CHANGED
|
@@ -1,7 +1,9 @@
|
|
|
1
1
|
"""Textual-based TUI for Shrink Ray."""
|
|
2
2
|
|
|
3
3
|
import os
|
|
4
|
-
|
|
4
|
+
import traceback
|
|
5
|
+
from collections.abc import AsyncGenerator
|
|
6
|
+
from contextlib import aclosing
|
|
5
7
|
from datetime import timedelta
|
|
6
8
|
from typing import Literal, Protocol
|
|
7
9
|
|
|
@@ -114,7 +116,7 @@ class ReductionClientProtocol(Protocol):
|
|
|
114
116
|
|
|
115
117
|
@property
|
|
116
118
|
def error_message(self) -> str | None: ...
|
|
117
|
-
def get_progress_updates(self) ->
|
|
119
|
+
def get_progress_updates(self) -> AsyncGenerator[ProgressUpdate, None]: ...
|
|
118
120
|
@property
|
|
119
121
|
def is_completed(self) -> bool: ...
|
|
120
122
|
|
|
@@ -485,7 +487,9 @@ class PassStatsScreen(ModalScreen[None]):
|
|
|
485
487
|
reductions = str(ps.successful_reductions)
|
|
486
488
|
success = f"{ps.success_rate:.1f}%"
|
|
487
489
|
|
|
488
|
-
table.add_row(
|
|
490
|
+
table.add_row(
|
|
491
|
+
checkbox, name, runs, bytes_del, tests, reductions, success
|
|
492
|
+
)
|
|
489
493
|
|
|
490
494
|
# Restore cursor and scroll position after rebuilding
|
|
491
495
|
# Only restore if the saved position is still valid
|
|
@@ -510,7 +514,9 @@ class PassStatsScreen(ModalScreen[None]):
|
|
|
510
514
|
# Update footer with disabled count
|
|
511
515
|
disabled_count = len(self.disabled_passes)
|
|
512
516
|
if disabled_count > 0:
|
|
513
|
-
footer_text =
|
|
517
|
+
footer_text = (
|
|
518
|
+
f"Showing {len(self.pass_stats)} passes ({disabled_count} disabled)"
|
|
519
|
+
)
|
|
514
520
|
else:
|
|
515
521
|
footer_text = f"Showing {len(self.pass_stats)} passes in run order"
|
|
516
522
|
footer = self.query_one("#stats-footer", Static)
|
|
@@ -713,18 +719,21 @@ class ShrinkRayApp(App[None]):
|
|
|
713
719
|
stats_display = self.query_one("#stats-display", StatsDisplay)
|
|
714
720
|
content_preview = self.query_one("#content-preview", ContentPreview)
|
|
715
721
|
|
|
716
|
-
async
|
|
717
|
-
|
|
718
|
-
|
|
719
|
-
|
|
720
|
-
|
|
721
|
-
|
|
722
|
+
async with aclosing(self._client.get_progress_updates()) as updates:
|
|
723
|
+
async for update in updates:
|
|
724
|
+
stats_display.update_stats(update)
|
|
725
|
+
content_preview.update_content(
|
|
726
|
+
update.content_preview, update.hex_mode
|
|
727
|
+
)
|
|
728
|
+
self._latest_pass_stats = update.pass_stats
|
|
729
|
+
self._current_pass_name = update.current_pass_name
|
|
730
|
+
self._disabled_passes = update.disabled_passes
|
|
722
731
|
|
|
723
|
-
|
|
724
|
-
|
|
732
|
+
# Check if all passes are disabled
|
|
733
|
+
self._check_all_passes_disabled()
|
|
725
734
|
|
|
726
|
-
|
|
727
|
-
|
|
735
|
+
if self._client.is_completed:
|
|
736
|
+
break
|
|
728
737
|
|
|
729
738
|
self._completed = True
|
|
730
739
|
|
|
@@ -739,6 +748,7 @@ class ShrinkRayApp(App[None]):
|
|
|
739
748
|
self.update_status("Reduction completed! Press 'q' to exit.")
|
|
740
749
|
|
|
741
750
|
except Exception as e:
|
|
751
|
+
traceback.print_exc()
|
|
742
752
|
self.exit(return_code=1, message=f"Error: {e}")
|
|
743
753
|
finally:
|
|
744
754
|
if self._owns_client and self._client:
|
|
@@ -750,7 +760,7 @@ class ShrinkRayApp(App[None]):
|
|
|
750
760
|
all_pass_names = {ps.pass_name for ps in self._latest_pass_stats}
|
|
751
761
|
if all_pass_names and all_pass_names <= set(self._disabled_passes):
|
|
752
762
|
self.update_status(
|
|
753
|
-
"Reduction paused (all passes disabled) -
|
|
763
|
+
"Reduction paused (all passes disabled) - [p] to re-enable passes"
|
|
754
764
|
)
|
|
755
765
|
|
|
756
766
|
def update_status(self, message: str) -> None:
|
shrinkray/work.py
CHANGED
|
@@ -13,7 +13,7 @@ Key concepts:
|
|
|
13
13
|
|
|
14
14
|
import heapq
|
|
15
15
|
from collections.abc import Awaitable, Callable, Sequence
|
|
16
|
-
from contextlib import asynccontextmanager
|
|
16
|
+
from contextlib import aclosing, asynccontextmanager
|
|
17
17
|
from enum import IntEnum
|
|
18
18
|
from itertools import islice
|
|
19
19
|
from random import Random
|
|
@@ -100,8 +100,9 @@ class WorkContext:
|
|
|
100
100
|
async with parallel_map(
|
|
101
101
|
values, f, parallelism=min(self.parallelism, n)
|
|
102
102
|
) as result:
|
|
103
|
-
async
|
|
104
|
-
|
|
103
|
+
async with aclosing(result) as aiter:
|
|
104
|
+
async for v in aiter:
|
|
105
|
+
await send.send(v)
|
|
105
106
|
|
|
106
107
|
n *= 2
|
|
107
108
|
else:
|
|
@@ -122,9 +123,10 @@ class WorkContext:
|
|
|
122
123
|
@nursery.start_soon
|
|
123
124
|
async def _():
|
|
124
125
|
async with self.map(ls, apply) as results:
|
|
125
|
-
async
|
|
126
|
-
|
|
127
|
-
|
|
126
|
+
async with aclosing(results) as aiter:
|
|
127
|
+
async for x, v in aiter:
|
|
128
|
+
if v:
|
|
129
|
+
await send.send(x)
|
|
128
130
|
send.close()
|
|
129
131
|
|
|
130
132
|
yield receive
|
|
@@ -139,8 +141,9 @@ class WorkContext:
|
|
|
139
141
|
Will run in parallel if parallelism is enabled.
|
|
140
142
|
"""
|
|
141
143
|
async with self.filter(ls, f) as filtered:
|
|
142
|
-
async
|
|
143
|
-
|
|
144
|
+
async with aclosing(filtered) as aiter:
|
|
145
|
+
async for x in aiter:
|
|
146
|
+
return x
|
|
144
147
|
raise NotFound()
|
|
145
148
|
|
|
146
149
|
async def find_large_integer(self, f: Callable[[int], Awaitable[bool]]) -> int:
|
|
@@ -1,16 +1,16 @@
|
|
|
1
1
|
shrinkray/__init__.py,sha256=b5MvcvhsEGYya3GRXNbCJAlAL5IZHSsETLK_vtfmXRY,18
|
|
2
|
-
shrinkray/__main__.py,sha256=
|
|
2
|
+
shrinkray/__main__.py,sha256=AL1WNfohkA5Uu7uiCQRhNjzfUc4qKC-UjMTDraPlT8I,10919
|
|
3
3
|
shrinkray/cli.py,sha256=1-qjaIchyCDd-YCdGWtK7q9j9qr6uX6AqtwW8m5QCQg,1697
|
|
4
4
|
shrinkray/display.py,sha256=WYN05uqmUVpZhwi2pxr1U-wLHWZ9KiL0RUlTCBJ1N3E,2430
|
|
5
5
|
shrinkray/formatting.py,sha256=tXCGnhJn-WJGpHMaLHRCAXK8aKJBbrOdiW9QGERrQEk,3121
|
|
6
6
|
shrinkray/problem.py,sha256=Kp7QN10E4tzjdpoqJve8_RT26VpywzQwY0gX2VkBGCo,17277
|
|
7
7
|
shrinkray/process.py,sha256=-eP8h5X0ESbkcTic8FFEzkd4-vwaZ0YI5tLxUR25L8U,1599
|
|
8
8
|
shrinkray/py.typed,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
|
9
|
-
shrinkray/reducer.py,sha256=
|
|
10
|
-
shrinkray/state.py,sha256=
|
|
11
|
-
shrinkray/tui.py,sha256=
|
|
9
|
+
shrinkray/reducer.py,sha256=xhLo_GF7qrIVoiLHed6Wt4nxjdE-9jj_7K9F76un89o,19877
|
|
10
|
+
shrinkray/state.py,sha256=jqAKlirXjKK6smA2G1BnGjjoH7NgVokQhER2Ax18q64,22381
|
|
11
|
+
shrinkray/tui.py,sha256=YiiCDVxGl5g5TlcZN62NMYiD_IqRV68qoRDkNcasvc4,31540
|
|
12
12
|
shrinkray/ui.py,sha256=xuDUwU-MM3AetvwUB7bfzav0P_drUsBrKFPhON_Nr-k,2251
|
|
13
|
-
shrinkray/work.py,sha256=
|
|
13
|
+
shrinkray/work.py,sha256=GEZ14Kk3bvwUxAnACvY-wom2lVWaGrELMNxrDjv03dk,8110
|
|
14
14
|
shrinkray/passes/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
|
15
15
|
shrinkray/passes/bytes.py,sha256=pX2kBeH38SM4j55f8bNF_2PVBCDo6XdUj73EvOFH9f8,23904
|
|
16
16
|
shrinkray/passes/clangdelta.py,sha256=t9EQ_kc159HRs48JwB5JvlJCsiCscrZgf2nhHCZRZX0,8419
|
|
@@ -19,15 +19,15 @@ shrinkray/passes/genericlanguages.py,sha256=qbTuJgUieHqWtf7cly2tm0qdbrVXzVoWcAnF
|
|
|
19
19
|
shrinkray/passes/json.py,sha256=AcmroHgb38Aa3aApwcuYNzmyya_vnCi2RFSVqomiDg8,2586
|
|
20
20
|
shrinkray/passes/patching.py,sha256=1uOTir3IbywKmsg6IIhSnxHFovZTdUCS-8PSwzgza00,8936
|
|
21
21
|
shrinkray/passes/python.py,sha256=3WN1lZTf5oVL8FCTGomhrCuE04wIX9ocKcmFV86NMZA,6875
|
|
22
|
-
shrinkray/passes/sat.py,sha256=
|
|
22
|
+
shrinkray/passes/sat.py,sha256=5Zv4IgGfg3SYplMAAaPLkbBNh4fuVpci4F9GdVacayA,19504
|
|
23
23
|
shrinkray/passes/sequences.py,sha256=jCK1fWBxCz79u7JWSps9wf7Yru7W_FAsJwdgg--CLxU,3040
|
|
24
24
|
shrinkray/subprocess/__init__.py,sha256=FyV2y05uwQ1RTZGwREI0aAVaLX1jiwRcWsdsksFmdbM,451
|
|
25
|
-
shrinkray/subprocess/client.py,sha256=
|
|
25
|
+
shrinkray/subprocess/client.py,sha256=i2CJ7xU8_jklqDl-yphpIv-mwD0gG93jVzEDEtsdWvE,9277
|
|
26
26
|
shrinkray/subprocess/protocol.py,sha256=LuHl0IkKpDzYhAGZz_EiTHNqDNq_v1ozg5aUSl7UzE4,6203
|
|
27
|
-
shrinkray/subprocess/worker.py,sha256=
|
|
28
|
-
shrinkray-25.12.
|
|
29
|
-
shrinkray-25.12.
|
|
30
|
-
shrinkray-25.12.
|
|
31
|
-
shrinkray-25.12.
|
|
32
|
-
shrinkray-25.12.
|
|
33
|
-
shrinkray-25.12.
|
|
27
|
+
shrinkray/subprocess/worker.py,sha256=IyO9FNQ11vWwrc2ikH-Ca3iGoc03MJOIRNUqK3R06aE,19269
|
|
28
|
+
shrinkray-25.12.27.0.dist-info/licenses/LICENSE,sha256=iMKX79AuokJfIZUnGUARdUp30vVAoIPOJ7ek8TY63kk,1072
|
|
29
|
+
shrinkray-25.12.27.0.dist-info/METADATA,sha256=jdpwOHRfJE7bJnBFBbYlpEw7bINLJaU_v2Pz_aBGsmw,9693
|
|
30
|
+
shrinkray-25.12.27.0.dist-info/WHEEL,sha256=_zCd3N1l69ArxyTb8rzEoP9TpbYXkqRFSNOD5OuxnTs,91
|
|
31
|
+
shrinkray-25.12.27.0.dist-info/entry_points.txt,sha256=wIZvnGyOdVeaLTiv2klnSyTe-EKkkwn4SwHh9bmJ7qk,104
|
|
32
|
+
shrinkray-25.12.27.0.dist-info/top_level.txt,sha256=fLif8-rFoFOnf5h8-vs3ECkKNWQopTQh3xvl1s7pchQ,10
|
|
33
|
+
shrinkray-25.12.27.0.dist-info/RECORD,,
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|