• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 2022 Huawei Device Co., Ltd.
3  * Licensed under the Apache License, Version 2.0 (the "License");
4  * you may not use this file except in compliance with the License.
5  * You may obtain a copy of the License at
6  *
7  *     http://www.apache.org/licenses/LICENSE-2.0
8  *
9  * Unless required by applicable law or agreed to in writing, software
10  * distributed under the License is distributed on an "AS IS" BASIS,
11  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12  * See the License for the specific language governing permissions and
13  * limitations under the License.
14  */
15 
16 #include "dump_usage.h"
17 #include "cpu_dumper.h"
18 #include "executor/memory/get_heap_info.h"
19 #include "executor/memory/memory_info.h"
20 #include "executor/memory/parse/parse_smaps_info.h"
21 #include "securec.h"
22 
23 #include <gtest/gtest.h>
24 #include <unistd.h>
25 
26 using namespace testing::ext;
27 namespace OHOS {
28 namespace HiviewDFX {
29 static constexpr int MALLOC_SIZE = 1024;
30 static constexpr int LAUNCHER_PID_BUFFER_SIZE = 6;
31 static int g_pid = -1;
32 static int g_appManagerPid = -1;
33 class HiDumperInnerkitsTest : public testing::Test {
34 public:
35     using ValueMap = std::map<std::string, uint64_t>;
36     using GroupMap = std::map<std::string, ValueMap>;
37     static void SetUpTestCase(void);
38     static void TearDownTestCase(void);
39     void SetUp();
40     void TearDown();
41     static void GetAppManagerPids();
42     static int GetAppManagerPid(std::string process);
43     static void StartTestProcess();
44     static void StopProcess();
45 };
46 
SetUpTestCase(void)47 void HiDumperInnerkitsTest::SetUpTestCase(void)
48 {
49     GetAppManagerPids();
50     StartTestProcess();
51     if (g_pid < 0) {
52         printf("[SetUpTestCase] fork process failure!\n");
53         return;
54     }
55     if (g_pid == 0) {
56         printf("[SetUpTestCase] this process's pid is %d, it's should be child process\n", getpid());
57         return;
58     }
59 }
TearDownTestCase(void)60 void HiDumperInnerkitsTest::TearDownTestCase(void)
61 {
62     if (g_pid < 0) {
63         printf("[TearDownTestCase] fork process failure!\n");
64         return;
65     }
66     if (g_pid == 0) {
67         printf("[TearDownTestCase] this process's pid is %d, it's should be child process\n", getpid());
68         return;
69     }
70     StopProcess();
71 }
SetUp(void)72 void HiDumperInnerkitsTest::SetUp(void)
73 {
74 }
TearDown(void)75 void HiDumperInnerkitsTest::TearDown(void)
76 {
77 }
78 
StartTestProcess()79 void HiDumperInnerkitsTest::StartTestProcess()
80 {
81     int processNum = fork();
82     if (processNum == 0) {
83         while (true) {
84             void* p = malloc(MALLOC_SIZE);
85             if (p == nullptr) {
86                 const int bufSize = 256;
87                 char buf[bufSize] = { 0 };
88                 (void)strerror_r(errno, buf, bufSize);
89                 printf("malloc failure, errno(%d:%s)", errno, buf);
90                 return;
91             }
92             usleep(1);
93             free(p);
94         }
95     } else {
96         g_pid = processNum;
97     }
98 }
99 
StopProcess()100 void HiDumperInnerkitsTest::StopProcess()
101 {
102     std::string stopCmd = "kill " + std::to_string(g_pid);
103     system(stopCmd.c_str());
104 }
105 
GetAppManagerPids()106 void HiDumperInnerkitsTest::GetAppManagerPids()
107 {
108     std::vector<std::string> processes = {"com.ohos.launcher", "com.ohos.medialibrary.medialibrarydata", "hiview",
109         "com.ohos.settingsdata", "com.ohos.systemui", "render_service"};
110     for (std::vector<std::string>::iterator iter = processes.begin(); iter != processes.end(); iter++) {
111         int res = GetAppManagerPid(*iter);
112         if (res > 0) {
113             g_appManagerPid = res;
114             break;
115         }
116     }
117 }
118 
GetAppManagerPid(std::string process)119 int HiDumperInnerkitsTest::GetAppManagerPid(std::string process)
120 {
121     std::string cmd = "pidof " + process;
122     char appManagerPidChar[LAUNCHER_PID_BUFFER_SIZE] = {"\0"};
123     int appManagerPid = -1;
124     FILE *fp = nullptr;
125     fp = popen(cmd.c_str(), "r");
126     if (fp == nullptr) {
127         return -1;
128     }
129     if (fgets(appManagerPidChar, sizeof(appManagerPidChar), fp) != nullptr) {
130         pclose(fp);
131         int ret = sscanf_s(appManagerPidChar, "%d", &appManagerPid);
132         if (ret <= 0) {
133             return -1;
134         }
135         return appManagerPid;
136     }
137     pclose(fp);
138     return -1;
139 }
140 
141 /**
142  * @tc.name: GetMemInfoTest001
143  * @tc.desc: Test GetMemInfo.
144  * @tc.type: FUNC
145  * @tc.require: issueI5NWZQ
146  */
147 HWTEST_F(HiDumperInnerkitsTest, GetMemInfoTest001, TestSize.Level1)
148 {
149     std::unique_ptr<DumpUsage> dumpUsage = std::make_unique<DumpUsage>();
150     MemInfoData::MemInfo info;
151     EXPECT_TRUE(dumpUsage->GetMemInfo(g_pid, info));
152     EXPECT_GT(info.pss, 0);
153 }
154 
155 /**
156  * @tc.name: GetPssTest001
157  * @tc.desc: Test GetPss.
158  * @tc.type: FUNC
159  * @tc.require: issueI5NWZQ
160  */
161 HWTEST_F(HiDumperInnerkitsTest, GetPssTest001, TestSize.Level1)
162 {
163     std::unique_ptr<DumpUsage> dumpUsage = std::make_unique<DumpUsage>();
164     EXPECT_GT(dumpUsage->GetPss(g_pid), 0);
165 }
166 
167 /**
168  * @tc.name: GetPrivateDirtyTest001
169  * @tc.desc: Test GetPrivateDirty.
170  * @tc.type: FUNC
171  * @tc.require: issueI5NWZQ
172  */
173 HWTEST_F(HiDumperInnerkitsTest, GetPrivateDirtyTest001, TestSize.Level1)
174 {
175     std::unique_ptr<DumpUsage> dumpUsage = std::make_unique<DumpUsage>();
176     EXPECT_GE(dumpUsage->GetPrivateDirty(g_pid), 0);
177 }
178 
179 /**
180  * @tc.name: GetSharedDirtyTest001
181  * @tc.desc: Test GetSharedDirty.
182  * @tc.type: FUNC
183  * @tc.require: issueI5NWZQ
184  */
185 HWTEST_F(HiDumperInnerkitsTest, GetSharedDirtyTest001, TestSize.Level1)
186 {
187     std::unique_ptr<DumpUsage> dumpUsage = std::make_unique<DumpUsage>();
188     EXPECT_GE(dumpUsage->GetSharedDirty(g_pid), 0);
189 }
190 
191 /**
192  * @tc.name: GetCpuUsage001
193  * @tc.desc: Test GetCpuUsage.
194  * @tc.type: FUNC
195  * @tc.require: issueI5NWZQ
196  */
197 HWTEST_F(HiDumperInnerkitsTest, GetCpuUsage001, TestSize.Level1)
198 {
199     std::unique_ptr<DumpUsage> dumpUsage = std::make_unique<DumpUsage>();
200     EXPECT_GT(dumpUsage->GetCpuUsage(g_pid), 0);
201 }
202 
203 /**
204  * @tc.name: GetProcCpuInfo001
205  * @tc.desc: Test GetProcCpuInfo when a new process appeared.
206  * @tc.type: FUNC
207  */
208 HWTEST_F(HiDumperInnerkitsTest, GetProcCpuInfo001, TestSize.Level1)
209 {
210     auto parameter = std::make_shared<DumperParameter>();
211     DumperOpts opts;
212     opts.isDumpCpuUsage_ = true;
213     opts.cpuUsagePid_ = g_pid;
214     parameter->SetOpts(opts);
215     auto dumpDatas = std::make_shared<std::vector<std::vector<std::string>>>();
216     auto cpuDumper = std::make_shared<CPUDumper>();
217     int ret = DumpStatus::DUMP_FAIL;
218     ret = cpuDumper->PreExecute(parameter, dumpDatas);
219     ASSERT_EQ(ret, DumpStatus::DUMP_OK);
220     ret = cpuDumper->Execute();
221     ASSERT_EQ(ret, DumpStatus::DUMP_OK);
222     ret = cpuDumper->AfterExecute();
223     ASSERT_EQ(ret, DumpStatus::DUMP_OK);
224 }
225 
226 /**
227  * @tc.name: GetProcCpuInfo001
228  * @tc.desc: Test GetProcCpuInfo when a new process appeared.
229  * @tc.type: FUNC
230  */
231 HWTEST_F(HiDumperInnerkitsTest, GetHeapInfo001, TestSize.Level1)
232 {
233     int testPid = g_pid;
234     GroupMap groupMap;
235     std::map<std::string, uint64_t> value = {};
236     value["test"] = 1;
237     groupMap["test"] = value;
238     std::unique_ptr<GetHeapInfo> getHeapInfo = std::make_unique<GetHeapInfo>();
239     ASSERT_TRUE(getHeapInfo->GetInfo(MemoryFilter::APPOINT_PID, testPid, groupMap));
240 
241     if (g_appManagerPid != -1) {
242         testPid = g_appManagerPid;
243         ASSERT_TRUE(getHeapInfo->GetInfo(MemoryFilter::APPOINT_PID, testPid, groupMap));
244     }
245 }
246 
247 /**
248  * @tc.name: ParseSmapsInfoGetInfoTest001
249  * @tc.desc: Test GetMemInfo.
250  * @tc.type: FUNC
251  * @tc.require: issueI5NWZQ
252  */
253 HWTEST_F(HiDumperInnerkitsTest, ParseSmapsInfoGetInfoTest001, TestSize.Level1)
254 {
255     std::unique_ptr<ParseSmapsInfo> parseSmapsInfo = std::make_unique<ParseSmapsInfo>();
256     GroupMap groupMap;
257     EXPECT_TRUE(parseSmapsInfo->GetInfo(MemoryFilter::APPOINT_PID, 1, groupMap));
258 }
259 } // namespace HiviewDFX
260 } // namespace OHOS
261