diff --git a/ql/ql/src/codeql_ql/style/RedundantOverrideQuery.qll b/ql/ql/src/codeql_ql/style/RedundantOverrideQuery.qll new file mode 100644 index 00000000000..5d8abd4e170 --- /dev/null +++ b/ql/ql/src/codeql_ql/style/RedundantOverrideQuery.qll @@ -0,0 +1,46 @@ +import ql + +/** Holds if `pred` overrides super predicate `sup` by forwarding via `mc`. */ +private predicate forwardingOverride(ClassPredicate pred, MemberCall mc, ClassPredicate sup) { + pred.overrides(sup) and + mc.getBase() instanceof Super and + mc.getTarget() = sup and + not exists(pred.getQLDoc()) and + forall(int i, VarDecl p | p = pred.getParameter(i) | mc.getArgument(i) = p.getAnAccess()) and + ( + pred.getBody() = + any(ComparisonFormula comp | + comp.getOperator() = "=" and + comp.getAnOperand() instanceof ResultAccess and + comp.getAnOperand() = mc and + pred.getReturnType() = sup.getReturnType() + ) + or + pred.getBody() = mc + ) +} + +private predicate forwardingOverrideProj(ClassPredicate pred, ClassPredicate sup) { + forwardingOverride(pred, _, sup) +} + +private ClassPredicate getUltimateDef(ClassPredicate p) { + forwardingOverrideProj*(p, result) and + not forwardingOverrideProj(result, _) +} + +predicate redundantOverride(ClassPredicate pred, ClassPredicate sup) { + exists(MemberCall mc | + forwardingOverride(pred, mc, sup) and + // overridden to provide more precise QL doc + not exists(pred.getQLDoc()) and + // overridden to disambiguate + not exists(ClassPredicate other | + getUltimateDef(sup) != getUltimateDef(other) and + pred.getDeclaringType().getASuperType+() = other.getDeclaringType() and + not sup.overrides*(other) and + other.getName() = pred.getName() and + other.getArity() = pred.getArity() + ) + ) +} diff --git a/ql/ql/src/queries/style/RedundantOverride.ql b/ql/ql/src/queries/style/RedundantOverride.ql index e95df3cf8a3..53b17be1992 100644 --- a/ql/ql/src/queries/style/RedundantOverride.ql +++ b/ql/ql/src/queries/style/RedundantOverride.ql @@ -9,51 +9,7 @@ */ import ql - -/** Holds if `pred` overrides super predicate `sup` by forwarding via `mc`. */ -private predicate forwardingOverride(ClassPredicate pred, MemberCall mc, ClassPredicate sup) { - pred.overrides(sup) and - mc.getBase() instanceof Super and - mc.getTarget() = sup and - not exists(pred.getQLDoc()) and - forall(int i, VarDecl p | p = pred.getParameter(i) | mc.getArgument(i) = p.getAnAccess()) and - ( - pred.getBody() = - any(ComparisonFormula comp | - comp.getOperator() = "=" and - comp.getAnOperand() instanceof ResultAccess and - comp.getAnOperand() = mc and - pred.getReturnType() = sup.getReturnType() - ) - or - pred.getBody() = mc - ) -} - -private predicate forwardingOverrideProj(ClassPredicate pred, ClassPredicate sup) { - forwardingOverride(pred, _, sup) -} - -private ClassPredicate getUltimateDef(ClassPredicate p) { - forwardingOverrideProj*(p, result) and - not forwardingOverrideProj(result, _) -} - -private predicate redundantOverride(ClassPredicate pred, ClassPredicate sup) { - exists(MemberCall mc | - forwardingOverride(pred, mc, sup) and - // overridden to provide more precise QL doc - not exists(pred.getQLDoc()) and - // overridden to disambiguate - not exists(ClassPredicate other | - getUltimateDef(sup) != getUltimateDef(other) and - pred.getDeclaringType().getASuperType+() = other.getDeclaringType() and - not sup.overrides*(other) and - other.getName() = pred.getName() and - other.getArity() = pred.getArity() - ) - ) -} +import codeql_ql.style.RedundantOverrideQuery from ClassPredicate pred, ClassPredicate sup where redundantOverride(pred, sup)