-
Notifications
You must be signed in to change notification settings - Fork 1.9k
Open
Labels
Description
Description of the issue
Currently QL always pretends that the parent of a LambdaExpr.getExprBody() is a ReturnStmt, however that is incorrect.
If the lambda implements an interface method with void as return type, the parent must not be ReturnStmt, but should be ExprStmt instead.
Example query:
import java
class RunMethod extends Method {
RunMethod() {
getDeclaringType().hasQualifiedName("java.lang", "Runnable")
and hasStringSignature("run()")
}
}
from LambdaExpr lambda, Expr expr
where
expr = lambda.getExprBody()
and expr.getParent() instanceof ReturnStmt
and lambda.asMethod().getAnOverride*() instanceof RunMethod
select exprThe current behavior likely causes false negatives for multiple queries in this repository because they check expr.getParent() instanceof ExprStmt to see if the return value of the call is discarded.
Edit: This apparently also affects the implicit method which MemberRefExpr.asMethod() has as result. And there the implicit method also has the wrong return type, e.g. run(): String for a Runnable r = this::toString();.
So there are three bugs:
-
LambdaExpr.asMethod()hasReturnStmtinstead ofExprStmtfor target interface methods withvoidas return type -
MemberRefExpr.asMethod()hasReturnStmtinstead ofExprStmtfor target interface methods withvoidas return type -
MemberRefExpr.asMethod()has wrongMethod.getReturnType()(i.e. non-void) for target interface methods withvoidas return type