• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
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 #ifndef ECMASCRIPT_TOOLING_TEST_TESTCASES_JS_HEAPDUMP_TEST_H
17 #define ECMASCRIPT_TOOLING_TEST_TESTCASES_JS_HEAPDUMP_TEST_H
18 
19 #include "tooling/test/client_utils/test_util.h"
20 
21 namespace panda::ecmascript::tooling::test {
22 class JsHeapdumpTest : public TestActions {
23 public:
JsHeapdumpTest()24     JsHeapdumpTest()
25     {
26         testAction = {
27             {SocketAction::SEND, "enable"},
28             {SocketAction::RECV, "", ActionRule::CUSTOM_RULE, MatchRule::replySuccess},
29             {SocketAction::SEND, "runtime-enable"},
30             {SocketAction::RECV, "", ActionRule::CUSTOM_RULE, MatchRule::replySuccess},
31             {SocketAction::SEND, "run"},
32             {SocketAction::RECV, "", ActionRule::CUSTOM_RULE, MatchRule::replySuccess},
33             // load sample.js
34             {SocketAction::RECV, "Debugger.scriptParsed", ActionRule::STRING_CONTAIN},
35             // break on start
36             {SocketAction::RECV, "Debugger.paused", ActionRule::STRING_CONTAIN},
37             {SocketAction::SEND, "heapprofiler-enable"},
38             {SocketAction::RECV, "", ActionRule::CUSTOM_RULE, MatchRule::replySuccess},
39             {SocketAction::SEND, "heapdump"},
40             {SocketAction::RECV, "", ActionRule::CUSTOM_RULE, [this] (auto recv, auto, auto) -> bool {
41                 return RecvReportProgress(recv);
42             }},
43             {SocketAction::RECV, "", ActionRule::CUSTOM_RULE, [this] (auto recv, auto, bool& needMoreMsg) -> bool {
44                 return RecvReportProgressFinished(recv, needMoreMsg);
45             }},
46             {SocketAction::RECV, "", ActionRule::CUSTOM_RULE, [this] (auto recv, auto, bool& needMoreMsg) -> bool {
47                 return RecvReportProgressChunk(recv, needMoreMsg);
48             }},
49             {SocketAction::RECV, "", ActionRule::CUSTOM_RULE, MatchRule::replySuccess},
50             {SocketAction::SEND, "heapprofiler-disable"},
51             {SocketAction::RECV, "", ActionRule::CUSTOM_RULE, MatchRule::replySuccess},
52             // reply success and run
53             {SocketAction::SEND, "success"},
54             {SocketAction::SEND, "resume"},
55             {SocketAction::RECV, "Debugger.resumed", ActionRule::STRING_CONTAIN},
56             {SocketAction::RECV, "", ActionRule::CUSTOM_RULE, MatchRule::replySuccess},
57         };
58     }
59 
RecvReportProgress(std::string recv)60     bool RecvReportProgress(std::string recv)
61     {
62         std::unique_ptr<PtJson> json = PtJson::Parse(recv);
63         Result ret;
64         std::string method;
65         ret = json->GetString("method", &method);
66         if (ret != Result::SUCCESS) {
67             return false;
68         }
69 
70         if (method != "HeapProfiler.reportHeapSnapshotProgress") {
71             return false;
72         }
73 
74         std::unique_ptr<PtJson> params = nullptr;
75         ret = json->GetObject("params", &params);
76         if (ret != Result::SUCCESS) {
77             return false;
78         }
79 
80         int done;
81         ret = params->GetInt("done", &done);
82         if (ret != Result::SUCCESS) {
83             return false;
84         }
85 
86         if (done != 0) {
87             return false;
88         }
89         return true;
90     }
91 
RecvReportProgressFinished(std::string recv,bool & needMoreMsg)92     bool RecvReportProgressFinished(std::string recv, bool &needMoreMsg)
93     {
94         needMoreMsg = false;
95         std::unique_ptr<PtJson> json = PtJson::Parse(recv);
96         Result ret;
97         std::string method;
98         ret = json->GetString("method", &method);
99         if (ret != Result::SUCCESS) {
100             return false;
101         }
102 
103         if (method != "HeapProfiler.reportHeapSnapshotProgress") {
104             return false;
105         }
106 
107         std::unique_ptr<PtJson> params = nullptr;
108         ret = json->GetObject("params", &params);
109         if (ret != Result::SUCCESS) {
110             return false;
111         }
112 
113         int done;
114         ret = params->GetInt("done", &done);
115         if (ret != Result::SUCCESS) {
116             return false;
117         }
118 
119         bool finished;
120         ret = params->GetBool("finished", &finished);
121         if (ret != Result::SUCCESS) {
122             needMoreMsg = true;
123         }
124         return true;
125     }
126 
RecvReportProgressChunk(std::string recv,bool & needMoreMsg)127     bool RecvReportProgressChunk(std::string recv, bool& needMoreMsg)
128     {
129         static std::string content;
130         needMoreMsg = false;
131         std::unique_ptr<PtJson> json = PtJson::Parse(recv);
132         Result ret;
133         std::string method;
134         ret = json->GetString("method", &method);
135         if (ret != Result::SUCCESS) {
136             return false;
137         }
138 
139         if (method != "HeapProfiler.addHeapSnapshotChunk") {
140             return false;
141         }
142 
143         std::unique_ptr<PtJson> params = nullptr;
144         ret = json->GetObject("params", &params);
145         if (ret != Result::SUCCESS) {
146             return false;
147         }
148 
149         std::string chunk;
150         ret = params->GetString("chunk", &chunk);
151         if (ret != Result::SUCCESS) {
152             return false;
153         }
154 
155         content += chunk;
156         std::unique_ptr<PtJson> contentJson = PtJson::Parse(content);
157         if (contentJson == nullptr || contentJson->Stringify().empty()) {
158             needMoreMsg = true;
159         }
160         return true;
161     }
162 
GetEntryPoint()163     std::pair<std::string, std::string> GetEntryPoint() override
164     {
165         return {pandaFile_, entryPoint_};
166     }
167     ~JsHeapdumpTest() = default;
168 
169 private:
170     std::string pandaFile_ = DEBUGGER_ABC_DIR "sample.abc";
171     std::string sourceFile_ = DEBUGGER_JS_DIR "sample.js";
172     std::string entryPoint_ = "_GLOBAL::func_main_0";
173 };
174 
GetJsHeapdumpTest()175 std::unique_ptr<TestActions> GetJsHeapdumpTest()
176 {
177     return std::make_unique<JsHeapdumpTest>();
178 }
179 }  // namespace panda::ecmascript::tooling::test
180 
181 #endif  // ECMASCRIPT_TOOLING_TEST_TESTCASES_JS_HEAPDUMP_TEST_H
182