Skip to content

Commit 854a41d

Browse files
committed
Add more QCheck-STM tests
1 parent d7572aa commit 854a41d

File tree

4 files changed

+219
-0
lines changed

4 files changed

+219
-0
lines changed

test/kcas_data/dllist_test_stm.ml

Lines changed: 87 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,87 @@
1+
open QCheck
2+
open STM
3+
open Kcas_data
4+
5+
module Spec = struct
6+
type cmd = Add_l of int | Take_opt_l | Add_r of int | Take_opt_r
7+
8+
let show_cmd = function
9+
| Add_l x -> "Add_l " ^ string_of_int x
10+
| Take_opt_l -> "Take_opt_l"
11+
| Add_r x -> "Add_r " ^ string_of_int x
12+
| Take_opt_r -> "Take_opt_r"
13+
14+
module State = struct
15+
type t = int list * int list
16+
17+
let push_l x (l, r) = (x :: l, r)
18+
let push_r x (l, r) = (l, x :: r)
19+
20+
let drop_l (l, r) =
21+
match l with
22+
| _ :: l -> (l, r)
23+
| [] -> begin
24+
match List.rev r with [] -> ([], []) | _ :: l -> (l, [])
25+
end
26+
27+
let drop_r (l, r) =
28+
match r with
29+
| _ :: r -> (l, r)
30+
| [] -> begin
31+
match List.rev l with [] -> ([], []) | _ :: r -> ([], r)
32+
end
33+
34+
let peek_opt_l (l, r) =
35+
match l with
36+
| x :: _ -> Some x
37+
| [] -> begin match List.rev r with x :: _ -> Some x | [] -> None end
38+
39+
let peek_opt_r (l, r) =
40+
match r with
41+
| x :: _ -> Some x
42+
| [] -> begin match List.rev l with x :: _ -> Some x | [] -> None end
43+
end
44+
45+
type state = State.t
46+
type sut = int Dllist.t
47+
48+
let arb_cmd _s =
49+
[
50+
Gen.int |> Gen.map (fun x -> Add_l x);
51+
Gen.return Take_opt_l;
52+
Gen.int |> Gen.map (fun x -> Add_r x);
53+
Gen.return Take_opt_r;
54+
]
55+
|> Gen.oneof |> make ~print:show_cmd
56+
57+
let init_state = ([], [])
58+
let init_sut () = Dllist.create ()
59+
let cleanup _ = ()
60+
61+
let next_state c s =
62+
match c with
63+
| Add_l x -> State.push_l x s
64+
| Take_opt_l -> State.drop_l s
65+
| Add_r x -> State.push_r x s
66+
| Take_opt_r -> State.drop_r s
67+
68+
let precond _ _ = true
69+
70+
let run c d =
71+
match c with
72+
| Add_l x -> Res (unit, Dllist.add_l x d |> ignore)
73+
| Take_opt_l -> Res (option int, Dllist.take_opt_l d)
74+
| Add_r x -> Res (unit, Dllist.add_r x d |> ignore)
75+
| Take_opt_r -> Res (option int, Dllist.take_opt_r d)
76+
77+
let postcond c (s : state) res =
78+
match (c, res) with
79+
| Add_l _x, Res ((Unit, _), ()) -> true
80+
| Take_opt_l, Res ((Option Int, _), res) -> res = State.peek_opt_l s
81+
| Add_r _x, Res ((Unit, _), ()) -> true
82+
| Take_opt_r, Res ((Option Int, _), res) -> res = State.peek_opt_r s
83+
| _, _ -> false
84+
end
85+
86+
let () =
87+
Stm_run.run ~count:1000 ~verbose:true ~name:"Dllist" (module Spec) |> exit

test/kcas_data/dune

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -13,10 +13,13 @@
1313
(names
1414
accumulator_test_stm
1515
dllist_test
16+
dllist_test_stm
1617
hashtbl_test
18+
hashtbl_test_stm
1719
lru_cache_example
1820
mvar_test
1921
queue_test
22+
queue_test_stm
2023
stack_test
2124
stack_test_stm
2225
xt_test)

test/kcas_data/hashtbl_test_stm.ml

