Merge "Test for unexpected prefix updates in SetAndClearNat64Prefix." into rvc-dev
diff --git a/tests/dns_metrics_listener/dns_metrics_listener.cpp b/tests/dns_metrics_listener/dns_metrics_listener.cpp
index 18c98d2..c3a15ed 100644
--- a/tests/dns_metrics_listener/dns_metrics_listener.cpp
+++ b/tests/dns_metrics_listener/dns_metrics_listener.cpp
@@ -33,6 +33,7 @@
                                                             const std::string& prefixString,
                                                             int32_t /*prefixLength*/) {
     std::lock_guard lock(mMutex);
+    mUnexpectedNat64PrefixUpdates++;
     if (netId == mNetId) mNat64Prefix = added ? prefixString : "";
     return ::ndk::ScopedAStatus::ok();
 }
@@ -49,15 +50,16 @@
     return ::ndk::ScopedAStatus::ok();
 }
 
-bool DnsMetricsListener::waitForNat64Prefix(ExpectNat64PrefixStatus status,
-                                            milliseconds timeout) const {
+bool DnsMetricsListener::waitForNat64Prefix(ExpectNat64PrefixStatus status, milliseconds timeout) {
     android::base::Timer t;
     while (t.duration() < timeout) {
         {
             std::lock_guard lock(mMutex);
             if ((status == EXPECT_FOUND && !mNat64Prefix.empty()) ||
-                (status == EXPECT_NOT_FOUND && mNat64Prefix.empty()))
+                (status == EXPECT_NOT_FOUND && mNat64Prefix.empty())) {
+                mUnexpectedNat64PrefixUpdates--;
                 return true;
+            }
         }
         std::this_thread::sleep_for(kRetryIntervalMs);
     }
diff --git a/tests/dns_metrics_listener/dns_metrics_listener.h b/tests/dns_metrics_listener/dns_metrics_listener.h
index 4322296..0b36462 100644
--- a/tests/dns_metrics_listener/dns_metrics_listener.h
+++ b/tests/dns_metrics_listener/dns_metrics_listener.h
@@ -51,8 +51,14 @@
                                                      bool validated) override;
 
     // Wait for expected NAT64 prefix status until timeout.
-    bool waitForNat64Prefix(ExpectNat64PrefixStatus status,
-                            std::chrono::milliseconds timeout) const;
+    bool waitForNat64Prefix(ExpectNat64PrefixStatus status, std::chrono::milliseconds timeout)
+            EXCLUDES(mMutex);
+
+    // Returns the number of updates to the NAT64 prefix that have not yet been waited for.
+    int getUnexpectedNat64PrefixUpdates() const EXCLUDES(mMutex) {
+        std::lock_guard lock(mMutex);
+        return mUnexpectedNat64PrefixUpdates;
+    }
 
     // Wait for the expected private DNS validation result until timeout.
     bool waitForPrivateDnsValidation(const std::string& serverAddr, const bool validated);
@@ -64,6 +70,12 @@
         return mValidationRecords.find({mNetId, serverAddr}) != mValidationRecords.end();
     }
 
+    void reset() EXCLUDES(mMutex) {
+        std::lock_guard lock(mMutex);
+        mUnexpectedNat64PrefixUpdates = 0;
+        mValidationRecords.clear();
+    }
+
   private:
     typedef std::pair<int32_t, std::string> ServerKey;
 
@@ -77,6 +89,13 @@
     // The NAT64 prefix of the network |mNetId|. It is updated by the event onNat64PrefixEvent().
     std::string mNat64Prefix GUARDED_BY(mMutex);
 
+    // The number of updates to the NAT64 prefix of network |mNetId| that have not yet been waited
+    // for. Increases by 1 every time onNat64PrefixEvent is called, and decreases by 1 every time
+    // waitForNat64Prefix returns true.
+    // This allows tests to check that no unexpected events have been received without having to
+    // resort to timeouts that make the tests slower and flakier.
+    int mUnexpectedNat64PrefixUpdates GUARDED_BY(mMutex);
+
     // Used to store the data from onPrivateDnsValidationEvent.
     std::map<ServerKey, bool> mValidationRecords GUARDED_BY(mMutex);
 
diff --git a/tests/resolv_integration_test.cpp b/tests/resolv_integration_test.cpp
index d70a552..595d621 100644
--- a/tests/resolv_integration_test.cpp
+++ b/tests/resolv_integration_test.cpp
@@ -185,7 +185,11 @@
     static void TearDownTestSuite() { AIBinder_DeathRecipient_delete(sResolvDeathRecipient); }
 
   protected:
-    void SetUp() { mDnsClient.SetUp(); }
+    void SetUp() {
+        mDnsClient.SetUp();
+        sDnsMetricsListener->reset();
+    }
+
     void TearDown() {
         // Ensure the dump works at the end of each test.
         DumpResolverService();
@@ -3816,6 +3820,8 @@
 
     EXPECT_TRUE(resolvService->stopPrefix64Discovery(TEST_NETID).isOk());
     EXPECT_TRUE(WaitForNat64Prefix(EXPECT_NOT_FOUND));
+
+    EXPECT_EQ(0, sDnsMetricsListener->getUnexpectedNat64PrefixUpdates());
 }
 
 namespace {