diff options
| author | 2023-12-06 14:58:01 +0000 | |
|---|---|---|
| committer | 2023-12-07 15:27:50 +0000 | |
| commit | d358b579a98f8dcc5e1ba6678649543df51f7af5 (patch) | |
| tree | bb5b6186696c67483d04875f0ffb3d97663ee99c /runtime/exec_utils_test.cc | |
| parent | 27e688ccbaa6dfc8260e7c2905df98e6b86ec764 (diff) | |
Make ProcessStat collection more robust.
- Handle the case where start time is 0.
- Handle the case where getting uptime failed.
- Use 64bit int. (32bit is enough to record a time less than 24 days, but
just in case.)
Bug: 315061143
Test: m test-art-host-gtest-art_runtime_tests
Change-Id: I3ac546f6921b8d6add2491170b5d8f50cc7169c1
Diffstat (limited to 'runtime/exec_utils_test.cc')
| -rw-r--r-- | runtime/exec_utils_test.cc | 67 |
1 files changed, 64 insertions, 3 deletions
diff --git a/runtime/exec_utils_test.cc b/runtime/exec_utils_test.cc index e89180b572..fc628fc078 100644 --- a/runtime/exec_utils_test.cc +++ b/runtime/exec_utils_test.cc @@ -22,9 +22,11 @@ #include <cstring> #include <filesystem> #include <memory> +#include <optional> #include <tuple> #include "android-base/logging.h" +#include "android-base/result.h" #include "android-base/stringprintf.h" #include "base/file_utils.h" #include "base/memory_tool.h" @@ -34,6 +36,7 @@ namespace art { +using ::android::base::Result; using ::testing::_; using ::testing::AllOf; using ::testing::Gt; @@ -68,8 +71,19 @@ std::tuple<int, int> GetKernelVersion() { class TestingExecUtils : public ExecUtils { public: MOCK_METHOD(std::string, GetProcStat, (pid_t pid), (const, override)); - MOCK_METHOD(int64_t, GetUptimeMs, (), (const, override)); + MOCK_METHOD(Result<int64_t>, DoGetUptimeMs, (), (const)); MOCK_METHOD(int64_t, GetTicksPerSec, (), (const, override)); + + // A workaround to avoid MOCK_METHOD on a method with an `std::string*` parameter, which will lead + // to a conflict between gmock and android-base/logging.h (b/132668253). + std::optional<int64_t> GetUptimeMs(std::string* error_msg) const override { + Result<int64_t> result = DoGetUptimeMs(); + if (result.ok()) { + return *result; + } + *error_msg = result.error().message(); + return std::nullopt; + } }; class AlwaysFallbackExecUtils : public TestingExecUtils { @@ -204,7 +218,7 @@ TEST_P(ExecUtilsTest, ExecStat) { .WillOnce(Return( "14963 (a) b) Z 6067 14963 1 0 -1 4228108 105 0 0 0 94 5 0 0 39 19 1 0 162034388 0 0 " "18446744073709551615 0 0 0 0 0 0 20999 0 0 1 0 0 17 71 0 0 0 0 0 0 0 0 0 0 0 0 9")); - EXPECT_CALL(*exec_utils_, GetUptimeMs()).WillOnce(Return(1620344887ll)); + EXPECT_CALL(*exec_utils_, DoGetUptimeMs()).WillOnce(Return(1620344887ll)); EXPECT_CALL(*exec_utils_, GetTicksPerSec()).WillOnce(Return(100)); ASSERT_EQ( @@ -218,6 +232,53 @@ TEST_P(ExecUtilsTest, ExecStat) { EXPECT_EQ(stat.wall_time_ms, 1007); } +TEST_P(ExecUtilsTest, ExecStatNoStartTime) { + std::vector<std::string> command; + command.push_back(GetBin("id")); + + std::string error_msg; + ProcessStat stat; + + // The process filename is "a) b". + EXPECT_CALL(*exec_utils_, GetProcStat(_)) + .WillOnce(Return( + "14963 (a) b) Z 6067 14963 1 0 -1 4228108 105 0 0 0 94 5 0 0 39 19 1 0 0 0 0 " + "18446744073709551615 0 0 0 0 0 0 20999 0 0 1 0 0 17 71 0 0 0 0 0 0 0 0 0 0 0 0 9")); + EXPECT_CALL(*exec_utils_, DoGetUptimeMs()).WillOnce(Return(1620344887ll)); + EXPECT_CALL(*exec_utils_, GetTicksPerSec()).WillOnce(Return(100)); + + ASSERT_EQ( + exec_utils_ + ->ExecAndReturnResult(command, /*timeout_sec=*/-1, ExecCallbacks(), &stat, &error_msg) + .status, + ExecResult::kExited) + << error_msg; + + EXPECT_EQ(stat.cpu_time_ms, 0); + EXPECT_EQ(stat.wall_time_ms, 0); +} + +TEST_P(ExecUtilsTest, ExecStatNoUptime) { + std::vector<std::string> command; + command.push_back(GetBin("id")); + + std::string error_msg; + ProcessStat stat; + + EXPECT_CALL(*exec_utils_, DoGetUptimeMs()) + .WillOnce(Return(Result<int64_t>(Errorf("Failed to get uptime")))); + + ASSERT_EQ( + exec_utils_ + ->ExecAndReturnResult(command, /*timeout_sec=*/-1, ExecCallbacks(), &stat, &error_msg) + .status, + ExecResult::kExited) + << error_msg; + + EXPECT_EQ(stat.cpu_time_ms, 0); + EXPECT_EQ(stat.wall_time_ms, 0); +} + TEST_P(ExecUtilsTest, ExecStatFailed) { std::vector<std::string> command = SleepCommand(5); @@ -228,7 +289,7 @@ TEST_P(ExecUtilsTest, ExecStatFailed) { .WillOnce(Return( "14963 (a) b) Z 6067 14963 1 0 -1 4228108 105 0 0 0 94 5 0 0 39 19 1 0 162034388 0 0 " "18446744073709551615 0 0 0 0 0 0 20999 0 0 1 0 0 17 71 0 0 0 0 0 0 0 0 0 0 0 0 9")); - EXPECT_CALL(*exec_utils_, GetUptimeMs()).WillOnce(Return(1620344887ll)); + EXPECT_CALL(*exec_utils_, DoGetUptimeMs()).WillOnce(Return(1620344887ll)); EXPECT_CALL(*exec_utils_, GetTicksPerSec()).WillOnce(Return(100)); // This will always time out. |