1 /*
2 * Copyright (c) 2021 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 #include "command_poller.h"
16 #include "buffer_writer.h"
17 #include "plugin_manager.h"
18 #include "socket_context.h"
19
20 #include <fcntl.h>
21 #include <unistd.h>
22
23 namespace {
24 constexpr int SLEEP_TIME = 10;
25 }
26
CommandPoller(const ManagerInterfacePtr & p)27 CommandPoller::CommandPoller(const ManagerInterfacePtr& p) : requestIdAutoIncrease_(1), pluginManager_(p) {}
28
~CommandPoller()29 CommandPoller::~CommandPoller() {}
30
GetRequestId()31 uint32_t CommandPoller::GetRequestId()
32 {
33 return requestIdAutoIncrease_++;
34 }
35
OnConnect()36 bool CommandPoller::OnConnect()
37 {
38 return Connect(DEFAULT_UNIX_SOCKET_FULL_PATH);
39 }
40
OnCreateSessionCmd(const CreateSessionCmd & cmd,SocketContext & context) const41 bool CommandPoller::OnCreateSessionCmd(const CreateSessionCmd& cmd, SocketContext& context) const
42 {
43 HILOG_DEBUG(LOG_CORE, "%s:proc", __func__);
44 if (cmd.buffer_sizes().size() == 0 || cmd.plugin_configs().size() == 0) {
45 HILOG_ERROR(LOG_CORE, "%s:cmd invalid!", __func__);
46 return false;
47 }
48 uint32_t bufferSize = cmd.buffer_sizes(0);
49 ProfilerPluginConfig config = cmd.plugin_configs(0);
50 std::vector<ProfilerPluginConfig> configVec;
51 configVec.push_back(config);
52
53 auto pluginManager = pluginManager_.lock(); // promote to shared_ptr
54 CHECK_NOTNULL(pluginManager, false, "promote FAILED!");
55
56 if (!pluginManager->LoadPlugin(config.name())) {
57 HILOG_DEBUG(LOG_CORE, "%s:fail 1", __func__);
58 return false;
59 }
60 int smbFd = -1;
61 int eventFd = -1;
62 if (bufferSize != 0) {
63 HILOG_DEBUG(LOG_CORE, "%s:bufferSize = %d", __func__, bufferSize);
64 smbFd = context.ReceiveFileDiscriptor();
65 eventFd = context.ReceiveFileDiscriptor();
66 int flags = fcntl(eventFd, F_GETFL);
67 HILOG_DEBUG(LOG_CORE, "%s:smbFd = %d, eventFd = %d", __func__, smbFd, eventFd);
68 HILOG_DEBUG(LOG_CORE, "%s:eventFd flags = %X", __func__, flags);
69 }
70 if (!pluginManager->CreateWriter(config.name(), bufferSize, smbFd, eventFd)) {
71 HILOG_DEBUG(LOG_CORE, "%s:createWriter failed!", __func__);
72 return false;
73 }
74 if (!pluginManager->CreatePluginSession(configVec)) {
75 HILOG_DEBUG(LOG_CORE, "%s:createPluginSession failed!", __func__);
76 return false;
77 }
78 HILOG_DEBUG(LOG_CORE, "%s:ok", __func__);
79 return true;
80 }
81
OnDestroySessionCmd(const DestroySessionCmd & cmd) const82 bool CommandPoller::OnDestroySessionCmd(const DestroySessionCmd& cmd) const
83 {
84 HILOG_DEBUG(LOG_CORE, "%s:proc", __func__);
85 if (cmd.plugin_ids().size() == 0) {
86 HILOG_ERROR(LOG_CORE, "%s:cmd invalid!", __func__);
87 return false;
88 }
89 uint32_t pluginId = cmd.plugin_ids(0);
90 std::vector<uint32_t> pluginIdVec;
91 pluginIdVec.push_back(pluginId);
92
93 auto pluginManager = pluginManager_.lock(); // promote to shared_ptr
94 CHECK_NOTNULL(pluginManager, false, "promote FAILED!");
95
96 if (!pluginManager->DestroyPluginSession(pluginIdVec)) {
97 HILOG_DEBUG(LOG_CORE, "%s:destroyPluginSession failed!", __func__);
98 return false;
99 }
100 if (!pluginManager->ResetWriter(pluginId)) {
101 HILOG_DEBUG(LOG_CORE, "%s:resetWriter failed!", __func__);
102 return false;
103 }
104 if (!pluginManager->UnloadPlugin(pluginId)) {
105 HILOG_DEBUG(LOG_CORE, "%s:unloadPlugin failed!", __func__);
106 return false;
107 }
108 HILOG_DEBUG(LOG_CORE, "%s:ok", __func__);
109 return true;
110 }
111
OnStartSessionCmd(const StartSessionCmd & cmd,PluginResult & result) const112 bool CommandPoller::OnStartSessionCmd(const StartSessionCmd& cmd, PluginResult& result) const
113 {
114 HILOG_DEBUG(LOG_CORE, "%s:proc", __func__);
115 if (cmd.plugin_ids().size() == 0 || cmd.plugin_configs().size() == 0) {
116 HILOG_ERROR(LOG_CORE, "%s:cmd invalid!", __func__);
117 return false;
118 }
119 std::vector<uint32_t> pluginIds;
120 pluginIds.push_back(cmd.plugin_ids(0));
121 std::vector<ProfilerPluginConfig> configVec;
122 configVec.push_back(cmd.plugin_configs(0));
123
124 auto pluginManager = pluginManager_.lock(); // promote to shared_ptr
125 CHECK_NOTNULL(pluginManager, false, "promote FAILED!");
126
127 if (!pluginManager->StartPluginSession(pluginIds, configVec, result)) {
128 HILOG_DEBUG(LOG_CORE, "%s:start Session failed!", __func__);
129 return false;
130 }
131 HILOG_DEBUG(LOG_CORE, "%s:OK", __func__);
132 return true;
133 }
134
OnStopSessionCmd(const StopSessionCmd & cmd) const135 bool CommandPoller::OnStopSessionCmd(const StopSessionCmd& cmd) const
136 {
137 HILOG_DEBUG(LOG_CORE, "%s:proc", __func__);
138 if (cmd.plugin_ids().size() == 0) {
139 HILOG_ERROR(LOG_CORE, "%s:cmd invalid!", __func__);
140 return false;
141 }
142 std::vector<uint32_t> pluginIds;
143 pluginIds.push_back(cmd.plugin_ids(0));
144
145 auto pluginManager = pluginManager_.lock(); // promote to shared_ptr
146 CHECK_NOTNULL(pluginManager, false, "promote FAILED!");
147
148 if (!pluginManager->StopPluginSession(pluginIds)) {
149 HILOG_DEBUG(LOG_CORE, "%s:stop Session failed!", __func__);
150 return false;
151 }
152 HILOG_DEBUG(LOG_CORE, "%s:ok", __func__);
153 return true;
154 }
155
OnReportBasicDataCmd(const RefreshSessionCmd & cmd) const156 bool CommandPoller::OnReportBasicDataCmd(const RefreshSessionCmd& cmd) const
157 {
158 HILOG_DEBUG(LOG_CORE, "%s:proc", __func__);
159 if (cmd.plugin_ids().size() == 0) {
160 HILOG_ERROR(LOG_CORE, "%s:cmd invalid!", __func__);
161 return false;
162 }
163 std::vector<uint32_t> pluginIds;
164 pluginIds.push_back(cmd.plugin_ids(0));
165
166 auto pluginManager = pluginManager_.lock(); // promote to shared_ptr
167 CHECK_NOTNULL(pluginManager, false, "promote FAILED!");
168
169 if (!pluginManager->ReportPluginBasicData(pluginIds)) {
170 HILOG_ERROR(LOG_CORE, "%s:report basic data failed!", __func__);
171 return false;
172 }
173 HILOG_INFO(LOG_CORE, "%s:ok", __func__);
174 return true;
175 }
176
OnGetCommandResponse(SocketContext & context,::GetCommandResponse & response)177 bool CommandPoller::OnGetCommandResponse(SocketContext& context, ::GetCommandResponse& response)
178 {
179 HILOG_DEBUG(LOG_CORE, "%s:proc", __func__);
180 std::this_thread::sleep_for(std::chrono::milliseconds(SLEEP_TIME));
181 NotifyResultRequest nrr;
182 nrr.set_request_id(1);
183 nrr.set_command_id(response.command_id());
184 PluginResult* pr = nrr.add_result();
185 ProfilerPluginState* status = pr->mutable_status();
186
187 if (response.has_create_session_cmd()) {
188 if (OnCreateSessionCmd(response.create_session_cmd(), context)) {
189 status->set_state(ProfilerPluginState::LOADED);
190 } else {
191 status->set_state(ProfilerPluginState::REGISTERED);
192 }
193 } else if (response.has_destroy_session_cmd()) {
194 if (OnDestroySessionCmd(response.destroy_session_cmd())) {
195 status->set_state(ProfilerPluginState::REGISTERED);
196 } else {
197 status->set_state(ProfilerPluginState::LOADED);
198 }
199 } else if (response.has_start_session_cmd()) {
200 if (OnStartSessionCmd(response.start_session_cmd(), *pr)) {
201 status->set_state(ProfilerPluginState::IN_SESSION);
202 } else {
203 status->set_state(ProfilerPluginState::LOADED);
204 }
205 } else if (response.has_stop_session_cmd()) {
206 if (OnStopSessionCmd(response.stop_session_cmd())) {
207 status->set_state(ProfilerPluginState::LOADED);
208 } else {
209 status->set_state(ProfilerPluginState::IN_SESSION);
210 }
211 } else if (response.has_refresh_session_cmd()) {
212 OnReportBasicDataCmd(response.refresh_session_cmd());
213 status->set_state(ProfilerPluginState::IN_SESSION);
214 } else {
215 HILOG_DEBUG(LOG_CORE, "%s:command Response failed!", __func__);
216 return false;
217 }
218 HILOG_DEBUG(LOG_CORE, "%s:ok id = %d", __func__, nrr.command_id());
219 NotifyResult(nrr);
220 return true;
221 }
222