Lines changed: 61 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,61 @@
1+
open QCheck
2+
open STM
3+
open Kcas_data
4+
5+
module Spec = struct
6+
type cmd = Add of int | Mem of int | Remove of int | Length
7+
8+
let show_cmd = function
9+
| Add x -> "Add " ^ string_of_int x
10+
| Mem x -> "Mem " ^ string_of_int x
11+
| Remove x -> "Remove " ^ string_of_int x
12+
| Length -> "Length"
13+
14+
type state = int list
15+
type sut = (int, unit) Hashtbl.t
16+
17+
let arb_cmd _s =
18+
[
19+
Gen.int_bound 10 |> Gen.map (fun x -> Add x);
20+
Gen.int_bound 10 |> Gen.map (fun x -> Mem x);
21+
Gen.int_bound 10 |> Gen.map (fun x -> Remove x);
22+
Gen.return Length;
23+
]
24+
|> Gen.oneof |> make ~print:show_cmd
25+
26+
let init_state = []
27+
let init_sut () = Hashtbl.create ()
28+
let cleanup _ = ()
29+
30+
let next_state c s =
31+
match c with
32+
| Add x -> x :: s
33+
| Mem _ -> s
34+
| Remove x ->
35+
let[@tail_mod_cons] rec drop_first = function
36+
| [] -> []
37+
| x' :: xs -> if x = x' then xs else x' :: drop_first xs
38+
in
39+
drop_first s
40+
| Length -> s
41+
42+
let precond _ _ = true
43+
44+
let run c d =
45+
match c with
46+
| Add x -> Res (unit, Hashtbl.add d x ())
47+
| Mem x -> Res (bool, Hashtbl.mem d x)
48+
| Remove x -> Res (unit, Hashtbl.remove d x)
49+
| Length -> Res (int, Hashtbl.length d)
50+
51+
let postcond c (s : state) res =
52+
match (c, res) with
53+
| Add _x, Res ((Unit, _), ()) -> true
54+
| Mem x, Res ((Bool, _), res) -> res = List.exists (( = ) x) s
55+
| Remove _x, Res ((Unit, _), ()) -> true
56+
| Length, Res ((Int, _), res) -> res = List.length s
57+
| _, _ -> false
58+
end
59+
60+
let () =
61+
Stm_run.run ~count:1000 ~verbose:true ~name:"Hashtbl" (module Spec) |> exit

test/kcas_data/queue_test_stm.ml

Lines changed: 68 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,68 @@
1+
open QCheck
2+
open STM
3+
open Kcas_data
4+
5+
module Spec = struct
6+
type cmd = Push of int | Take_opt | Peek_opt | Length
7+
8+
let show_cmd = function
9+
| Push x -> "Push " ^ string_of_int x
10+
| Take_opt -> "Take_opt"
11+
| Peek_opt -> "Peek_opt"
12+
| Length -> "Length"
13+
14+
module State = struct
15+
type t = int list * int list
16+
17+
let push x (h, t) = if h == [] then ([ x ], []) else (h, x :: t)
18+
let peek_opt (h, _) = match h with x :: _ -> Some x | [] -> None
19+
20+
let drop ((h, t) as s) =
21+
match h with [] -> s | [ _ ] -> (List.rev t, []) | _ :: h -> (h, t)
22+
23+
let length (h, t) = List.length h + List.length t
24+
end
25+
26+
type state = State.t
27+
type sut = int Queue.t
28+
29+
let arb_cmd _s =
30+
[
31+
Gen.int |> Gen.map (fun x -> Push x);
32+
Gen.return Take_opt;
33+
Gen.return Peek_opt;
34+
Gen.return Length;
35+
]
36+
|> Gen.oneof |> make ~print:show_cmd
37+
38+
let init_state = ([], [])
39+
let init_sut () = Queue.create ()
40+
let cleanup _ = ()
41+
42+
let next_state c s =
43+
match c with
44+
| Push x -> State.push x s
45+
| Take_opt -> State.drop s
46+
| Peek_opt -> s
47+
| Length -> s
48+
49+
let precond _ _ = true
50+
51+
let run c d =
52+
match c with
53+
| Push x -> Res (unit, Queue.push x d)
54+
| Take_opt -> Res (option int, Queue.take_opt d)
55+
| Peek_opt -> Res (option int, Queue.peek_opt d)
56+
| Length -> Res (int, Queue.length d)
57+
58+
let postcond c (s : state) res =
59+
match (c, res) with
60+
| Push _x, Res ((Unit, _), ()) -> true
61+
| Take_opt, Res ((Option Int, _), res) -> res = State.peek_opt s
62+
| Peek_opt, Res ((Option Int, _), res) -> res = State.peek_opt s
63+
| Length, Res ((Int, _), res) -> res = State.length s
64+
| _, _ -> false
65+
end
66+
67+
let () =
68+
Stm_run.run ~count:1000 ~verbose:true ~name:"Queue" (module Spec) |> exit

0 commit comments

Comments
 (0)