1/*
2 * Copyright (c) 2023 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 <cstdio>
17
18#include "ecmascript/dfx/hprof/heap_profiler_interface.h"
19#include "ecmascript/dfx/hprof/heap_profiler.h"
20#include "ecmascript/dfx/hprof/heap_sampling.h"
21#include "ecmascript/dfx/stackinfo/js_stackgetter.h"
22#include "ecmascript/tests/test_helper.h"
23
24using namespace panda::ecmascript;
25
26namespace panda::test {
27class HeapSamplingTest : public testing::Test {
28public:
29    static void SetUpTestCase()
30    {
31        GTEST_LOG_(INFO) << "SetUpTestCase";
32    }
33
34    static void TearDownTestCase()
35    {
36        GTEST_LOG_(INFO) << "TearDownCase";
37    }
38
39    void SetUp() override
40    {
41        TestHelper::CreateEcmaVMWithScope(instance, thread, scope);
42        instance->SetEnableForceGC(false);
43    }
44
45    void TearDown() override
46    {
47        TestHelper::DestroyEcmaVMWithScope(instance, scope);
48    }
49
50    EcmaVM *instance {nullptr};
51    EcmaHandleScope *scope {nullptr};
52    JSThread *thread {nullptr};
53};
54
55HWTEST_F_L0(HeapSamplingTest, StartHeapSampling)
56{
57    HeapProfilerInterface *heapProfile = HeapProfilerInterface::GetInstance(instance);
58    uint64_t samplingInterval = 1 << 15; // default interval
59    int stackDepth = 128; // default depth
60    bool result = heapProfile->StartHeapSampling(samplingInterval, stackDepth);
61    ASSERT_TRUE(result);
62    result = heapProfile->StartHeapSampling(samplingInterval, stackDepth);
63    ASSERT_FALSE(result);
64}
65
66HWTEST_F_L0(HeapSamplingTest, StopHeapSampling)
67{
68    HeapProfilerInterface *heapProfile = HeapProfilerInterface::GetInstance(instance);
69    uint64_t samplingInterval = 1 << 15; // default interval
70    int stackDepth = 128; // default depth
71    bool result = heapProfile->StartHeapSampling(samplingInterval, stackDepth);
72    ASSERT_TRUE(result);
73    heapProfile->StopHeapSampling();
74    result = heapProfile->StartHeapSampling(samplingInterval, stackDepth);
75    ASSERT_TRUE(result);
76}
77
78HWTEST_F_L0(HeapSamplingTest, GetAllocationProfile)
79{
80    HeapProfilerInterface *heapProfile = HeapProfilerInterface::GetInstance(instance);
81    const SamplingInfo *result = heapProfile->GetAllocationProfile();
82    ASSERT_TRUE(result == nullptr);
83    uint64_t samplingInterval = 1 << 15; // default interval
84    int stackDepth = 128; // default depth
85    heapProfile->StartHeapSampling(samplingInterval, stackDepth);
86    result = heapProfile->GetAllocationProfile();
87    EXPECT_TRUE(result != nullptr);
88    EXPECT_TRUE(result->head_.callFrameInfo_.functionName_ == "(root)");
89}
90
91HWTEST_F_L0(HeapSamplingTest, ImplementSampling)
92{
93    uint64_t samplingInterval = 1 << 15; // default interval
94    int stackDepth = 128; // default depth
95    std::unique_ptr<HeapSampling> heapSampling = std::make_unique<HeapSampling>(instance,
96        const_cast<Heap *>(instance->GetHeap()), samplingInterval, stackDepth);
97    size_t size = 1U << 15U; // default size
98    Address addr = 0;
99    heapSampling->ImplementSampling(addr, size);
100    const SamplingInfo *result = heapSampling->GetAllocationProfile();
101    EXPECT_TRUE(result != nullptr);
102    EXPECT_TRUE(result->samples_[0].size_ == size);
103}
104}  // namespace panda::test
105