Implement transfer function for checking that member accesses on pointers via the arrow (->) operator are null-safe.
We use a single matcher to handle both cases:\
Case 1: checking -> access on pointers\
Case 2: initialisation of null state for pointers which are members
We don't use distinct matchers as the `MatchSwitch` utility will only invoke one matcher case at a time, so the situation where both cases need to be invoked (see example below) will not be handled correctly.
```
struct Foo {
Foo* MemberPtr;
};
Foo* BasePtr;
BasePtr->MemberPtr; // Matches case 1 and 2
```
PiperOrigin-RevId: 454133816
diff --git a/nullability_verification/pointer_nullability_matchers.cc b/nullability_verification/pointer_nullability_matchers.cc
index 4f277dc..c37ce4a 100644
--- a/nullability_verification/pointer_nullability_matchers.cc
+++ b/nullability_verification/pointer_nullability_matchers.cc
@@ -11,6 +11,7 @@
namespace tidy {
namespace nullability {
+using ast_matchers::anyOf;
using ast_matchers::binaryOperator;
using ast_matchers::declRefExpr;
using ast_matchers::expr;
@@ -23,6 +24,7 @@
using ast_matchers::ignoringImplicit;
using ast_matchers::implicitCastExpr;
using ast_matchers::isAnyPointer;
+using ast_matchers::isArrow;
using ast_matchers::memberExpr;
using ast_matchers::nullPointerConstant;
using ast_matchers::unaryOperator;
@@ -46,8 +48,8 @@
Matcher<Stmt> isImplicitCastPointerToBool() {
return implicitCastExpr(hasCastKind(CK_PointerToBoolean));
}
-Matcher<Stmt> isPointerMemberExpr() {
- return memberExpr(hasType(isAnyPointer()));
+Matcher<Stmt> isMemberExprInvolvingPointers() {
+ return memberExpr(anyOf(isArrow(), hasType(isAnyPointer())));
}
} // namespace nullability
} // namespace tidy