[nullability] Fix assertion failure when calling free overloaded operator.
PiperOrigin-RevId: 526848860
diff --git a/nullability_verification/pointer_nullability_diagnosis.cc b/nullability_verification/pointer_nullability_diagnosis.cc
index f9f392c..c3064e4 100644
--- a/nullability_verification/pointer_nullability_diagnosis.cc
+++ b/nullability_verification/pointer_nullability_diagnosis.cc
@@ -195,9 +195,11 @@
auto ParamTypes = CalleeFPT->getParamTypes();
ArrayRef<const Expr*> Args(CE->getArgs(), CE->getNumArgs());
- if (isa<CXXOperatorCallExpr>(CE)) {
- // The first argument of an operator call expression is the operand which
- // does not appear in the list of parameter types.
+ // The first argument of an member operator call expression is the implicit
+ // object argument, which does not appear in the list of parameter types.
+ // Note that operator calls always have a direct callee.
+ if (isa<CXXOperatorCallExpr>(CE) &&
+ isa<CXXMethodDecl>(CE->getDirectCallee())) {
Args = Args.drop_front();
}
if (CalleeFPT->isVariadic()) {
diff --git a/nullability_verification/test/function_calls.cc b/nullability_verification/test/function_calls.cc
index 26b295c..77533ac 100644
--- a/nullability_verification/test/function_calls.cc
+++ b/nullability_verification/test/function_calls.cc
@@ -365,6 +365,19 @@
)cc"));
}
+TEST(PointerNullabilityTest, CallFreeOperator) {
+ // No nullability involved. This is just a regression test to make sure we can
+ // process a call to a free overloaded operator.
+ EXPECT_TRUE(checkDiagnostics(R"cc(
+ struct A {};
+ A operator+(A, A);
+ void target() {
+ A a;
+ a = a + a;
+ }
+ )cc"));
+}
+
} // namespace
} // namespace nullability
} // namespace tidy