Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 1243ddea authored by Yifan Hong's avatar Yifan Hong
Browse files

lshal: ListCommand::getPidInfo should be cached.

The function parses a big file and its result should be cached.
Add ListCommand::getPidInfoCached, which is a cached version
of this function.

Test: lshal_test
Change-Id: I03d8f149bf67b1512be431a3c4c29e83f7743a2f
parent 7a3b46c2
Loading
Loading
Loading
Loading
+11 −1
Original line number Diff line number Diff line
@@ -85,7 +85,7 @@ void ListCommand::removeDeadProcesses(Pids *pids) {
    }), pids->end());
}

bool scanBinderContext(pid_t pid,
static bool scanBinderContext(pid_t pid,
        const std::string &contextName,
        std::function<void(const std::string&)> eachLine) {
    std::ifstream ifs("/d/binder/proc/" + std::to_string(pid));
@@ -171,6 +171,16 @@ bool ListCommand::getPidInfo(
    });
}

const PidInfo* ListCommand::getPidInfoCached(pid_t serverPid) {
    auto pair = mCachedPidInfos.insert({serverPid, PidInfo{}});
    if (pair.second /* did insertion take place? */) {
        if (!getPidInfo(serverPid, &pair.first->second)) {
            return nullptr;
        }
    }
    return &pair.first->second;
}

// Must process hwbinder services first, then passthrough services.
void ListCommand::forEachTable(const std::function<void(Table &)> &f) {
    f(mServicesTable);
+7 −0
Original line number Diff line number Diff line
@@ -85,7 +85,11 @@ protected:
    Status fetchBinderized(const sp<::android::hidl::manager::V1_0::IServiceManager> &manager);
    Status fetchAllLibraries(const sp<::android::hidl::manager::V1_0::IServiceManager> &manager);

    // Get relevant information for a PID by parsing files under /d/binder.
    // It is a virtual member function so that it can be mocked.
    virtual bool getPidInfo(pid_t serverPid, PidInfo *info) const;
    // Retrieve from mCachedPidInfos and call getPidInfo if necessary.
    const PidInfo* getPidInfoCached(pid_t serverPid);

    void dumpTable(const NullableOStream<std::ostream>& out) const;
    void dumpVintf(const NullableOStream<std::ostream>& out) const;
@@ -129,6 +133,9 @@ protected:
    // If an entry exist and not empty, it contains the cached content of /proc/{pid}/cmdline.
    std::map<pid_t, std::string> mCmdlines;

    // Cache for getPidInfo.
    std::map<pid_t, PidInfo> mCachedPidInfos;

    RegisteredOptions mOptions;
    // All selected columns
    std::vector<TableColumnType> mSelectedColumns;
+10 −0
Original line number Diff line number Diff line
@@ -196,6 +196,9 @@ public:
        return ListCommand::dumpVintf(out);
    }
    void internalPostprocess() { ListCommand::postprocess(); }
    const PidInfo* getPidInfoCached(pid_t serverPid) {
        return ListCommand::getPidInfoCached(serverPid);
    }

    MOCK_METHOD0(postprocess, void());
    MOCK_CONST_METHOD2(getPidInfo, bool(pid_t, PidInfo*));
@@ -355,6 +358,13 @@ public:
    sp<MockServiceManager> passthruManager;
};

TEST_F(ListTest, GetPidInfoCached) {
    EXPECT_CALL(*mockList, getPidInfo(5, _)).Times(1);

    EXPECT_NE(nullptr, mockList->getPidInfoCached(5));
    EXPECT_NE(nullptr, mockList->getPidInfoCached(5));
}

TEST_F(ListTest, Fetch) {
    EXPECT_EQ(0u, mockList->fetch());
    std::array<std::string, 6> transports{{"hwbinder", "hwbinder", "passthrough",