5
5
6
6
import pytest
7
7
8
+ from pyk .kore .manip import substitute_vars
8
9
from pyk .kore .parser import KoreParser
9
- from pyk .kore .prelude import inj , top_cell_initializer
10
+ from pyk .kore .prelude import generated_counter , generated_top , inj , int_dv , k , map_pattern , top_cell_initializer
10
11
from pyk .kore .syntax import DV , App , EVar , SortApp , String
11
12
from pyk .ktool .kfuzz import KFuzz , kintegers
12
13
from pyk .ktool .kprint import _kast
15
16
from ..utils import K_FILES , TEST_DATA_DIR
16
17
17
18
if TYPE_CHECKING :
19
+ from collections .abc import Mapping
18
20
from pathlib import Path
19
21
from typing import Final
20
22
28
30
VAR_Y = EVar (name = 'VarY' , sort = SortApp ('SortInt' ))
29
31
30
32
33
+ def t (k_cell : Pattern , state_cell : Pattern ) -> App :
34
+ return App ("Lbl'-LT-'T'-GT-'" , (), (k_cell , state_cell ))
35
+
36
+
37
+ def state (pattern : Pattern ) -> App :
38
+ return App ("Lbl'-LT-'state'-GT-'" , (), (pattern ,))
39
+
40
+
41
+ def subst_on_k_cell (template : Pattern , subst_case : Mapping [EVar , Pattern ]) -> Pattern :
42
+ """A substitution function that only applies substitutions within the K cell.
43
+ Used to test custom substitution option in fuzzing and optimize fuzzers by
44
+ restricting changes to relevant parts of the configuration.
45
+
46
+ Args:
47
+ template: The template configuration containing variables in the K cell.
48
+ subst_case: A mapping from variables to their replacement patterns.
49
+ """
50
+ match template :
51
+ case App (
52
+ "Lbl'-LT-'generatedTop'-GT-'" ,
53
+ args = (
54
+ App ("Lbl'-LT-'T'-GT-'" , args = (k_cell , state_cell )),
55
+ generated_counter_cell ,
56
+ ),
57
+ ):
58
+ k_cell = substitute_vars (k_cell , subst_case )
59
+ return generated_top ((t (k_cell , state_cell ), generated_counter_cell ))
60
+
61
+ raise ValueError (template )
62
+
63
+
31
64
class TestImpFuzz (KompiledTest ):
32
65
KOMPILE_MAIN_FILE = K_FILES / 'imp.k'
33
66
KOMPILE_BACKEND = 'llvm'
@@ -37,6 +70,10 @@ class TestImpFuzz(KompiledTest):
37
70
def kfuzz (self , definition_dir : Path ) -> KFuzz :
38
71
return KFuzz (definition_dir )
39
72
73
+ @pytest .fixture
74
+ def kfuzz_with_subst (self , definition_dir : Path ) -> KFuzz :
75
+ return KFuzz (definition_dir , subst_func = subst_on_k_cell )
76
+
40
77
@staticmethod
41
78
def check (p : Pattern ) -> None :
42
79
def check_inner (p : Pattern ) -> Pattern :
@@ -76,6 +113,25 @@ def replace_var_ids(p: Pattern) -> Pattern:
76
113
77
114
return init_pattern
78
115
116
+ @staticmethod
117
+ def setup_program_with_config (definition_dir : Path , text : str ) -> Pattern :
118
+
119
+ kore_text = _kast (definition_dir = definition_dir , input = 'program' , output = 'kore' , expression = text ).stdout
120
+
121
+ program_pattern = KoreParser (kore_text ).pattern ()
122
+
123
+ def replace_var_ids (p : Pattern ) -> Pattern :
124
+ match p :
125
+ case App ('inj' , _, (DV (_, String ('varx' )),)):
126
+ return VAR_X
127
+ case App ('inj' , _, (DV (_, String ('vary' )),)):
128
+ return VAR_Y
129
+ return p
130
+
131
+ program_pattern = program_pattern .top_down (replace_var_ids )
132
+
133
+ return generated_top ((t (k (program_pattern ), state (map_pattern ())), generated_counter (int_dv (0 ))))
134
+
79
135
def test_fuzz (
80
136
self ,
81
137
definition_dir : Path ,
@@ -124,3 +180,28 @@ def test_fuzz_fail(
124
180
# Then
125
181
with pytest .raises (AssertionError ):
126
182
kfuzz .fuzz_with_check (init_pattern , self .SUBSTS , self .check )
183
+
184
+ def test_fuzz_with_subst (
185
+ self ,
186
+ definition_dir : Path ,
187
+ kfuzz_with_subst : KFuzz ,
188
+ ) -> None :
189
+ # Given
190
+ program_text = """
191
+ // Checks the commutativity of addition
192
+ int x, y, a, b, res;
193
+ x = varx;
194
+ y = vary;
195
+ a = x + y;
196
+ b = y + x;
197
+ if ((a <= b) && (b <= a)) { // a == b
198
+ res = 0;
199
+ } else {
200
+ res = 1;
201
+ }
202
+ """
203
+
204
+ init_pattern = self .setup_program_with_config (definition_dir , program_text )
205
+
206
+ # Then
207
+ kfuzz_with_subst .fuzz_with_check (init_pattern , self .SUBSTS , self .check )
0 commit comments