fm-weck 1.2.0__py3-none-any.whl → 1.3.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.
- fm_weck/__init__.py +1 -1
- fm_weck/cli.py +47 -4
- fm_weck/config.py +60 -15
- fm_weck/engine.py +36 -14
- fm_weck/exceptions.py +9 -0
- fm_weck/image_mgr.py +4 -2
- fm_weck/resources/BenchExec-3.25-py3-none-any.whl +0 -0
- fm_weck/resources/BenchExec-3.25-py3-none-any.whl.license +3 -0
- fm_weck/resources/__init__.py +2 -0
- fm_weck/resources/fm_tools/2ls.yml +1 -1
- fm_weck/resources/fm_tools/brick.yml +1 -1
- fm_weck/resources/fm_tools/bubaak-split.yml +5 -0
- fm_weck/resources/fm_tools/bubaak.yml +1 -1
- fm_weck/resources/fm_tools/cbmc.yml +5 -0
- fm_weck/resources/fm_tools/coveritest.yml +12 -2
- fm_weck/resources/fm_tools/cpa-witness2test.yml +11 -2
- fm_weck/resources/fm_tools/cpachecker.yml +5 -0
- fm_weck/resources/fm_tools/cpv.yml +8 -1
- fm_weck/resources/fm_tools/cseq.yml +15 -5
- fm_weck/resources/fm_tools/dartagnan.yml +1 -1
- fm_weck/resources/fm_tools/deagle.yml +1 -1
- fm_weck/resources/fm_tools/ebf.yml +1 -1
- fm_weck/resources/fm_tools/esbmc-kind.yml +1 -1
- fm_weck/resources/fm_tools/frama-c-sv.yml +1 -1
- fm_weck/resources/fm_tools/fshell-witness2test.yml +10 -1
- fm_weck/resources/fm_tools/fusebmc-ia.yml +1 -1
- fm_weck/resources/fm_tools/fusebmc.yml +1 -1
- fm_weck/resources/fm_tools/gdart.yml +1 -1
- fm_weck/resources/fm_tools/goblint.yml +1 -1
- fm_weck/resources/fm_tools/gwit.yml +1 -1
- fm_weck/resources/fm_tools/infer.yml +13 -5
- fm_weck/resources/fm_tools/jayhorn.yml +1 -1
- fm_weck/resources/fm_tools/jbmc.yml +1 -1
- fm_weck/resources/fm_tools/key.yml +8 -0
- fm_weck/resources/fm_tools/korn.yml +1 -1
- fm_weck/resources/fm_tools/liv.yml +13 -1
- fm_weck/resources/fm_tools/metaval.yml +14 -1
- fm_weck/resources/fm_tools/mlb.yml +1 -1
- fm_weck/resources/fm_tools/mopsa.yml +1 -1
- fm_weck/resources/fm_tools/pesco.yml +1 -1
- fm_weck/resources/fm_tools/predatorhp.yml +1 -1
- fm_weck/resources/fm_tools/prtest.yml +1 -1
- fm_weck/resources/fm_tools/schema.yml +16 -0
- fm_weck/resources/fm_tools/symbiotic.yml +10 -2
- fm_weck/resources/fm_tools/testcov.yml +1 -1
- fm_weck/resources/fm_tools/theta.yml +1 -1
- fm_weck/resources/fm_tools/tracerx.yml +1 -1
- fm_weck/resources/fm_tools/uautomizer.yml +5 -1
- fm_weck/resources/fm_tools/ugemcutter.yml +1 -1
- fm_weck/resources/fm_tools/ukojak.yml +1 -1
- fm_weck/resources/fm_tools/utaipan.yml +1 -1
- fm_weck/resources/fm_tools/veriabs.yml +2 -2
- fm_weck/resources/fm_tools/veriabsl.yml +2 -2
- fm_weck/resources/fm_tools/verifuzz.yml +1 -1
- fm_weck/resources/run_with_overlay.sh +1 -1
- fm_weck/resources/runexec +16 -0
- fm_weck/runexec_util.py +30 -0
- fm_weck/serve.py +29 -2
- {fm_weck-1.2.0.dist-info → fm_weck-1.3.0.dist-info}/METADATA +1 -1
- {fm_weck-1.2.0.dist-info → fm_weck-1.3.0.dist-info}/RECORD +62 -57
- {fm_weck-1.2.0.dist-info → fm_weck-1.3.0.dist-info}/WHEEL +0 -0
- {fm_weck-1.2.0.dist-info → fm_weck-1.3.0.dist-info}/entry_points.txt +0 -0
fm_weck/__init__.py
CHANGED
fm_weck/cli.py
CHANGED
|
@@ -22,7 +22,7 @@ from fm_weck.resources import iter_fm_data, iter_properties
|
|
|
22
22
|
|
|
23
23
|
from . import __version__
|
|
24
24
|
from .engine import Engine, NoImageError
|
|
25
|
-
from .serve import run_guided, run_manual, setup_fm_tool
|
|
25
|
+
from .serve import run_guided, run_manual, run_runexec, setup_fm_tool
|
|
26
26
|
|
|
27
27
|
logger = logging.getLogger(__name__)
|
|
28
28
|
|
|
@@ -100,6 +100,14 @@ def parse(raw_args: list[str]) -> Tuple[Callable[[], None], Namespace]:
|
|
|
100
100
|
default=False,
|
|
101
101
|
)
|
|
102
102
|
|
|
103
|
+
parser.add_argument(
|
|
104
|
+
"--dry-run",
|
|
105
|
+
action="store_true",
|
|
106
|
+
help="Just print the command that would be executed.",
|
|
107
|
+
required=False,
|
|
108
|
+
default=False,
|
|
109
|
+
)
|
|
110
|
+
|
|
103
111
|
subparsers = parser.add_subparsers()
|
|
104
112
|
|
|
105
113
|
run = subparsers.add_parser("run", aliases=["r"], help="Run a verifier inside a container.")
|
|
@@ -173,6 +181,32 @@ def parse(raw_args: list[str]) -> Tuple[Callable[[], None], Namespace]:
|
|
|
173
181
|
add_tool_arg(install, nargs="+")
|
|
174
182
|
install.set_defaults(main=main_install)
|
|
175
183
|
|
|
184
|
+
runexec = subparsers.add_parser("runexec", help="Run runexec on a command inside a container.")
|
|
185
|
+
runexec.add_argument(
|
|
186
|
+
"--image",
|
|
187
|
+
dest="use_image",
|
|
188
|
+
action="store",
|
|
189
|
+
default=None,
|
|
190
|
+
type=str,
|
|
191
|
+
help=(
|
|
192
|
+
"The image that shall be used for the container."
|
|
193
|
+
" The image is treated as 'full_container_image', i.e., fm-weck will not attempt to install any packages"
|
|
194
|
+
" inside of the image"
|
|
195
|
+
),
|
|
196
|
+
)
|
|
197
|
+
|
|
198
|
+
runexec.add_argument(
|
|
199
|
+
"--benchexec-path",
|
|
200
|
+
action="store",
|
|
201
|
+
dest="benchexec_package",
|
|
202
|
+
type=Path,
|
|
203
|
+
help=("The path to the benchexec .whl or .egg file. If not given, fm-weck will use its own benchexec package."),
|
|
204
|
+
default=None,
|
|
205
|
+
)
|
|
206
|
+
|
|
207
|
+
runexec.add_argument("argument_list", metavar="args", nargs="*", help="Arguments for runexec.")
|
|
208
|
+
runexec.set_defaults(main=main_runexec)
|
|
209
|
+
|
|
176
210
|
def help_callback():
|
|
177
211
|
parser.print_help()
|
|
178
212
|
|
|
@@ -265,6 +299,15 @@ def main_run(args: argparse.Namespace):
|
|
|
265
299
|
)
|
|
266
300
|
|
|
267
301
|
|
|
302
|
+
def main_runexec(args: argparse.Namespace):
|
|
303
|
+
run_runexec(
|
|
304
|
+
benchexec_package=args.benchexec_package,
|
|
305
|
+
use_image=args.use_image,
|
|
306
|
+
configuration=Config(),
|
|
307
|
+
command=args.argument_list,
|
|
308
|
+
)
|
|
309
|
+
|
|
310
|
+
|
|
268
311
|
def main_manual(args: argparse.Namespace):
|
|
269
312
|
if not args.TOOL:
|
|
270
313
|
logger.error("No fm-tool given. Aborting...")
|
|
@@ -360,6 +403,8 @@ def cli(raw_args: list[str]):
|
|
|
360
403
|
help_callback, args = parse(raw_args)
|
|
361
404
|
configuration = Config().load(args.config)
|
|
362
405
|
set_log_level(args.loglevel, configuration)
|
|
406
|
+
if args.dry_run:
|
|
407
|
+
Config().set_dry_run(True)
|
|
363
408
|
|
|
364
409
|
if args.list:
|
|
365
410
|
print("List of fm-tools callable by name:")
|
|
@@ -370,9 +415,7 @@ def cli(raw_args: list[str]):
|
|
|
370
415
|
print(f" - {prop}")
|
|
371
416
|
return
|
|
372
417
|
|
|
373
|
-
|
|
374
|
-
|
|
375
|
-
if not hasattr(args, "TOOL"):
|
|
418
|
+
if not hasattr(args, "main"):
|
|
376
419
|
return help_callback()
|
|
377
420
|
|
|
378
421
|
try:
|
fm_weck/config.py
CHANGED
|
@@ -5,8 +5,11 @@
|
|
|
5
5
|
#
|
|
6
6
|
# SPDX-License-Identifier: Apache-2.0
|
|
7
7
|
|
|
8
|
+
import logging
|
|
8
9
|
import os
|
|
9
10
|
import shutil
|
|
11
|
+
import stat
|
|
12
|
+
import sys
|
|
10
13
|
from functools import cache
|
|
11
14
|
from pathlib import Path
|
|
12
15
|
from typing import Any, Callable, Iterable, Optional, Tuple, TypeVar
|
|
@@ -14,7 +17,7 @@ from typing import Any, Callable, Iterable, Optional, Tuple, TypeVar
|
|
|
14
17
|
import yaml
|
|
15
18
|
from fm_tools.fmdata import FmData
|
|
16
19
|
|
|
17
|
-
from fm_weck.resources import RUN_WITH_OVERLAY
|
|
20
|
+
from fm_weck.resources import RUN_WITH_OVERLAY, RUNEXEC_SCRIPT
|
|
18
21
|
|
|
19
22
|
try:
|
|
20
23
|
import tomllib as toml
|
|
@@ -22,10 +25,10 @@ except ImportError:
|
|
|
22
25
|
import tomli as toml
|
|
23
26
|
|
|
24
27
|
_SEARCH_ORDER: tuple[Path, ...] = (
|
|
25
|
-
Path.cwd() / ".weck",
|
|
26
|
-
Path.home() / ".weck",
|
|
27
|
-
Path.home() / ".config" / "weck",
|
|
28
|
-
Path.home() / ".config" / "weck" / "config.toml",
|
|
28
|
+
Path.cwd() / ".fm-weck",
|
|
29
|
+
Path.home() / ".fm-weck",
|
|
30
|
+
Path.home() / ".config" / "fm-weck",
|
|
31
|
+
Path.home() / ".config" / "fm-weck" / "config.toml",
|
|
29
32
|
)
|
|
30
33
|
BASE_CONFIG = """
|
|
31
34
|
[logging]
|
|
@@ -51,6 +54,7 @@ class Config(object):
|
|
|
51
54
|
if cls._instance is None:
|
|
52
55
|
cls._instance = super(Config, cls).__new__(cls)
|
|
53
56
|
cls._instance._config = None
|
|
57
|
+
cls._instance._dry_run = False
|
|
54
58
|
return cls._instance
|
|
55
59
|
|
|
56
60
|
def load(self, config: Optional[Path] = None) -> dict[str, Any]:
|
|
@@ -88,6 +92,15 @@ class Config(object):
|
|
|
88
92
|
|
|
89
93
|
return default
|
|
90
94
|
|
|
95
|
+
def set_dry_run(self, dry_run: bool) -> None:
|
|
96
|
+
self._dry_run = dry_run
|
|
97
|
+
|
|
98
|
+
def is_dry_run(self) -> bool:
|
|
99
|
+
return self._dry_run
|
|
100
|
+
|
|
101
|
+
def set_default_image(self, image: str) -> None:
|
|
102
|
+
self._config["defaults"]["image"] = image
|
|
103
|
+
|
|
91
104
|
def defaults(self) -> dict[str, Any]:
|
|
92
105
|
return self.get("defaults", {})
|
|
93
106
|
|
|
@@ -114,11 +127,11 @@ class Config(object):
|
|
|
114
127
|
@property
|
|
115
128
|
@_handle_relative_paths
|
|
116
129
|
def cache_location(self) -> Path:
|
|
117
|
-
cache = Path.home() / ".cache" / "weck_cache"
|
|
130
|
+
cache = Path.home() / ".cache" / "fm-weck_cache"
|
|
118
131
|
xdg_cache_home = os.environ.get("XDG_CACHE_HOME")
|
|
119
132
|
|
|
120
133
|
if xdg_cache_home:
|
|
121
|
-
cache = Path(xdg_cache_home) / "weck_cache"
|
|
134
|
+
cache = Path(xdg_cache_home) / "fm-weck_cache"
|
|
122
135
|
|
|
123
136
|
return Path(self.defaults().get("cache_location", cache.resolve()))
|
|
124
137
|
|
|
@@ -144,15 +157,47 @@ class Config(object):
|
|
|
144
157
|
property_name = path.name
|
|
145
158
|
return shelve / property_name
|
|
146
159
|
|
|
147
|
-
def
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
151
|
-
return run_script
|
|
160
|
+
def get_shelve_path_for_benchexec(self) -> Path:
|
|
161
|
+
shelve = self.cache_location / ".lib" / "benchexec.whl"
|
|
162
|
+
shelve.parent.mkdir(parents=True, exist_ok=True)
|
|
163
|
+
return shelve
|
|
152
164
|
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
return
|
|
165
|
+
@staticmethod
|
|
166
|
+
def _system_is_not_posix():
|
|
167
|
+
return not (sys.platform.startswith("linux") or sys.platform == "darwin")
|
|
168
|
+
|
|
169
|
+
def make_runexec_script_available(self) -> Path:
|
|
170
|
+
return self.make_script_available(RUNEXEC_SCRIPT, "runexec")
|
|
171
|
+
|
|
172
|
+
def make_script_available(self, source: Path = RUN_WITH_OVERLAY, target_name: str = "run_with_overlay.sh") -> Path:
|
|
173
|
+
script_dir = self.cache_location / ".scripts"
|
|
174
|
+
target = script_dir / target_name
|
|
175
|
+
if not (target.exists() and target.is_file()):
|
|
176
|
+
script_dir.mkdir(parents=True, exist_ok=True)
|
|
177
|
+
shutil.copy(source, target)
|
|
178
|
+
else:
|
|
179
|
+
# Compare if the RUN_WITH_OVERLAY script is newer than the existing one
|
|
180
|
+
if source.stat().st_mtime > target.stat().st_mtime:
|
|
181
|
+
shutil.copy(source, target)
|
|
182
|
+
else:
|
|
183
|
+
logging.debug("Using existing run_with_overlay.sh script")
|
|
184
|
+
return target
|
|
185
|
+
|
|
186
|
+
if Config._system_is_not_posix():
|
|
187
|
+
return target
|
|
188
|
+
|
|
189
|
+
try:
|
|
190
|
+
# Get the current file permissions
|
|
191
|
+
current_permissions = os.stat(target).st_mode
|
|
192
|
+
|
|
193
|
+
# Add the executable bit for the owner, group, and others
|
|
194
|
+
os.chmod(target, current_permissions | stat.S_IXUSR | stat.S_IXGRP | stat.S_IXOTH)
|
|
195
|
+
except OSError as e:
|
|
196
|
+
logging.error(
|
|
197
|
+
f"Failed to set executable bit: {e}. "
|
|
198
|
+
"In some cases this can lead to permission errors when "
|
|
199
|
+
"running the script inside of the container."
|
|
200
|
+
)
|
|
156
201
|
|
|
157
202
|
|
|
158
203
|
@cache
|
fm_weck/engine.py
CHANGED
|
@@ -17,35 +17,42 @@ from typing import List, Optional, Union
|
|
|
17
17
|
from fm_tools.fmdata import FmData, FmImageConfig
|
|
18
18
|
|
|
19
19
|
from fm_weck.config import Config, parse_fm_data
|
|
20
|
+
from fm_weck.exceptions import NoImageError
|
|
20
21
|
from fm_weck.image_mgr import ImageMgr
|
|
21
22
|
|
|
22
23
|
logger = logging.getLogger(__name__)
|
|
23
24
|
|
|
24
25
|
|
|
25
|
-
|
|
26
|
-
|
|
26
|
+
CWD_MOUNT_LOCATION = "/home/cwd"
|
|
27
|
+
CACHE_MOUNT_LOCATION = "/home/fm-weck_cache"
|
|
28
|
+
OUTPUT_MOUNT_LOCATION = "/home/output"
|
|
29
|
+
|
|
30
|
+
RESERVED_LOCATIONS = frozenset([CACHE_MOUNT_LOCATION, CWD_MOUNT_LOCATION, OUTPUT_MOUNT_LOCATION])
|
|
27
31
|
|
|
28
32
|
|
|
29
33
|
class Engine(ABC):
|
|
30
34
|
interactive: bool = False
|
|
31
35
|
add_benchexec_capabilities: bool = False
|
|
32
36
|
image: Optional[str] = None
|
|
37
|
+
dry_run: bool = False
|
|
33
38
|
|
|
34
39
|
def __init__(self, image: Union[str, FmImageConfig]):
|
|
40
|
+
self._tmp_output_dir = Path(mkdtemp("fm_weck_output")).resolve()
|
|
35
41
|
self.image = self._initialize_image(image)
|
|
36
42
|
self.extra_args = {}
|
|
37
43
|
self._engine = None
|
|
38
|
-
self._tmp_output_dir = Path(mkdtemp("fm_weck_output")).resolve()
|
|
39
44
|
|
|
40
45
|
self.output_dir = Path.cwd() / "output"
|
|
41
46
|
self.log_file = None
|
|
42
47
|
|
|
48
|
+
self.env = {}
|
|
49
|
+
|
|
43
50
|
def __del__(self):
|
|
44
51
|
if self._tmp_output_dir.exists():
|
|
45
52
|
shutil.rmtree(self._tmp_output_dir)
|
|
46
53
|
|
|
47
54
|
def get_workdir(self):
|
|
48
|
-
return Path(
|
|
55
|
+
return Path(CWD_MOUNT_LOCATION)
|
|
49
56
|
|
|
50
57
|
def set_output_log(self, output_log: Path):
|
|
51
58
|
self.log_file = output_log
|
|
@@ -69,6 +76,9 @@ class Engine(ABC):
|
|
|
69
76
|
def interactive_command(self):
|
|
70
77
|
return ["-it"]
|
|
71
78
|
|
|
79
|
+
def add_environment(self):
|
|
80
|
+
return sum([["-e", f"{key}={value}"] for key, value in self.env.items()], [])
|
|
81
|
+
|
|
72
82
|
def setup_command(self):
|
|
73
83
|
return [
|
|
74
84
|
"--entrypoint",
|
|
@@ -76,11 +86,11 @@ class Engine(ABC):
|
|
|
76
86
|
"--cap-add",
|
|
77
87
|
"SYS_ADMIN",
|
|
78
88
|
"-v",
|
|
79
|
-
f"{Path.cwd().absolute()}
|
|
89
|
+
f"{Path.cwd().absolute()}:{CWD_MOUNT_LOCATION}",
|
|
80
90
|
"-v",
|
|
81
|
-
f"{Config().cache_location}
|
|
91
|
+
f"{Config().cache_location}:{CACHE_MOUNT_LOCATION}",
|
|
82
92
|
"-v",
|
|
83
|
-
f"{self._tmp_output_dir}
|
|
93
|
+
f"{self._tmp_output_dir}:{OUTPUT_MOUNT_LOCATION}",
|
|
84
94
|
"--workdir",
|
|
85
95
|
str(self.get_workdir()),
|
|
86
96
|
"--rm",
|
|
@@ -101,6 +111,7 @@ class Engine(ABC):
|
|
|
101
111
|
base += self.benchexec_capabilities()
|
|
102
112
|
|
|
103
113
|
base += self.setup_command()
|
|
114
|
+
base += self.add_environment()
|
|
104
115
|
|
|
105
116
|
if self.interactive:
|
|
106
117
|
base += self.interactive_command()
|
|
@@ -127,7 +138,7 @@ class Engine(ABC):
|
|
|
127
138
|
return self.get_workdir() / relative
|
|
128
139
|
elif p.is_relative_to(Config().cache_location):
|
|
129
140
|
relative = p.relative_to(Config().cache_location)
|
|
130
|
-
return Path(
|
|
141
|
+
return Path(CACHE_MOUNT_LOCATION) / relative
|
|
131
142
|
else:
|
|
132
143
|
return p
|
|
133
144
|
mapped = _map_path(Path(p))
|
|
@@ -156,7 +167,7 @@ class Engine(ABC):
|
|
|
156
167
|
|
|
157
168
|
@staticmethod
|
|
158
169
|
def _base_engine_class(config: Config):
|
|
159
|
-
engine = config.defaults().get("engine", "").lower()
|
|
170
|
+
engine = config.defaults().get("engine", "podman").lower()
|
|
160
171
|
|
|
161
172
|
if engine == "docker":
|
|
162
173
|
return Docker
|
|
@@ -204,6 +215,9 @@ class Engine(ABC):
|
|
|
204
215
|
continue
|
|
205
216
|
engine.mount(src, target)
|
|
206
217
|
|
|
218
|
+
if config.is_dry_run():
|
|
219
|
+
engine.dry_run = True
|
|
220
|
+
|
|
207
221
|
return engine
|
|
208
222
|
|
|
209
223
|
@abstractmethod
|
|
@@ -262,7 +276,12 @@ class Engine(ABC):
|
|
|
262
276
|
raise NoImageError("No image set for engine.")
|
|
263
277
|
|
|
264
278
|
command = self.assemble_command(command)
|
|
265
|
-
logger.
|
|
279
|
+
logger.debug("Running: %s", command)
|
|
280
|
+
if self.dry_run:
|
|
281
|
+
print("Command to be executed:")
|
|
282
|
+
print(" ".join(command))
|
|
283
|
+
return
|
|
284
|
+
|
|
266
285
|
self._run_process(command)
|
|
267
286
|
self._move_output()
|
|
268
287
|
|
|
@@ -284,12 +303,15 @@ class Podman(Engine):
|
|
|
284
303
|
return [
|
|
285
304
|
"--annotation",
|
|
286
305
|
"run.oci.keep_original_groups=1",
|
|
306
|
+
# "--cgroups=split",
|
|
307
|
+
"--security-opt",
|
|
308
|
+
"unmask=/sys/fs/cgroup",
|
|
287
309
|
"--security-opt",
|
|
288
310
|
"unmask=/proc/*",
|
|
289
311
|
"--security-opt",
|
|
290
312
|
"seccomp=unconfined",
|
|
291
313
|
"-v",
|
|
292
|
-
"/sys/fs/cgroup:/sys/fs/cgroup",
|
|
314
|
+
"/sys/fs/cgroup:/sys/fs/cgroup:rw",
|
|
293
315
|
]
|
|
294
316
|
|
|
295
317
|
|
|
@@ -336,11 +358,11 @@ class Docker(Engine):
|
|
|
336
358
|
"--cap-add",
|
|
337
359
|
"SYS_ADMIN",
|
|
338
360
|
"-v",
|
|
339
|
-
f"{Path.cwd().absolute()}
|
|
361
|
+
f"{Path.cwd().absolute()}:{CWD_MOUNT_LOCATION}",
|
|
340
362
|
"-v",
|
|
341
|
-
f"{Config().cache_location}
|
|
363
|
+
f"{Config().cache_location}:{CACHE_MOUNT_LOCATION}",
|
|
342
364
|
"-v",
|
|
343
|
-
f"{self._tmp_output_dir}
|
|
365
|
+
f"{self._tmp_output_dir}:{OUTPUT_MOUNT_LOCATION}",
|
|
344
366
|
"--workdir",
|
|
345
367
|
str(self.get_workdir()),
|
|
346
368
|
"--rm",
|
fm_weck/exceptions.py
ADDED
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
# This file is part of fm-weck: executing fm-tools in containerized environments.
|
|
2
|
+
# https://gitlab.com/sosy-lab/software/fm-weck
|
|
3
|
+
#
|
|
4
|
+
# SPDX-FileCopyrightText: 2024 Dirk Beyer <https://www.sosy-lab.org>
|
|
5
|
+
#
|
|
6
|
+
# SPDX-License-Identifier: Apache-2.0
|
|
7
|
+
|
|
8
|
+
class NoImageError(Exception):
|
|
9
|
+
pass
|
fm_weck/image_mgr.py
CHANGED
|
@@ -12,7 +12,7 @@ from typing import TYPE_CHECKING
|
|
|
12
12
|
from fm_tools.fmdata import FmImageConfig
|
|
13
13
|
from yaspin import yaspin
|
|
14
14
|
|
|
15
|
-
from fm_weck import
|
|
15
|
+
from fm_weck.exceptions import NoImageError
|
|
16
16
|
|
|
17
17
|
if TYPE_CHECKING:
|
|
18
18
|
from fm_weck.engine import Engine
|
|
@@ -30,7 +30,6 @@ class ImageMgr(object):
|
|
|
30
30
|
def __new__(cls):
|
|
31
31
|
if cls._instance is None:
|
|
32
32
|
cls._instance = super(ImageMgr, cls).__new__(cls)
|
|
33
|
-
cls._instance.image_db = Config().get("images", {}).get("database", None) or ":memory:"
|
|
34
33
|
return cls._instance
|
|
35
34
|
|
|
36
35
|
def prepare_image(self, engine: "Engine", image: FmImageConfig) -> str:
|
|
@@ -40,6 +39,9 @@ class ImageMgr(object):
|
|
|
40
39
|
if image.base_images and not image.required_packages:
|
|
41
40
|
return image.base_images[0]
|
|
42
41
|
|
|
42
|
+
if not image.base_images:
|
|
43
|
+
raise NoImageError("No base image specified")
|
|
44
|
+
|
|
43
45
|
logging.info(
|
|
44
46
|
"Building image from from base image %s with packages %s", image.base_images[0], image.required_packages
|
|
45
47
|
)
|
|
Binary file
|
fm_weck/resources/__init__.py
CHANGED
|
@@ -16,6 +16,8 @@ CONTAINERFILE = resource_dir / "Containerfile"
|
|
|
16
16
|
FM_DATA_LOCATION = resource_dir / "fm_tools"
|
|
17
17
|
PROPERTY_LOCATION = resource_dir / "properties"
|
|
18
18
|
RUN_WITH_OVERLAY = resource_dir / "run_with_overlay.sh"
|
|
19
|
+
BENCHEXEC_WHL = resource_dir / "BenchExec-3.25-py3-none-any.whl"
|
|
20
|
+
RUNEXEC_SCRIPT = resource_dir / "runexec"
|
|
19
21
|
|
|
20
22
|
|
|
21
23
|
def iter_fm_data():
|
|
@@ -23,7 +23,7 @@ versions:
|
|
|
23
23
|
benchexec_toolinfo_options: ['--graphml-witness', 'witness.graphml']
|
|
24
24
|
required_ubuntu_packages: []
|
|
25
25
|
- version: "svcomp23"
|
|
26
|
-
url: "https://gitlab.com/sosy-lab/sv-comp/archives-2023/-/raw/
|
|
26
|
+
url: "https://gitlab.com/sosy-lab/sv-comp/archives-2023/-/raw/svcomp23/2023/2ls.zip"
|
|
27
27
|
benchexec_toolinfo_options: ['--graphml-witness', 'witness.graphml']
|
|
28
28
|
required_ubuntu_packages: []
|
|
29
29
|
|
|
@@ -22,7 +22,7 @@ versions:
|
|
|
22
22
|
benchexec_toolinfo_options: []
|
|
23
23
|
required_ubuntu_packages: []
|
|
24
24
|
- version: "svcomp23"
|
|
25
|
-
url: "https://gitlab.com/sosy-lab/sv-comp/archives-2023/-/raw/
|
|
25
|
+
url: "https://gitlab.com/sosy-lab/sv-comp/archives-2023/-/raw/svcomp23/2023/brick.zip"
|
|
26
26
|
benchexec_toolinfo_options: []
|
|
27
27
|
required_ubuntu_packages: []
|
|
28
28
|
|
|
@@ -49,6 +49,11 @@ techniques:
|
|
|
49
49
|
|
|
50
50
|
frameworks_solvers: []
|
|
51
51
|
|
|
52
|
+
used_actors:
|
|
53
|
+
- actor_type: "Splitter"
|
|
54
|
+
description: |
|
|
55
|
+
Splits a program and verifies in parallel.
|
|
56
|
+
|
|
52
57
|
literature:
|
|
53
58
|
- doi: 10.1007/978-3-031-57256-2_20
|
|
54
59
|
title: "Bubaak-SpLit: Split What You Cannot Verify (Competition Contribution)"
|
|
@@ -25,7 +25,7 @@ versions:
|
|
|
25
25
|
- python3
|
|
26
26
|
- python3-lxml
|
|
27
27
|
- version: "svcomp23"
|
|
28
|
-
url: "https://gitlab.com/sosy-lab/sv-comp/archives-2023/-/raw/
|
|
28
|
+
url: "https://gitlab.com/sosy-lab/sv-comp/archives-2023/-/raw/svcomp23/2023/bubaak.zip"
|
|
29
29
|
benchexec_toolinfo_options: ["-sv-comp", "-sv-comp-witness", "witness.graphml"]
|
|
30
30
|
required_ubuntu_packages:
|
|
31
31
|
- clang
|
|
@@ -53,6 +53,11 @@ frameworks_solvers:
|
|
|
53
53
|
- CProver
|
|
54
54
|
- MiniSAT
|
|
55
55
|
|
|
56
|
+
used_actors:
|
|
57
|
+
- actor_type: "Translator"
|
|
58
|
+
description: |
|
|
59
|
+
Translates from C to a Goto program for verification.
|
|
60
|
+
|
|
56
61
|
literature:
|
|
57
62
|
- doi: 10.1007/978-3-642-54862-8_26
|
|
58
63
|
title: "CBMC: C Bounded Model Checker (Competition Contribution)"
|
|
@@ -10,7 +10,8 @@ fmtools_entry_maintainers:
|
|
|
10
10
|
- mjakobs
|
|
11
11
|
|
|
12
12
|
maintainers:
|
|
13
|
-
-
|
|
13
|
+
- orcid: 0000-0002-5890-4673
|
|
14
|
+
name: Marie-Christine Jakobs
|
|
14
15
|
institution: LMU Munich
|
|
15
16
|
country: Germany
|
|
16
17
|
url: https://www.sosy-lab.org/people/jakobs/
|
|
@@ -22,7 +23,7 @@ versions:
|
|
|
22
23
|
required_ubuntu_packages:
|
|
23
24
|
- openjdk-17-jre-headless
|
|
24
25
|
- version: "testcomp23"
|
|
25
|
-
url: "https://gitlab.com/sosy-lab/test-comp/archives-2023/-/raw/
|
|
26
|
+
url: "https://gitlab.com/sosy-lab/test-comp/archives-2023/-/raw/testcomp23/2023/coveritest.zip"
|
|
26
27
|
benchexec_toolinfo_options: ['-benchmark', '-heap', '10000M', '-testcomp23', "-setprop", "log.consoleLevel=SEVERE"]
|
|
27
28
|
required_ubuntu_packages:
|
|
28
29
|
- openjdk-11-jre-headless
|
|
@@ -32,6 +33,7 @@ competition_participations:
|
|
|
32
33
|
track: "Test Generation"
|
|
33
34
|
tool_version: "testcomp24"
|
|
34
35
|
jury_member:
|
|
36
|
+
orcid: 0000-0002-5890-4673
|
|
35
37
|
name: Marie-Christine Jakobs
|
|
36
38
|
institution: LMU Munich
|
|
37
39
|
country: Germany
|
|
@@ -40,6 +42,7 @@ competition_participations:
|
|
|
40
42
|
track: "Test Generation"
|
|
41
43
|
tool_version: "testcomp23"
|
|
42
44
|
jury_member:
|
|
45
|
+
orcid: 0000-0002-5890-4673
|
|
43
46
|
name: Marie-Christine Jakobs
|
|
44
47
|
institution: TU Darmstadt
|
|
45
48
|
country: Germany
|
|
@@ -53,3 +56,10 @@ techniques:
|
|
|
53
56
|
- Portfolio
|
|
54
57
|
|
|
55
58
|
frameworks_solvers: []
|
|
59
|
+
|
|
60
|
+
used_actors:
|
|
61
|
+
- actor_type: "Specification Transformer"
|
|
62
|
+
description: |
|
|
63
|
+
Transforms from test goals to error locations and use reachability analyzers to generate tests.
|
|
64
|
+
|
|
65
|
+
literature: []
|
|
@@ -12,11 +12,13 @@ fmtools_entry_maintainers:
|
|
|
12
12
|
- lemberger
|
|
13
13
|
|
|
14
14
|
maintainers:
|
|
15
|
-
-
|
|
15
|
+
- orcid: 0000-0003-4832-7662
|
|
16
|
+
name: Dirk Beyer
|
|
16
17
|
institution: LMU Munich
|
|
17
18
|
country: Germany
|
|
18
19
|
url: https://www.sosy-lab.org/people/dbeyer/
|
|
19
|
-
-
|
|
20
|
+
- orcid: 0000-0002-5139-341X
|
|
21
|
+
name: Philipp Wendler
|
|
20
22
|
institution: LMU Munich
|
|
21
23
|
country: Germany
|
|
22
24
|
url: https://www.sosy-lab.org/people/pwendler/
|
|
@@ -43,6 +45,7 @@ competition_participations:
|
|
|
43
45
|
track: "Validation of Violation Witnesses 1.0"
|
|
44
46
|
tool_version: "2.3"
|
|
45
47
|
jury_member:
|
|
48
|
+
orcid: 0000-0003-0291-815X
|
|
46
49
|
name: Thomas Lemberger
|
|
47
50
|
institution: LMU Munich
|
|
48
51
|
country: Germany
|
|
@@ -51,6 +54,7 @@ competition_participations:
|
|
|
51
54
|
track: "Validation of Violation Witnesses 1.0"
|
|
52
55
|
tool_version: "2.2"
|
|
53
56
|
jury_member:
|
|
57
|
+
orcid: 0000-0002-4768-4054
|
|
54
58
|
name: Henrik Wachowitz
|
|
55
59
|
institution: LMU Munich
|
|
56
60
|
country: Germany
|
|
@@ -63,6 +67,11 @@ techniques:
|
|
|
63
67
|
|
|
64
68
|
frameworks_solvers: []
|
|
65
69
|
|
|
70
|
+
used_actors:
|
|
71
|
+
- actor_type: "Witness Transformer"
|
|
72
|
+
description: |
|
|
73
|
+
Transforms a witness to a test case.
|
|
74
|
+
|
|
66
75
|
literature:
|
|
67
76
|
- doi: 10.1007/978-3-319-92994-1_1
|
|
68
77
|
title: "Tests from Witnesses: Execution-Based Validation of Verification Results"
|
|
@@ -1,4 +1,9 @@
|
|
|
1
1
|
name: CPAchecker
|
|
2
|
+
description: |
|
|
3
|
+
CPAchecker is a configurable framework for software verification that
|
|
4
|
+
is based on configurable program analysis and
|
|
5
|
+
implements many model-checking algorithms
|
|
6
|
+
to check for software errors and to verify program properties.
|
|
2
7
|
input_languages:
|
|
3
8
|
- C
|
|
4
9
|
project_url: https://cpachecker.sosy-lab.org
|
|
@@ -41,7 +41,6 @@ competition_participations:
|
|
|
41
41
|
url: https://www.sosy-lab.org/people/chien/
|
|
42
42
|
|
|
43
43
|
techniques:
|
|
44
|
-
- Algorithm Selection
|
|
45
44
|
- Bit-Precise Analysis
|
|
46
45
|
- Bounded Model Checking
|
|
47
46
|
- CEGAR
|
|
@@ -56,6 +55,14 @@ techniques:
|
|
|
56
55
|
frameworks_solvers:
|
|
57
56
|
- MiniSAT
|
|
58
57
|
|
|
58
|
+
used_actors:
|
|
59
|
+
- actor_type: "Witness Transformer"
|
|
60
|
+
description: |
|
|
61
|
+
Transforms a Btor2 hardware witness to an automata-based software witness.
|
|
62
|
+
- actor_type: "Instrumentor"
|
|
63
|
+
description: |
|
|
64
|
+
Instruments a program to facilitate witness transformation.
|
|
65
|
+
|
|
59
66
|
literature:
|
|
60
67
|
- doi: 10.1007/978-3-031-57256-2_22
|
|
61
68
|
title: "CPV: A Circuit-Based Program Verifier (Competition Contribution)"
|
|
@@ -9,7 +9,8 @@ fmtools_entry_maintainers:
|
|
|
9
9
|
- emersonwds
|
|
10
10
|
|
|
11
11
|
maintainers:
|
|
12
|
-
-
|
|
12
|
+
- orcid: 0000-0001-5606-9216
|
|
13
|
+
name: Emerson Sales
|
|
13
14
|
institution: Gran Sasso Science Institute
|
|
14
15
|
country: Italy
|
|
15
16
|
url: https://github.com/Emersonwds
|
|
@@ -43,6 +44,19 @@ techniques:
|
|
|
43
44
|
- Bit-Precise Analysis
|
|
44
45
|
- Concurrency Support
|
|
45
46
|
|
|
47
|
+
frameworks_solvers:
|
|
48
|
+
- CProver
|
|
49
|
+
- MiniSAT
|
|
50
|
+
|
|
51
|
+
frameworks_solvers:
|
|
52
|
+
- CProver
|
|
53
|
+
- MiniSAT
|
|
54
|
+
|
|
55
|
+
used_actors:
|
|
56
|
+
- actor_type: "Specification Transformer"
|
|
57
|
+
description: |
|
|
58
|
+
Transforms from concurrent programs to sequential programs by limiting context switches.
|
|
59
|
+
|
|
46
60
|
literature:
|
|
47
61
|
- doi: 10.1145/3478536
|
|
48
62
|
title: "Bounded Verification of Multi-threaded Programs via Lazy Sequentialization"
|
|
@@ -50,7 +64,3 @@ literature:
|
|
|
50
64
|
- doi: 10.1007/978-3-030-99527-0_23
|
|
51
65
|
title: "A Prototype for Data Race Detection in CSeq 3 (Competition Contribution)"
|
|
52
66
|
year: 2022
|
|
53
|
-
|
|
54
|
-
frameworks_solvers:
|
|
55
|
-
- CProver
|
|
56
|
-
- MiniSAT
|
|
@@ -24,7 +24,7 @@ versions:
|
|
|
24
24
|
- clang-14
|
|
25
25
|
- llvm-14
|
|
26
26
|
- version: "svcomp23"
|
|
27
|
-
url: "https://gitlab.com/sosy-lab/sv-comp/archives-2023/-/raw/
|
|
27
|
+
url: "https://gitlab.com/sosy-lab/sv-comp/archives-2023/-/raw/svcomp23/2023/dartagnan.zip"
|
|
28
28
|
benchexec_toolinfo_options: []
|
|
29
29
|
required_ubuntu_packages:
|
|
30
30
|
- clang-11
|
|
@@ -21,7 +21,7 @@ versions:
|
|
|
21
21
|
benchexec_toolinfo_options: []
|
|
22
22
|
required_ubuntu_packages: []
|
|
23
23
|
- version: "svcomp23"
|
|
24
|
-
url: "https://gitlab.com/sosy-lab/sv-comp/archives-2023/-/raw/
|
|
24
|
+
url: "https://gitlab.com/sosy-lab/sv-comp/archives-2023/-/raw/svcomp23/2023/deagle.zip"
|
|
25
25
|
benchexec_toolinfo_options: ["--no-unwinding-assertions", "--closure"]
|
|
26
26
|
required_ubuntu_packages: []
|
|
27
27
|
|