23 const auto LeftAndOperator = [=](
const BinOp *A) {
24 return implies(A->left(), LNeg, RHS, RNeg) &&
25 implies(A->right(), LNeg, RHS, RNeg);
27 const auto RightAndOperator = [=](
const BinOp *A) {
28 return implies(LHS, LNeg, A->left(), RNeg) &&
29 implies(LHS, LNeg, A->right(), RNeg);
33 const auto LeftOrOperator = [=](
const BinOp *A) {
34 return implies(A->left(), LNeg, RHS, RNeg) ||
35 implies(A->right(), LNeg, RHS, RNeg);
37 const auto RightOrOperator = [=](
const BinOp *A) {
38 return implies(LHS, LNeg, A->left(), RNeg) ||
39 implies(LHS, LNeg, A->right(), RNeg);
43 switch (RHS->
kind()) {
49 return RNeg ? RightOrOperator(cast<And>(RHS))
50 : RightAndOperator(cast<And>(RHS));
56 return RNeg ? RightAndOperator(cast<Or>(RHS))
57 : RightOrOperator(cast<Or>(RHS));
61 return implies(LHS, LNeg, cast<Not>(RHS)->
exp(), !RNeg);
68 switch (LHS->
kind()) {
74 return LNeg ? LeftAndOperator(cast<And>(LHS))
75 : LeftOrOperator(cast<And>(LHS));
81 return LNeg ? LeftOrOperator(cast<Or>(LHS))
82 : LeftAndOperator(cast<Or>(LHS));
86 return implies(cast<Not>(LHS)->
exp(), !LNeg, RHS, RNeg);
98 return cast<Terminal>(LHS)->expr() == cast<Terminal>(RHS)->expr();
102namespace threadSafety {
107 return ::implies(LHS,
false, RHS,
false);
static bool implies(const LExpr *LHS, bool LNeg, const LExpr *RHS, bool RNeg)
bool implies(const LExpr *LHS, const LExpr *RHS)
Logical implication.
The JSON file list parser is used to communicate input to InstallAPI.
Diagnostic wrappers for TextAPI types for error reporting.