[incremental] add last pending reads info in dumpsys

Example section of dumpsys output:
        lastPendingReads:
          fileId: 03300000000000000000000000000000
          metadataHex: 0330
          blockIndex: 857738
          bootClockTsUs: 166877488

Test: manual
BUG: 162600251
Change-Id: I37b04751c2a11972450ce7e9082116f8047e87df
diff --git a/services/incremental/IncrementalService.cpp b/services/incremental/IncrementalService.cpp
index 599ac93..91478a5 100644
--- a/services/incremental/IncrementalService.cpp
+++ b/services/incremental/IncrementalService.cpp
@@ -2341,17 +2341,16 @@
         return result;
     }
 
-    std::vector<incfs::ReadInfo> pendingReads;
-    if (mService.mIncFs->waitForPendingReads(control, 0ms, &pendingReads) !=
+    if (mService.mIncFs->waitForPendingReads(control, 0ms, &mLastPendingReads) !=
                 android::incfs::WaitResult::HaveData ||
-        pendingReads.empty()) {
+        mLastPendingReads.empty()) {
         return result;
     }
 
     LOG(DEBUG) << id() << ": pendingReads: " << control.pendingReads() << ", "
-               << pendingReads.size() << ": " << pendingReads.front().bootClockTsUs;
+               << mLastPendingReads.size() << ": " << mLastPendingReads.front().bootClockTsUs;
 
-    for (auto&& pendingRead : pendingReads) {
+    for (auto&& pendingRead : mLastPendingReads) {
         result = std::min(result, pendingRead.bootClockTsUs);
     }
     return result;
@@ -2400,6 +2399,18 @@
     }
 }
 
+static std::string toHexString(const RawMetadata& metadata) {
+    int n = metadata.size();
+    std::string res(n * 2, '\0');
+    // Same as incfs::toString(fileId)
+    static constexpr char kHexChar[] = "0123456789abcdef";
+    for (int i = 0; i < n; ++i) {
+        res[i * 2] = kHexChar[(metadata[i] & 0xf0) >> 4];
+        res[i * 2 + 1] = kHexChar[(metadata[i] & 0x0f)];
+    }
+    return res;
+}
+
 void IncrementalService::DataLoaderStub::onDump(int fd) {
     dprintf(fd, "    dataLoader: {\n");
     dprintf(fd, "      currentStatus: %d\n", mCurrentStatus);
@@ -2415,6 +2426,15 @@
     dprintf(fd, "        unhealthyTimeoutMs: %d\n", int(mHealthCheckParams.unhealthyTimeoutMs));
     dprintf(fd, "        unhealthyMonitoringMs: %d\n",
             int(mHealthCheckParams.unhealthyMonitoringMs));
+    dprintf(fd, "        lastPendingReads: \n");
+    const auto control = mService.mIncFs->openMount(mHealthPath);
+    for (auto&& pendingRead : mLastPendingReads) {
+        dprintf(fd, "          fileId: %s\n", mService.mIncFs->toString(pendingRead.id).c_str());
+        const auto metadata = mService.mIncFs->getMetadata(control, pendingRead.id);
+        dprintf(fd, "          metadataHex: %s\n", toHexString(metadata).c_str());
+        dprintf(fd, "          blockIndex: %d\n", pendingRead.block);
+        dprintf(fd, "          bootClockTsUs: %lld\n", (long long)pendingRead.bootClockTsUs);
+    }
     dprintf(fd, "      }\n");
     const auto& params = mParams;
     dprintf(fd, "      dataLoaderParams: {\n");
diff --git a/services/incremental/IncrementalService.h b/services/incremental/IncrementalService.h
index 4c4b8bd..eb69470 100644
--- a/services/incremental/IncrementalService.h
+++ b/services/incremental/IncrementalService.h
@@ -257,6 +257,7 @@
         } mHealthBase = {TimePoint::max(), kMaxBootClockTsUs};
         StorageHealthCheckParams mHealthCheckParams;
         int mStreamStatus = content::pm::IDataLoaderStatusListener::STREAM_HEALTHY;
+        std::vector<incfs::ReadInfo> mLastPendingReads;
     };
     using DataLoaderStubPtr = sp<DataLoaderStub>;
 
diff --git a/services/incremental/ServiceWrappers.cpp b/services/incremental/ServiceWrappers.cpp
index 144c466..dfe9684 100644
--- a/services/incremental/ServiceWrappers.cpp
+++ b/services/incremental/ServiceWrappers.cpp
@@ -166,6 +166,7 @@
     FileId getFileId(const Control& control, std::string_view path) const final {
         return incfs::getFileId(control, path);
     }
+    std::string toString(FileId fileId) const final { return incfs::toString(fileId); }
     std::pair<IncFsBlockIndex, IncFsBlockIndex> countFilledBlocks(
             const Control& control, std::string_view path) const final {
         const auto fileId = incfs::getFileId(control, path);
diff --git a/services/incremental/ServiceWrappers.h b/services/incremental/ServiceWrappers.h
index 4815caf..f2d0073 100644
--- a/services/incremental/ServiceWrappers.h
+++ b/services/incremental/ServiceWrappers.h
@@ -92,6 +92,7 @@
     virtual incfs::RawMetadata getMetadata(const Control& control, FileId fileid) const = 0;
     virtual incfs::RawMetadata getMetadata(const Control& control, std::string_view path) const = 0;
     virtual FileId getFileId(const Control& control, std::string_view path) const = 0;
+    virtual std::string toString(FileId fileId) const = 0;
     virtual std::pair<IncFsBlockIndex, IncFsBlockIndex> countFilledBlocks(
             const Control& control, std::string_view path) const = 0;
     virtual ErrorCode link(const Control& control, std::string_view from,
diff --git a/services/incremental/test/IncrementalServiceTest.cpp b/services/incremental/test/IncrementalServiceTest.cpp
index 867312e..9b8cf40 100644
--- a/services/incremental/test/IncrementalServiceTest.cpp
+++ b/services/incremental/test/IncrementalServiceTest.cpp
@@ -294,6 +294,7 @@
     MOCK_CONST_METHOD2(getMetadata, RawMetadata(const Control& control, FileId fileid));
     MOCK_CONST_METHOD2(getMetadata, RawMetadata(const Control& control, std::string_view path));
     MOCK_CONST_METHOD2(getFileId, FileId(const Control& control, std::string_view path));
+    MOCK_CONST_METHOD1(toString, std::string(FileId fileId));
     MOCK_CONST_METHOD2(countFilledBlocks,
                        std::pair<IncFsBlockIndex, IncFsBlockIndex>(const Control& control,
                                                                    std::string_view path));