1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218
|
(****************************************************************************)
(* the diy toolsuite *)
(* *)
(* Jade Alglave, University College London, UK. *)
(* Luc Maranget, INRIA Paris-Rocquencourt, France. *)
(* *)
(* Copyright 2010-present Institut National de Recherche en Informatique et *)
(* en Automatique and the authors. All rights reserved. *)
(* *)
(* This software is governed by the CeCILL-B license under French law and *)
(* abiding by the rules of distribution of free software. You can use, *)
(* modify and/ or redistribute the software under the terms of the CeCILL-B *)
(* license as circulated by CEA, CNRS and INRIA at the following URL *)
(* "http://www.cecill.info". We also give a copy in LICENSE.txt. *)
(****************************************************************************)
(* Internal keys for mcompare *)
open LogState
(* A key is a reference for a row, it features the name of
the test, plus information left abstract *)
type 'a t = { name : string ; info : 'a }
module type Config = sig
val verbose : int
val kinds : LogState.kind TblRename.t
val conds : LogConstr.cond TblRename.t
end
module Make(Opt:Config) = struct
module W = Warn.Make(Opt)
module LS = LogState.Make(Opt)
module None = struct
type info = unit
let add_names ts = Array.map (fun n -> { name = n; info = (); }) ts
let add_log t =
Array.map (fun n -> { name = n.tname; info = (); }) t.tests
end
module Kind = struct
type info = { kind : LogState.kind ; loop : bool }
let add_kind_tests nks ts =
let sz_nks = Array.length nks in
let sz_ts = Array.length ts in
let tout = ExtArray.create () in
let out x = ExtArray.add tout x in
let rec do_rec idx_nks idx_ts =
if idx_nks >= sz_nks || idx_ts >= sz_ts then
ExtArray.blit tout nks idx_nks (sz_nks-idx_nks)
else
let (n,k,loop as nk) = nks.(idx_nks)
and t = ts.(idx_ts) in
let c = String.compare n t.tname in
if c < 0 then begin
out nk ; do_rec (idx_nks+1) idx_ts
end else if c > 0 then
do_rec idx_nks (idx_ts+1)
else (* c=0 *) match k with
| None ->
out (n,Some t.LogState.kind,t.LogState.loop) ;
do_rec (idx_nks+1) (idx_ts+1)
| Some k1 ->
let k2 = t.LogState.kind in
if k1=k2 then
out (n,Some k1,loop || t.LogState.loop)
else begin
W.warn "Kind variation for test %s" n ;
out (n,Some NoKind,loop || t.LogState.loop)
end ;
do_rec (idx_nks+1) (idx_ts+1) in
do_rec 0 0 ;
ExtArray.to_array tout
let default_kind name =
try
Some (TblRename.find_value Opt.kinds name)
with Not_found -> None
let add names ts =
let nks_init = Array.map (fun x -> x,None,false) names in
let nks =
List.fold_left
(fun nks t -> add_kind_tests nks t.tests)
nks_init ts in
Array.map
(fun (n,k,loop) ->
let k =
let kdefault = default_kind n in
match kdefault with
| None -> k
| Some _ -> kdefault in
match k with
| None ->
{ name = n ;
info = { kind = NoKind ; loop = false}}
| Some k ->
{ name = n ;
info = { kind = k ; loop = loop}})
nks
let pps =
Array.map
(fun key ->
let k = key.info.kind
and loop = key.info.loop in
let k = LS.pp_kind k in
if loop then [k;"Loop"] else [k])
end
(* complete information: ie test result for first column *)
module Full = struct
type info = LogState.test
let add log =
Array.map
(fun t -> { name = t.tname ; info = t; })
log.tests
end
(* Condition *)
module Cond = struct
type info =
{ cond : LogConstr.cond option ; unsure : bool ; kind : LogState.kind;}
let sure k c = { cond = c ; unsure = false; kind=k; }
let unsure k c = { cond = c ; unsure = true; kind=k; }
let change_condition k c = match c with
| None -> sure k None
| Some c ->
let p = ConstrGen.prop_of c in
let sure c = sure k (Some c) in
match k with
| Forbid -> sure (ConstrGen.NotExistsState p)
| Allow -> sure (ConstrGen.ExistsState p)
| Require -> sure (ConstrGen.ForallStates p)
| Undefined -> sure (ConstrGen.ExistsState p)
| NoKind -> unsure k (Some c)
| ErrorKind -> assert false
let add_col t1 =
Array.map
(fun t ->
let _k,c =
let c,from_log =
try
Some (TblRename.find_value Opt.conds t.tname),false
with Not_found -> t.condition,true in
try
let k = TblRename.find_value Opt.kinds t.tname in
k,change_condition k c
with Not_found ->
let k = match c with
| None -> NoKind
| Some c ->
let open ConstrGen in
begin match c with
| NotExistsState _ -> LogState.Forbid
| ExistsState _ -> LogState.Allow
| ForallStates _ -> LogState.Require
end in
k,if from_log then unsure k c else sure k c in
{ name = t.tname ; info = c; })
t1.tests
let add = add_col
let merge_cond x y = match x.cond,y.cond with
| Some _,_ -> x
| _,Some _ -> y
| _,_ -> x
let merge_info xs ys =
let sz_xs = Array.length xs
and sz_ys = Array.length ys in
let tout = ExtArray.create () in
let out x = ExtArray.add tout x in
let rec loop i_xs i_ys =
if i_xs >= sz_xs then
ExtArray.blit tout ys i_ys (sz_ys-i_ys)
else if i_ys >= sz_ys then
ExtArray.blit tout xs i_xs (sz_xs-i_xs)
else
let x = xs.(i_xs) and y = ys.(i_ys) in
let c = String.compare x.name y.name in
if c < 0 then begin
out x ; loop (i_xs+1) i_ys
end else if c > 0 then begin
out y ; loop i_xs (i_ys+1)
end else begin
out { x with info = merge_cond x.info y.info; } ;
loop (i_xs+1) (i_ys+1)
end in
loop 0 0 ;
ExtArray.to_array tout
let rec merge_infos xs = function
| [] -> xs
| ys::rem -> merge_infos (merge_info xs ys) rem
let adds tss =
let ess = List.map add_col tss in
match ess with
| [] -> [| |]
| xs::rem -> merge_infos xs rem
end
end
|