• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 2024 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 "collect_device_client.h"
16 
17 #include <cstring>
18 #include <iostream>
19 #include <memory>
20 #include <vector>
21 
22 #include <fcntl.h>
23 #include <sys/ioctl.h>
24 #include <sys/types.h>
25 #include <unistd.h>
26 
27 #include "hiview_logger.h"
28 #include "securec.h"
29 
30 #define UNIFIED_COLLECTION_DEVICE  "/dev/ucollection"
31 namespace OHOS {
32 namespace HiviewDFX {
33 DEFINE_LOG_TAG("UDeviceCli");
34 namespace {
35     constexpr int PID_ALL = 0;
36     constexpr unsigned int PROCESS_ONLY_ONE_COUNT = 1;
37     constexpr unsigned int ADD_COUNT = 30;
38 }
39 
CollectDeviceClient()40 CollectDeviceClient::CollectDeviceClient(): fd_(-1)
41 {}
42 
~CollectDeviceClient()43 CollectDeviceClient::~CollectDeviceClient()
44 {
45     if (fd_ > 0) {
46         close(fd_);
47     }
48 }
49 
GetDeviceFd(bool readOnly)50 int CollectDeviceClient::GetDeviceFd(bool readOnly)
51 {
52     int f = 0;
53     if (readOnly) {
54         f = open(UNIFIED_COLLECTION_DEVICE, O_RDONLY);
55     } else {
56         f = open(UNIFIED_COLLECTION_DEVICE, O_WRONLY);
57     }
58 
59     if (f < 0) {
60         HIVIEW_LOGE("Cannot open file=%{public}s, readOnly=%{public}d", UNIFIED_COLLECTION_DEVICE, readOnly);
61         return -1;
62     }
63     HIVIEW_LOGD("open ucollection device readOnly=%{public}d successful", readOnly);
64     return f;
65 }
66 
Open()67 int CollectDeviceClient::Open()
68 {
69     fd_ = GetDeviceFd(true);
70     return (fd_ > 0) ? 0 : -1;
71 }
72 
GetProcessCount()73 unsigned int CollectDeviceClient::GetProcessCount()
74 {
75     HIVIEW_LOGD("send IOCTRL_COLLECT_PROC_COUNT");
76     unsigned int processCount = 0;
77     int ret = ioctl(fd_, IOCTRL_COLLECT_PROC_COUNT, &processCount);
78     if (ret < 0) {
79         HIVIEW_LOGE("ioctl IOCTRL_COLLECT_PROC_COUNT, ret=%{public}d", ret);
80         return 0;
81     }
82     return processCount;
83 }
84 
FetchProcessCpuData()85 std::shared_ptr<ProcessCpuData> CollectDeviceClient::FetchProcessCpuData()
86 {
87     unsigned int processCount = GetProcessCount();
88     HIVIEW_LOGD("send IOCTRL_COLLECT_ALL_PROC_CPU");
89     std::shared_ptr<ProcessCpuData> data = std::make_shared<ProcessCpuData>(IOCTRL_COLLECT_ALL_PROC_CPU, PID_ALL,
90         processCount + ADD_COUNT);
91     int ret = ioctl(fd_, IOCTRL_COLLECT_ALL_PROC_CPU, data->entry_);
92     if (ret < 0) {
93         HIVIEW_LOGE("ioctl IOCTRL_COLLECT_ALL_PROC_CPU ret=%{public}d", ret);
94         return data;
95     }
96     return data;
97 }
98 
FetchProcessCpuData(int pid)99 std::shared_ptr<ProcessCpuData> CollectDeviceClient::FetchProcessCpuData(int pid)
100 {
101     HIVIEW_LOGD("send IOCTRL_COLLECT_THE_PROC_CPU");
102     std::shared_ptr<ProcessCpuData> data = std::make_shared<ProcessCpuData>(IOCTRL_COLLECT_THE_PROC_CPU, pid,
103         PROCESS_ONLY_ONE_COUNT);
104     int ret = ioctl(fd_, IOCTRL_COLLECT_THE_PROC_CPU, data->entry_);
105     if (ret < 0) {
106         HIVIEW_LOGE("ioctl IOCTRL_COLLECT_THE_PROC_CPU ret=%{public}d", ret);
107         return data;
108     }
109     return data;
110 }
111 
GetThreadCount(int pid)112 unsigned int CollectDeviceClient::GetThreadCount(int pid)
113 {
114     HIVIEW_LOGD("send IOCTRL_COLLECT_THREAD_COUNT");
115     struct ucollection_process_thread_count threadCount {pid, 0};
116     int ret = ioctl(fd_, IOCTRL_COLLECT_THREAD_COUNT, &threadCount);
117     if (ret < 0) {
118         HIVIEW_LOGE("ioctl IOCTRL_COLLECT_PROC_THREAD_COUNT ret=%{public}d", ret);
119         return 0;
120     }
121     return threadCount.thread_count;
122 }
123 
GetSelfThreadCount(int pid)124 unsigned int CollectDeviceClient::GetSelfThreadCount(int pid)
125 {
126     HIVIEW_LOGD("send IOCTRL_COLLECT_APP_THREAD_COUNT");
127     struct ucollection_process_thread_count threadCount {pid, 0};
128     int ret = ioctl(fd_, IOCTRL_COLLECT_APP_THREAD_COUNT, &threadCount);
129     if (ret < 0) {
130         HIVIEW_LOGE("ioctl IOCTRL_COLLECT_APP_THREAD_COUNT ret=%{public}d", ret);
131         return 0;
132     }
133     return threadCount.thread_count;
134 }
135 
FetchThreadCpuData(int pid)136 std::shared_ptr<ThreadCpuData> CollectDeviceClient::FetchThreadCpuData(int pid)
137 {
138     HIVIEW_LOGD("send IOCTRL_COLLECT_THE_THREAD");
139     unsigned int threadCount = GetThreadCount(pid);
140     if (threadCount <= 0) {
141         HIVIEW_LOGE("ioctl GetThreadCount error");
142         return nullptr;
143     }
144     auto data = std::make_shared<ThreadCpuData>(IOCTRL_COLLECT_THE_THREAD, pid, threadCount);
145     int ret = ioctl(fd_, IOCTRL_COLLECT_THE_THREAD, data->entry_);
146     if (ret < 0) {
147         HIVIEW_LOGE("ioctl FetchThreadData, ret=%{public}d", ret);
148         return data;
149     }
150     return data;
151 }
152 
FetchSelfThreadCpuData(int pid)153 std::shared_ptr<ThreadCpuData> CollectDeviceClient::FetchSelfThreadCpuData(int pid)
154 {
155     HIVIEW_LOGD("send IOCTRL_COLLECT_APP_THREAD, cmd=%{public}zu", IOCTRL_COLLECT_APP_THREAD);
156     unsigned int threadCount = GetSelfThreadCount(pid);
157     if (threadCount <= 0) {
158         HIVIEW_LOGE("ioctl GetSelfThreadCount error");
159         return nullptr;
160     }
161     auto data = std::make_shared<ThreadCpuData>(IOCTRL_COLLECT_APP_THREAD, pid, threadCount);
162     int ret = ioctl(fd_, IOCTRL_COLLECT_APP_THREAD, data->entry_);
163     if (ret < 0) {
164         HIVIEW_LOGE("ioctl FetchSelfThreadCpuData, ret=%{public}d", ret);
165         return data;
166     }
167     return data;
168 }
169 } // HiviewDFX
170 } // OHOS
171