1/*
2 * Copyright (c) 2021-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 "utilities_test.h"
17#include <chrono>
18#include <thread>
19#include "utilities.h"
20
21using namespace testing::ext;
22using namespace std;
23using namespace OHOS::HiviewDFX;
24namespace OHOS {
25namespace Developtools {
26namespace HiPerf {
27class UtilitiesTest : public testing::Test {
28public:
29    static void SetUpTestCase(void);
30    static void TearDownTestCase(void);
31    void SetUp();
32    void TearDown();
33    void TestThread();
34    void StartThreads(const size_t count);
35    void ExitThreads();
36    bool exitThreads_ = true;
37    std::vector<pid_t> tids_;
38    std::vector<std::thread> threads_;
39    const int sleepTime_ = {500};
40};
41
42void UtilitiesTest::SetUpTestCase() {}
43
44void UtilitiesTest::TearDownTestCase() {}
45
46void UtilitiesTest::SetUp() {}
47
48void UtilitiesTest::TearDown() {}
49
50void UtilitiesTest::TestThread()
51{
52    printf("threads %ld create\n", gettid());
53    int ret = fflush(nullptr);
54    if (ret == EOF) {
55        printf("fflush() error\n");
56    }
57
58    tids_.emplace_back(gettid());
59    while (!exitThreads_) {
60        std::this_thread::sleep_for(std::chrono::milliseconds(sleepTime_));
61    }
62    printf("threads %ld exited\n", gettid());
63    ret = fflush(nullptr);
64    if (ret == EOF) {
65        printf("fflush() error\n");
66    }
67}
68
69void UtilitiesTest::StartThreads(const size_t count)
70{
71    printf("create %zu threads\n", count);
72    int ret = fflush(nullptr);
73    if (ret == EOF) {
74        printf("fflush() error\n");
75    }
76
77    exitThreads_ = false;
78    size_t created = 0;
79    while (created < count) {
80        threads_.emplace_back(std::thread(&UtilitiesTest::TestThread, this));
81        created++;
82    }
83    while (tids_.size() < count) {
84        std::this_thread::sleep_for(std::chrono::milliseconds(sleepTime_));
85    }
86    printf("all threads created\n");
87    ret = fflush(nullptr);
88    if (ret == EOF) {
89        printf("fflush() error\n");
90    }
91}
92
93void UtilitiesTest::ExitThreads()
94{
95    printf("wait all threads exit\n");
96    exitThreads_ = true;
97    for (std::thread &t : this->threads_) {
98        t.join();
99    }
100    tids_.clear();
101    printf("all threads exited\n");
102}
103
104/**
105 * @tc.name: StringReplace
106 * @tc.desc:
107 * @tc.type: FUNC
108 */
109HWTEST_F(UtilitiesTest, StringReplace, TestSize.Level1)
110{
111    const std::string testString = "1234567890";
112    EXPECT_EQ(StringReplace(testString, "1", ""), "234567890");
113    EXPECT_EQ(StringReplace(testString, "2", ""), "134567890");
114    EXPECT_EQ(StringReplace(testString, "0", ""), "123456789");
115    EXPECT_EQ(StringReplace(testString, "1", "0"), "0234567890");
116    EXPECT_EQ(StringReplace(testString, "0", "1"), "1234567891");
117    EXPECT_EQ(StringReplace(testString, "123", "1"), "14567890");
118    EXPECT_EQ(StringReplace(testString, "890", "1"), "12345671");
119    EXPECT_EQ(StringReplace(testString, "456", "1"), "12317890");
120    EXPECT_EQ(StringReplace(testString, "123", "321"), "3214567890");
121    EXPECT_EQ(StringReplace(testString, "890", "098"), "1234567098");
122}
123
124/**
125 * @tc.name: StringSplit
126 * @tc.desc:
127 * @tc.type: FUNC
128 */
129HWTEST_F(UtilitiesTest, StringSplit, TestSize.Level1)
130{
131    std::string testString = "1,23,456,7890,";
132    size_t testSize = testString.size();
133    EXPECT_EQ(StringSplit(testString, "1").size(), 1u);
134    EXPECT_EQ(StringSplit(testString, "2").size(), 2u);
135    EXPECT_EQ(StringSplit(testString, ",").size(), 4u);
136    EXPECT_EQ(StringSplit(testString, "456").size(), 2u);
137    EXPECT_EQ(StringSplit(testString, "000").size(), 1u);
138    EXPECT_EQ(StringSplit(testString, "").size(), 1u);
139    // dont change the input string
140    EXPECT_EQ(testString.size(), testSize);
141
142    EXPECT_EQ(StringSplit(testString = "").size(), 0u);
143    EXPECT_EQ(StringSplit(testString = "1,2,3").size(), 3u);
144    EXPECT_EQ(StringSplit(testString = "1,2,3,,,").size(), 3u);
145}
146
147/**
148 * @tc.name: SubStringCount
149 * @tc.desc:
150 * @tc.type: FUNC
151 */
152HWTEST_F(UtilitiesTest, SubStringCount, TestSize.Level1)
153{
154    std::string testString = "1,22,333,4444,";
155    EXPECT_EQ(SubStringCount(testString, ""), testString.size());
156    EXPECT_EQ(SubStringCount(testString, "1"), 1u);
157    EXPECT_EQ(SubStringCount(testString, "2"), 2u);
158    EXPECT_EQ(SubStringCount(testString, "3"), 3u);
159    EXPECT_EQ(SubStringCount(testString, "4"), 4u);
160
161    EXPECT_EQ(SubStringCount(testString, "22"), 1u);
162    EXPECT_EQ(SubStringCount(testString, "33"), 1u);
163    EXPECT_EQ(SubStringCount(testString, "333"), 1u);
164    EXPECT_EQ(SubStringCount(testString, "4444"), 1u);
165    EXPECT_EQ(SubStringCount(testString, "444"), 1u);
166    EXPECT_EQ(SubStringCount(testString, "44"), 2u);
167}
168
169/**
170 * @tc.name: StringEndsWith
171 * @tc.desc:
172 * @tc.type: FUNC
173 */
174HWTEST_F(UtilitiesTest, StringEndsWith, TestSize.Level1)
175{
176    std::string testString = "1,22,333,4444,";
177    EXPECT_EQ(StringEndsWith(testString, ""), true);
178    EXPECT_EQ(StringEndsWith(testString, "1"), false);
179    EXPECT_EQ(StringEndsWith(testString, ","), true);
180
181    EXPECT_EQ(StringEndsWith("", ""), true);
182    EXPECT_EQ(StringEndsWith("", "1"), false);
183    EXPECT_EQ(StringEndsWith("", ","), false);
184}
185
186/**
187 * @tc.name: StringStartsWith
188 * @tc.desc:
189 * @tc.type: FUNC
190 */
191HWTEST_F(UtilitiesTest, StringStartsWith, TestSize.Level1)
192{
193    std::string testString = "1,22,333,4444,";
194    EXPECT_EQ(StringStartsWith(testString, ""), true);
195    EXPECT_EQ(StringStartsWith(testString, "1"), true);
196    EXPECT_EQ(StringStartsWith(testString, ","), false);
197
198    EXPECT_EQ(StringStartsWith("", ""), true);
199    EXPECT_EQ(StringStartsWith("", "1"), false);
200    EXPECT_EQ(StringStartsWith("", ","), false);
201}
202
203/**
204 * @tc.name: VectorToString
205 * @tc.desc:
206 * @tc.type: FUNC
207 */
208HWTEST_F(UtilitiesTest, VectorToString, TestSize.Level1)
209{
210    EXPECT_EQ(VectorToString<std::string>({}), "<empty>");
211    EXPECT_EQ(VectorToString<std::string>({"a", "b", "c"}), "a,b,c");
212    EXPECT_EQ(VectorToString<std::string>({"a"}), "a");
213    EXPECT_EQ(VectorToString<std::vector<std::string>>({
214                  {},
215              }),
216              "[<empty>]");
217    EXPECT_EQ(VectorToString<std::vector<std::string>>({
218                  {"a", "b", "c"},
219              }),
220              "[a,b,c]");
221    EXPECT_EQ(VectorToString<std::vector<std::string>>({
222                  {"a", "b", "c"},
223                  {"a", "b", "c"},
224                  {"a", "b", "c"},
225              }),
226              "[a,b,c],[a,b,c],[a,b,c]");
227
228    EXPECT_EQ(VectorToString<int>({}), "<empty>");
229    EXPECT_EQ(VectorToString<int>({1}), "1");
230    EXPECT_EQ(VectorToString<int>({1, 2, 3}), "1,2,3");
231
232    EXPECT_EQ(VectorToString<float>({}), "<empty>");
233    EXPECT_EQ(VectorToString<float>({1.0, 2.0, 3.0}), "1.000000,2.000000,3.000000");
234}
235
236/**
237 * @tc.name: BufferToHexString
238 * @tc.desc:
239 * @tc.type: FUNC
240 */
241HWTEST_F(UtilitiesTest, BufferToHexString, TestSize.Level1)
242{
243    const unsigned char buf[] = "12345678";
244
245    EXPECT_STREQ(BufferToHexString(buf, 0).c_str(), "0:");
246    EXPECT_STREQ(BufferToHexString(buf, 1).c_str(), "1: 0x31");
247    EXPECT_STREQ(BufferToHexString(buf, 4).c_str(), "4: 0x31 0x32 0x33 0x34");
248    EXPECT_STREQ(BufferToHexString(buf, 5).c_str(), "5: 0x31 0x32 0x33 0x34 0x35");
249    EXPECT_STREQ(BufferToHexString(buf, 8).c_str(), "8: 0x31 0x32 0x33 0x34 0x35 0x36 0x37 0x38");
250
251    const std::vector<unsigned char> vbuf(buf, buf + sizeof(buf) - 1u);
252
253    EXPECT_STREQ(BufferToHexString(vbuf).c_str(), "8: 0x31 0x32 0x33 0x34 0x35 0x36 0x37 0x38");
254
255    const unsigned char buf2[] = "1234567812345678";
256    EXPECT_STREQ(BufferToHexString(buf2, 0).c_str(), "0:");
257    EXPECT_STREQ(BufferToHexString(buf2, 1).c_str(), "1: 0x31");
258    EXPECT_STREQ(BufferToHexString(buf2, 4).c_str(), "4: 0x31 0x32 0x33 0x34");
259    EXPECT_STREQ(BufferToHexString(buf2, 5).c_str(), "5: 0x31 0x32 0x33 0x34 0x35");
260    EXPECT_STREQ(BufferToHexString(buf2, 8).c_str(), "8: 0x31 0x32 0x33 0x34 0x35 0x36 0x37 0x38");
261    EXPECT_STREQ(BufferToHexString(buf2, 9).c_str(),
262                 "9: 0x31 0x32 0x33 0x34 0x35 0x36 0x37 0x38 0x31");
263    EXPECT_STREQ(
264        BufferToHexString(buf2, 16).c_str(),
265        "16: 0x31 0x32 0x33 0x34 0x35 0x36 0x37 0x38 0x31 0x32 0x33 0x34 0x35 0x36 0x37 0x38");
266
267    const std::vector<unsigned char> vbuf2(buf2, buf2 + sizeof(buf2) - 1u);
268    EXPECT_STREQ(
269        BufferToHexString(vbuf2).c_str(),
270        "16: 0x31 0x32 0x33 0x34 0x35 0x36 0x37 0x38 0x31 0x32 0x33 0x34 0x35 0x36 0x37 0x38");
271}
272
273/**
274 * @tc.name: HexDump
275 * @tc.desc:
276 * @tc.type: FUNC
277 */
278HWTEST_F(UtilitiesTest, HexDump, TestSize.Level1)
279{
280    const unsigned char buf[] = "12345678";
281    const void *vbuf = static_cast<const void *>(buf);
282    ScopeDebugLevel tempLogLevel(LEVEL_MUCH, true);
283
284    StdoutRecord stdoutRecord;
285    stdoutRecord.Start();
286    HexDump(vbuf, 0);
287    HexDump(vbuf, 1);
288    HexDump(vbuf, 4);
289    HexDump(vbuf, 5);
290    HexDump(vbuf, 8);
291    stdoutRecord.Stop();
292}
293
294/**
295 * @tc.name: StringTrim
296 * @tc.desc:
297 * @tc.type: FUNC
298 */
299HWTEST_F(UtilitiesTest, StringTrim, TestSize.Level1)
300{
301    std::string test;
302    EXPECT_STREQ(StringTrim(test = " a ").c_str(), "a");
303    EXPECT_STREQ(StringTrim(test = " a").c_str(), "a");
304    EXPECT_STREQ(StringTrim(test = "a ").c_str(), "a");
305    EXPECT_STREQ(StringTrim(test = " a1a ").c_str(), "a1a");
306    EXPECT_STREQ(StringTrim(test = " a1a").c_str(), "a1a");
307    EXPECT_STREQ(StringTrim(test = "a1a ").c_str(), "a1a");
308    EXPECT_STREQ(StringTrim(test = "   a1a   ").c_str(), "a1a");
309    EXPECT_STREQ(StringTrim(test = "   a1a").c_str(), "a1a");
310    EXPECT_STREQ(StringTrim(test = "a1a   ").c_str(), "a1a");
311}
312
313/**
314 * @tc.name: RecordStdout
315 * @tc.desc:
316 * @tc.type: FUNC
317 */
318HWTEST_F(UtilitiesTest, RecordStdout, TestSize.Level1)
319{
320    StdoutRecord stdoutRecord;
321
322    ASSERT_EQ(stdoutRecord.Start(), true);
323    printf("line1: abc\n");
324    printf("line2: def\n");
325    printf("line3: ghi\n");
326    printf("\n");
327    std::string out = stdoutRecord.Stop();
328
329    printf("stdoutRecord:\n%s", out.c_str());
330    EXPECT_EQ(out.empty(), false);
331    EXPECT_NE(out.find("line1:"), std::string::npos);
332    EXPECT_NE(out.find("line2:"), std::string::npos);
333    EXPECT_NE(out.find("line3:"), std::string::npos);
334    EXPECT_EQ(out.find("line4:"), std::string::npos);
335}
336
337/**
338 * @tc.name: IsDigits
339 * @tc.desc:
340 * @tc.type: FUNC
341 */
342HWTEST_F(UtilitiesTest, IsDigits, TestSize.Level1)
343{
344    EXPECT_EQ(IsDigits(""), false);
345    EXPECT_EQ(IsDigits("1"), true);
346    EXPECT_EQ(IsDigits("12"), true);
347    EXPECT_EQ(IsDigits("1a"), false);
348    EXPECT_EQ(IsDigits("a1"), false);
349    EXPECT_EQ(IsDigits("1a2"), false);
350    EXPECT_EQ(IsDigits("a1b"), false);
351    EXPECT_EQ(IsDigits("_1"), false);
352    EXPECT_EQ(IsDigits("1_"), false);
353}
354
355/**
356 * @tc.name: IsHexxDigits
357 * @tc.desc:
358 * @tc.type: FUNC
359 */
360HWTEST_F(UtilitiesTest, IsHexxDigits, TestSize.Level1)
361{
362    EXPECT_EQ(IsHexDigits(""), false);
363    EXPECT_EQ(IsHexDigits("1"), true);
364    EXPECT_EQ(IsHexDigits("12"), true);
365    EXPECT_EQ(IsHexDigits("1a"), true);
366    EXPECT_EQ(IsHexDigits("f1"), true);
367    EXPECT_EQ(IsHexDigits("1f2"), true);
368    EXPECT_EQ(IsHexDigits("a1f"), true);
369    EXPECT_EQ(IsHexDigits("g1"), false);
370    EXPECT_EQ(IsHexDigits("1g"), false);
371    EXPECT_EQ(IsHexDigits("_1"), false);
372    EXPECT_EQ(IsHexDigits("1_"), false);
373}
374
375/**
376 * @tc.name: IsSameCommand
377 * @tc.desc:
378 * @tc.type: FUNC
379 */
380HWTEST_F(UtilitiesTest, IsSameCommand, TestSize.Level1)
381{
382    EXPECT_EQ(IsSameCommand("", ""), false);
383    EXPECT_EQ(IsSameCommand("a", ""), false);
384    EXPECT_EQ(IsSameCommand("", "b"), false);
385    EXPECT_EQ(IsSameCommand("1", "2"), false);
386    EXPECT_EQ(IsSameCommand("2", "1"), false);
387    EXPECT_EQ(IsSameCommand("1", "1"), true);
388    EXPECT_EQ(IsSameCommand("a", "a"), true);
389    EXPECT_EQ(IsSameCommand("a:1", "a:2"), false);
390}
391
392/**
393 * @tc.name: CompressFile
394 * @tc.desc:
395 * @tc.type: FUNC
396 */
397HWTEST_F(UtilitiesTest, CompressFile, TestSize.Level1)
398{
399    std::string srcPath = "./resource/testdata/elf_test_stripped_broken";
400    std::string destPath = "./test.gz";
401    EXPECT_EQ(CompressFile(srcPath, destPath), true);
402    srcPath = "";
403    EXPECT_EQ(CompressFile(srcPath, destPath), false);
404    srcPath = "./resource/testdata/elf_test_stripped_broken";
405    destPath = "";
406    EXPECT_EQ(CompressFile(srcPath, destPath), false);
407}
408
409/**
410 * @tc.name: UncompressFile
411 * @tc.desc:
412 * @tc.type: FUNC
413 */
414HWTEST_F(UtilitiesTest, UncompressFile, TestSize.Level1)
415{
416    std::string gzipPath = "./test.gz";
417    std::string dataPath = "./test";
418    EXPECT_EQ(UncompressFile(gzipPath, dataPath), true);
419    gzipPath = "./test.gz";
420    dataPath = "";
421    EXPECT_EQ(UncompressFile(gzipPath, dataPath), false);
422    gzipPath = "";
423    dataPath = "./resource/testdata/elf_test_stripped_broken";
424    EXPECT_EQ(UncompressFile(gzipPath, dataPath), false);
425}
426
427/**
428 * @tc.name: StringPrintf
429 * @tc.desc:
430 * @tc.type: FUNC
431 */
432HWTEST_F(UtilitiesTest, StringPrintf, TestSize.Level1)
433{
434    EXPECT_STREQ(StringPrintf("").c_str(), "");
435    EXPECT_STREQ(StringPrintf("123").c_str(), "123");
436    EXPECT_STREQ(StringPrintf("%d%s%c", 1, "2", 'c').c_str(), "12c");
437    EXPECT_STREQ(StringPrintf("%d%s%c\t\n", 1, "2", 'c').c_str(), "12c\t\n");
438
439    char format[PATH_MAX + 1];
440    std::fill(format, format + PATH_MAX, ' ');
441    format[PATH_MAX] = 0;
442    EXPECT_STRNE(StringPrintf(format).c_str(), format);
443    format[PATH_MAX - 1] = 0;
444    EXPECT_STREQ(StringPrintf(format).c_str(), format);
445    EXPECT_STREQ(StringPrintf(nullptr).c_str(), "");
446}
447
448/**
449 * @tc.name: GetEntriesInDir
450 * @tc.desc:
451 * @tc.type: FUNC
452 */
453HWTEST_F(UtilitiesTest, GetEntriesInDir, TestSize.Level1)
454{
455    std::vector<std::string> dirFileInfo;
456    dirFileInfo = GetEntriesInDir("./");
457    EXPECT_GE(dirFileInfo.size(), 0u);
458}
459
460/**
461 * @tc.name: GetSubDirs
462 * @tc.desc:
463 * @tc.type: FUNC
464 */
465HWTEST_F(UtilitiesTest, GetSubDirs, TestSize.Level1)
466{
467    std::vector<std::string> subDirFileInfo;
468    subDirFileInfo = GetSubDirs("../");
469    EXPECT_GE(subDirFileInfo.size(), 0u);
470}
471
472/**
473 * @tc.name: IsDir
474 * @tc.desc:
475 * @tc.type: FUNC
476 */
477HWTEST_F(UtilitiesTest, IsDir, TestSize.Level1)
478{
479    bool ret = IsDir("../");
480    EXPECT_EQ(ret, true);
481}
482
483/**
484 * @tc.name: IsPath
485 * @tc.desc:
486 * @tc.type: FUNC
487 */
488HWTEST_F(UtilitiesTest, IsPath, TestSize.Level1)
489{
490    bool ret = IsPath("./");
491    EXPECT_EQ(ret, true);
492}
493
494/**
495 * @tc.name: PlatformPathConvert
496 * @tc.desc:
497 * @tc.type: FUNC
498 */
499HWTEST_F(UtilitiesTest, PlatformPathConvert, TestSize.Level1)
500{
501    EXPECT_GE(PlatformPathConvert("./").length(), 0u);
502}
503
504/**
505 * @tc.name: ToHex
506 * @tc.desc:
507 * @tc.type: FUNC
508 */
509HWTEST_F(UtilitiesTest, ToHex, TestSize.Level1)
510{
511    unsigned char hVal = 'G';
512    EXPECT_STREQ(ToHex(hVal, 1, true).c_str(), "0x47");
513}
514
515/**
516 * @tc.name: ToHex
517 * @tc.desc:
518 * @tc.type: FUNC
519 */
520HWTEST_F(UtilitiesTest, CopyFromBufferAndMove, TestSize.Level1)
521{
522    unsigned char *buffer = new unsigned char[4];
523    buffer[0] = '1';
524    buffer[1] = '2';
525    buffer[2] = '3';
526    buffer[3] = '4';
527    int *dest = new int;
528    const unsigned char *srcStr = buffer;
529    EXPECT_EQ(CopyFromBufferAndMove(srcStr, dest, 4), 4u);
530}
531
532/**
533 * @tc.name: ReadIntFromProcFile
534 * @tc.desc:
535 * @tc.type: FUNC
536 */
537HWTEST_F(UtilitiesTest, ReadIntFromProcFile, TestSize.Level1)
538{
539    std::string strPath = "/proc/sys/kernel/perf_cpu_time_max_percent";
540    int strLen = 0;
541    EXPECT_EQ(ReadIntFromProcFile(strPath, strLen), true);
542}
543
544/**
545 * @tc.name: WriteIntToProcFile
546 * @tc.desc:
547 * @tc.type: FUNC
548 */
549HWTEST_F(UtilitiesTest, WriteIntToProcFile, TestSize.Level1)
550{
551    std::string strPath = "./hiperf_log.txt";
552    int strVal = 0;
553    EXPECT_EQ(WriteIntToProcFile(strPath, strVal), true);
554}
555
556/**
557 * @tc.name: ReadFileToString
558 * @tc.desc:
559 * @tc.type: FUNC
560 */
561HWTEST_F(UtilitiesTest, ReadFileToString, TestSize.Level1)
562{
563    std::string strPath = "./hiperf_log.txt";
564    EXPECT_NE(ReadFileToString(strPath).length(), 0u);
565}
566
567/**
568 * @tc.name: WriteStringToFile
569 * @tc.desc:
570 * @tc.type: FUNC
571 */
572HWTEST_F(UtilitiesTest, WriteStringToFile, TestSize.Level1)
573{
574    std::string strPath = "./hiperf_log.txt";
575    std::string content = "0";
576    EXPECT_EQ(WriteStringToFile(strPath, content), true);
577}
578
579/**
580 * @tc.name: Percentage
581 * @tc.desc:
582 * @tc.type: FUNC
583 */
584HWTEST_F(UtilitiesTest, Percentage, TestSize.Level1)
585{
586    EXPECT_EQ(Percentage(99, 100), 99);
587}
588
589/**
590 * @tc.name: IsRoot
591 * @tc.desc:
592 * @tc.type: FUNC
593 */
594HWTEST_F(UtilitiesTest, IsRoot, TestSize.Level1)
595{
596    bool isRoot = true;
597#if is_linux || is_ohos
598    isRoot = (getuid() == 0);
599#endif
600    EXPECT_EQ(IsRoot(), isRoot);
601}
602
603/**
604 * @tc.name: PowerOfTwo
605 * @tc.desc:
606 * @tc.type: FUNC
607 */
608HWTEST_F(UtilitiesTest, PowerOfTwo, TestSize.Level1)
609{
610    EXPECT_EQ(PowerOfTwo(1), true);
611}
612
613/**
614 * @tc.name: GetSubthreadIDs
615 * @tc.desc:
616 * @tc.type: FUNC
617 */
618HWTEST_F(UtilitiesTest, GetSubthreadIDs, TestSize.Level1)
619{
620    StartThreads(1);
621    std::vector<pid_t> tids = GetSubthreadIDs(getpid());
622    if (!HasFailure()) {
623        for (pid_t tid : tids_) {
624            EXPECT_NE(find(tids.begin(), tids.end(), tid), tids.end());
625        }
626    }
627    ExitThreads();
628}
629
630/**
631 * @tc.name: IsBeta
632 * @tc.desc:
633 * @tc.type: FUNC
634 */
635HWTEST_F(UtilitiesTest, IsBeta, TestSize.Level1)
636{
637    EXPECT_EQ(IsBeta(), true);
638}
639
640HWTEST_F(UtilitiesTest, CanonicalizeSpecPath, TestSize.Level1)
641{
642    EXPECT_EQ(CanonicalizeSpecPath(nullptr), "");
643    EXPECT_EQ(CanonicalizeSpecPath("/data/local/tmp/test/../test.txt"), "");
644    EXPECT_EQ(CanonicalizeSpecPath("/data/local/tmp/nonexistent.txt"), "/data/local/tmp/nonexistent.txt");
645    string largePath = "./";
646    for (int i = 0; i < 512; i++) { // 512: loop size
647        largePath += "testpath";
648    }
649    largePath += ".txt";
650    EXPECT_EQ(CanonicalizeSpecPath(largePath.c_str()), "");
651}
652
653/**
654 * @tc.name: RecordStdoutInit
655 * @tc.desc:
656 * @tc.type: FUNC
657 */
658HWTEST_F(UtilitiesTest, RecordStdoutInit, TestSize.Level1)
659{
660    StdoutRecord stdnormaloutRecord("/data/local/tmp/hiperf_log.txt", "rw");
661    (void)stdnormaloutRecord.Stop();
662    StdoutRecord stdexceptoutRecord("/data/local/tmp/../hiperf_log.txt");
663    EXPECT_EQ(stdexceptoutRecord.Stop().empty(), true);
664}
665} // namespace HiPerf
666} // namespace Developtools
667} // namespace OHOS
668