If you're mechanically translating policy lists to TLA+ to check them, it might not be the most ideal tool for the job - but anyway here's how you might do something like this:
--------------------------- MODULE AccessControl ---------------------------
EXTENDS Naturals, Sequences
Policy == [
perm : STRING,
op : STRING,
obj : STRING
]
ACL == <<
[
perm |-> "allow",
op |-> "db1",
obj |-> "all"
],
[
perm |-> "deny",
op |-> "db1",
obj |-> "all"
]
>>
TypeOK == ACL \in Seq(Policy)
ConflictsWith(p1, p2) ==
/\ ACL[p1].op = ACL[p2].op
/\ ACL[p1].obj = ACL[p2].obj
/\ ACL[p1].perm /= ACL[p2].perm
Conflicts == {
<<p1, p2>> \in (DOMAIN ACL) \X (DOMAIN ACL) :
/\ p1 < p2
/\ ConflictsWith(p1, p2)
}
=============================================================================
Then you create a model with no behavior spec, got to the Model Checking Results tab, and enter the expression "Conflicts" into the "Evaluate Constant Expression" box. It will return a set of pairs of indices in the sequence that conflict with one another.
Andrew