-
Notifications
You must be signed in to change notification settings - Fork 119
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Check mapping completeness #647
Open
trdthg
wants to merge
1
commit into
rems-project:sail2
Choose a base branch
from
trdthg:mapping-match-complete
base: sail2
Could not load branches
Branch not found: {{ refName }}
Loading
Could not load tags
Nothing to show
Loading
Are you sure you want to change the base?
Some commits from the old base branch may be removed from the timeline,
and old review comments may become outdated.
Open
Changes from all commits
Commits
File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -953,4 +953,113 @@ module Make (C : Config) = struct | |
|
||
let is_complete ?(keyword = "match") l ctx cases head_exp_typ = | ||
Option.is_some (is_complete_wildcarded ~keyword l ctx cases head_exp_typ) | ||
|
||
let rec pat_of_mpat mpat = | ||
match mpat with | ||
| MP_aux (mpat_aux, l) -> | ||
let res = | ||
match mpat_aux with | ||
| MP_lit lit -> P_lit lit | ||
| MP_id id -> P_id id | ||
| MP_app (id, mpat_list) -> P_app (id, List.map (fun mpat -> pat_of_mpat mpat) mpat_list) | ||
| MP_vector mpat_list -> P_vector (List.map (fun mpat -> pat_of_mpat mpat) mpat_list) | ||
| MP_vector_concat mpat_list -> P_vector_concat (List.map (fun mpat -> pat_of_mpat mpat) mpat_list) | ||
| MP_vector_subrange (id, l, r) -> P_vector_subrange (id, l, r) | ||
| MP_tuple mpat_list -> P_tuple (List.map (fun mpat -> pat_of_mpat mpat) mpat_list) | ||
| MP_list mpat_list -> P_list (List.map (fun mpat -> pat_of_mpat mpat) mpat_list) | ||
| MP_cons (mpat1, mpat2) -> P_cons (pat_of_mpat mpat1, pat_of_mpat mpat2) | ||
| MP_string_append mpat_list -> P_string_append (List.map (fun mpat -> pat_of_mpat mpat) mpat_list) | ||
| MP_typ (mp1, atyp) -> P_typ (atyp, pat_of_mpat mp1) | ||
| MP_struct id_mpat_list -> | ||
let fpl = List.map (fun (id, mpat) -> (id, pat_of_mpat mpat)) id_mpat_list in | ||
P_struct (fpl, FP_no_wild) | ||
| MP_as (mpat, id) -> ( | ||
match pat_of_mpat mpat with P_aux (pat, _id) -> pat | ||
) | ||
in | ||
P_aux (res, l) | ||
|
||
let is_complete_matrixs ?(keyword = "match") l ctx have_guard typ2matrixs = | ||
List.fold_left | ||
(fun all_complete (typ, matrix) -> | ||
(* be careful, all_complete && match { ... } will skip after warnings *) | ||
let complete = | ||
match matrix_is_complete l ctx matrix with | ||
| Incomplete (unmatched :: _) -> | ||
let guard_info = if have_guard then " by unguarded patterns" else "" in | ||
Reporting.warn "Incomplete pattern match statement at" (shrink_loc keyword l) | ||
("The following expression is unmatched" ^ guard_info ^ ": " | ||
^ (string_of_exp unmatched |> Util.yellow |> Util.clear) | ||
); | ||
false | ||
| Incomplete [] -> | ||
Reporting.warn "Unreachable pattern match type at" (shrink_loc keyword l) | ||
("The following type is unreachable: " ^ (string_of_typ typ |> Util.yellow |> Util.clear)); | ||
false | ||
| Complete cinfo -> | ||
List.iter | ||
(fun (idx, _) -> | ||
if IntSet.mem idx.num cinfo.redundant then | ||
Reporting.warn "Redundant case" idx.loc "This match case is never used" | ||
) | ||
(rows_to_list matrix); | ||
true | ||
| Completeness_unknown -> false | ||
in | ||
all_complete && complete | ||
) | ||
true typ2matrixs | ||
|
||
let is_complete_mapcls_wildcarded ?(keyword = "match") l ctx mapcls typl typr = | ||
let have_guard = false in | ||
let rec lpat_of_mapcl mapcl left = | ||
(* We don't consider guarded cases *) | ||
let pat_of_mpexp = function | ||
| MPat_aux (mpexp_aux, l) -> ( | ||
match mpexp_aux with MPat_when (mpat, exp) -> None | MPat_pat mpat -> Some (pat_of_mpat mpat) | ||
) | ||
in | ||
let rec pexp_to_pat = function | ||
| Pat_aux (Pat_exp ((P_aux (_, (l, _)) as pat), _), _) -> Some pat | ||
| Pat_aux (Pat_when _, _) -> None | ||
in | ||
match mapcl with | ||
| MCL_aux (mapcl_aux, _) -> | ||
if left then ( | ||
match mapcl_aux with | ||
| MCL_bidir (mpexp, _) -> pat_of_mpexp mpexp | ||
| MCL_forwards pexp -> pexp_to_pat pexp | ||
| MCL_backwards pexp -> None | ||
) | ||
else ( | ||
match mapcl_aux with | ||
| MCL_bidir (_, mpexp) -> pat_of_mpexp mpexp | ||
| MCL_forwards pexp -> None | ||
| MCL_backwards pexp -> pexp_to_pat pexp | ||
) | ||
in | ||
let rec opt_cases_to_pats from have_guard = function | ||
| [] -> (have_guard, []) | ||
| Some (P_aux (_, (l, _)) as pat) :: cases -> | ||
let pat, from = number_pat from pat in | ||
let have_guard, pats = opt_cases_to_pats from have_guard cases in | ||
(have_guard, (l, pat) :: pats) | ||
| _ :: cases -> opt_cases_to_pats from true cases | ||
in | ||
(* TODO: handle unsupported syntax *) | ||
try | ||
(* prepare left *) | ||
let lpats = List.map (fun mapcl -> lpat_of_mapcl mapcl true) mapcls in | ||
let _, lpats = opt_cases_to_pats 0 have_guard lpats in | ||
let lmatrix = | ||
Rows (List.mapi (fun i (l, pat) -> ({ loc = l; num = i }, Columns [generalize ctx (Some typl) pat])) lpats) | ||
in | ||
(* prepare right *) | ||
let rpats = List.map (fun mapcl -> lpat_of_mapcl mapcl false) mapcls in | ||
let _, rpats = opt_cases_to_pats 0 have_guard rpats in | ||
let rmatrix = | ||
Rows (List.mapi (fun i (l, pat) -> ({ loc = l; num = i }, Columns [generalize ctx (Some typr) pat])) rpats) | ||
in | ||
is_complete_matrixs ~keyword:"mapping" l ctx have_guard [(typl, lmatrix); (typr, rmatrix)] | ||
with _ -> false | ||
Comment on lines
+1049
to
+1064
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Some syntaxes are not supported in match, but are allowed by mapping example: test/c/poly_mapping2.sail
When encountering this kind of syntax, an exception will be thrown, so here fallback to false. |
||
end |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,10 @@ | ||
struct bool2 = { | ||
field: bool, | ||
} | ||
|
||
mapping m : bool <-> bool2 = { | ||
true <-> struct { field = true }, | ||
false <-> struct{ field = false }, | ||
} | ||
|
||
let foo = m(true) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,43 @@ | ||
[93mWarning[0m: Incomplete pattern match statement at [96mwarn_mapping_imcomplete.sail[0m:10.0-7: | ||
10[96m |[0mmapping imcomplete_oneside : bool <-> bool2 = { | ||
[91m |[0m[91m^-----^[0m | ||
[91m |[0m | ||
The following expression is unmatched: [93mstruct { field = true }[0m | ||
|
||
[93mWarning[0m: Incomplete pattern match statement at [96mwarn_mapping_imcomplete.sail[0m:15.0-7: | ||
15[96m |[0mmapping imcomplete_both_side : bool <-> bool2 = { | ||
[91m |[0m[91m^-----^[0m | ||
[91m |[0m | ||
The following expression is unmatched: [93mfalse[0m | ||
|
||
[93mWarning[0m: Unreachable pattern match type at [96mwarn_mapping_imcomplete.sail[0m:20.0-7: | ||
20[96m |[0mmapping forwords_unreachable : bool <-> int = { | ||
[91m |[0m[91m^-----^[0m | ||
[91m |[0m | ||
The following type is unreachable: [93mint[0m | ||
|
||
[93mWarning[0m: Unreachable pattern match type at [96mwarn_mapping_imcomplete.sail[0m:24.0-7: | ||
24[96m |[0mmapping backwords_unreachable : bool <-> int = { | ||
[91m |[0m[91m^-----^[0m | ||
[91m |[0m | ||
The following type is unreachable: [93mbool[0m | ||
|
||
[93mWarning[0m: Unreachable pattern match type at [96mwarn_mapping_imcomplete.sail[0m:28.0-7: | ||
28[96m |[0mmapping multi_warning : bool <-> int = { | ||
[91m |[0m[91m^-----^[0m | ||
[91m |[0m | ||
The following type is unreachable: [93mbool[0m | ||
|
||
[93mWarning[0m: Incomplete pattern match statement at [96mwarn_mapping_imcomplete.sail[0m:28.0-7: | ||
28[96m |[0mmapping multi_warning : bool <-> int = { | ||
[91m |[0m[91m^-----^[0m | ||
[91m |[0m | ||
The following expression is unmatched: [93m3[0m | ||
|
||
[93mWarning[0m: Unreachable pattern match type at Code generated nearby: | ||
[96mwarn_mapping_imcomplete.sail[0m:38.0-79: | ||
38[96m |[0mmapping clause encdec = true if enabled <-> struct { field = false } if enabled | ||
[91m |[0m[91m^-----------------------------------------------------------------------------^[0m | ||
[91m |[0m | ||
The following type is unreachable: [93mbool[0m | ||
|
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,40 @@ | ||
struct bool2 = { | ||
field: bool, | ||
} | ||
|
||
mapping complete : bool <-> bool2 = { | ||
true <-> struct { field = false }, | ||
false <-> struct{ field = true }, | ||
} | ||
|
||
mapping imcomplete_oneside : bool <-> bool2 = { | ||
true <-> struct { field = false }, | ||
false <-> struct { field = false }, | ||
} | ||
|
||
mapping imcomplete_both_side : bool <-> bool2 = { | ||
true <-> struct { field = false }, | ||
true <-> struct { field = false }, | ||
} | ||
|
||
mapping forwords_unreachable : bool <-> int = { | ||
forwards _ => 1, | ||
} | ||
|
||
mapping backwords_unreachable : bool <-> int = { | ||
backwards _ => false, | ||
} | ||
|
||
mapping multi_warning : bool <-> int = { | ||
backwards 2 => false, | ||
} | ||
|
||
register enabled : bool | ||
|
||
val encdec : bool <-> bool2 | ||
|
||
scattered mapping encdec | ||
|
||
mapping clause encdec = true if enabled <-> struct { field = false } if enabled | ||
|
||
end encdec |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Oops, something went wrong.
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
type_check again to add_attrs after scattered mapdefs get together