1# HiTraceMeter 2 3## Introduction 4 5HiTraceMeter is the OpenHarmony subsystem that provides APIs to implement call chain trace throughout a service process. With HiTraceMeter, you can quickly obtain the run log specific to the call chain of a service process and locate faults in inter-device, inter-process, or inter-thread communications. HiTraceMeter supports event logging in user mode and can collect trace data in user mode and kernel mode for performance trace and analysis. 6 7## Basic Concepts 8 9The HiTraceMeter subsystem consists of three parts: 10 11- JS/C++ HiTraceMeter APIs for application logging 12- hitrace CLI tool for data collection 13- smartperf tool for graphical data analysis 14 15Wherein, HiTraceMeter APIs and the hitrace CLI tool run on the device side, and the smartperf tool runs on the PC side. HiTraceMeter APIs are provided in C++ and JS for event logging, which aims to generate the trace data necessary for performance trace and analysis during the development process. 16 17The hitrace CLI tool is used to collect trace data. It captures trace data flows and saves the data as a text file. 18 19The smartperf tool allows you to perform data analysis manually or use the analysis script for automated data analysis. If you want to get the data analysis done automatically, you need to supply the data file generated by the hitrace CLI tool as the input for the smartperf tool. 20 21 Traces data is classified by trace tag or trace category. Generally, one device subsystem corresponds to one tag. The tag is passed as the **Tag** parameter to event logging APIs. When you use the hitrace CLI tool to collect trace data, only the trace data specified by the **Tag** parameter is collected. Trace data of applications is fixedly labeled as **APP Tag**, and therefore, no **Tag** parameter needs to be passed to JS APIs. The following is a list of trace tags supported by HiTraceMeter. You can view the tags in [hitrace_meter.h](https://gitee.com/openharmony/hiviewdfx_hitrace/blob/master/interfaces/native/innerkits/include/hitrace_meter/hitrace_meter.h). 22 23```cpp 24constexpr uint64_t HITRACE_TAG_NEVER = 0; // This tag is never enabled. 25constexpr uint64_t HITRACE_TAG_ALWAYS = (1ULL << 0); // This tag is always enabled. 26constexpr uint64_t HITRACE_TAG_DLP_CREDENTIAL = (1ULL << 21); // This tag is dlp credential service. 27constexpr uint64_t HITRACE_TAG_ACCESS_CONTROL = (1ULL << 22); // This tag is access control tag. 28constexpr uint64_t HITRACE_TAG_NET = (1ULL << 23); // Net tag. 29constexpr uint64_t HITRACE_TAG_NWEB = (1ULL << 24); // NWeb tag. 30constexpr uint64_t HITRACE_TAG_HUKS = (1ULL << 25); // This tag is huks. 31constexpr uint64_t HITRACE_TAG_USERIAM = (1ULL << 26); // This tag is useriam. 32constexpr uint64_t HITRACE_TAG_DISTRIBUTED_AUDIO = (1ULL << 27); // Distributed audio tag. 33constexpr uint64_t HITRACE_TAG_DLSM = (1ULL << 28); // device security level tag. 34constexpr uint64_t HITRACE_TAG_FILEMANAGEMENT = (1ULL << 29); // filemanagement tag. 35constexpr uint64_t HITRACE_TAG_OHOS = (1ULL << 30); // OHOS generic tag. 36constexpr uint64_t HITRACE_TAG_ABILITY_MANAGER = (1ULL << 31); // Ability Manager tag. 37constexpr uint64_t HITRACE_TAG_ZCAMERA = (1ULL << 32); // Camera module tag. 38constexpr uint64_t HITRACE_TAG_ZMEDIA = (1ULL << 33); // Media module tag. 39constexpr uint64_t HITRACE_TAG_ZIMAGE = (1ULL << 34); // Image module tag. 40constexpr uint64_t HITRACE_TAG_ZAUDIO = (1ULL << 35); // Audio module tag. 41constexpr uint64_t HITRACE_TAG_DISTRIBUTEDDATA = (1ULL << 36); // Distributeddata manager module tag. 42constexpr uint64_t HITRACE_TAG_MDFS = (1ULL << 37); // Mobile distributed file system tag. 43constexpr uint64_t HITRACE_TAG_GRAPHIC_AGP = (1ULL << 38); // Graphic module tag. 44constexpr uint64_t HITRACE_TAG_ACE = (1ULL << 39); // ACE development framework tag. 45constexpr uint64_t HITRACE_TAG_NOTIFICATION = (1ULL << 40); // Notification module tag. 46constexpr uint64_t HITRACE_TAG_MISC = (1ULL << 41); // Notification module tag. 47constexpr uint64_t HITRACE_TAG_MULTIMODALINPUT = (1ULL << 42); // Multi modal module tag. 48constexpr uint64_t HITRACE_TAG_SENSORS = (1ULL << 43); // Sensors mudule tag. 49constexpr uint64_t HITRACE_TAG_MSDP = (1ULL << 44); // Multimodal Sensor Data Platform module tag. 50constexpr uint64_t HITRACE_TAG_DSOFTBUS = (1ULL << 45); // Distributed Softbus tag. 51constexpr uint64_t HITRACE_TAG_RPC = (1ULL << 46); // RPC and IPC tag. 52constexpr uint64_t HITRACE_TAG_ARK = (1ULL << 47); // ARK tag. 53constexpr uint64_t HITRACE_TAG_WINDOW_MANAGER = (1ULL << 48); // window manager tag. 54constexpr uint64_t HITRACE_TAG_ACCOUNT_MANAGER = (1ULL << 49); // account manager tag. 55constexpr uint64_t HITRACE_TAG_DISTRIBUTED_SCREEN = (1ULL << 50); // Distributed screen tag. 56constexpr uint64_t HITRACE_TAG_DISTRIBUTED_CAMERA = (1ULL << 51); // Distributed camera tag. 57constexpr uint64_t HITRACE_TAG_DISTRIBUTED_HARDWARE_FWK = (1ULL << 52); // Distributed hardware fwk tag. 58constexpr uint64_t HITRACE_TAG_GLOBAL_RESMGR = (1ULL << 53); // Global resource manager tag. 59constexpr uint64_t HITRACE_TAG_DEVICE_MANAGER = (1ULL << 54); // Distributed hardware devicemanager tag. 60constexpr uint64_t HITRACE_TAG_SAMGR = (1ULL << 55); // SA tag. 61constexpr uint64_t HITRACE_TAG_POWER = (1ULL << 56); // power manager tag. 62constexpr uint64_t HITRACE_TAG_DISTRIBUTED_SCHEDULE = (1ULL << 57); // Distributed schedule tag. 63constexpr uint64_t HITRACE_TAG_DEVICE_PROFILE = (1ULL << 58); // device profile tag. 64constexpr uint64_t HITRACE_TAG_DISTRIBUTED_INPUT = (1ULL << 59); // Distributed input tag. 65constexpr uint64_t HITRACE_TAG_BLUETOOTH = (1ULL << 60); // bluetooth tag. 66constexpr uint64_t HITRACE_TAG_ACCESSIBILITY_MANAGER = (1ULL << 61); // accessibility manager tag. 67constexpr uint64_t HITRACE_TAG_APP = (1ULL << 62); // App tag. 68 69constexpr uint64_t HITRACE_TAG_LAST = HITRACE_TAG_APP; 70constexpr uint64_t HITRACE_TAG_NOT_READY = (1ULL << 63); // Reserved for initialization. 71constexpr uint64_t HITRACE_TAG_VALID_MASK = ((HITRACE_TAG_LAST - 1) | HITRACE_TAG_LAST); 72``` 73 74## Implementation Principles 75 76HiTraceMeter provides the hitrace CLI tool for capturing trace data in user mode and kernel mode, and provides C++ (innerkits) and JS (kits) APIs for event logging in user mode. Through extending kernel's ftrace functionality, HiTraceMeter can use the trace_marker node of ftrace to write the data, which is written into the user space by event logging APIs, to the kernel buffer. The following figure shows the basic HiTraceMeter architecture. 77 78 79 80![HiTraceMeter architecture](figures/HiTraceMeter.png) 81 82 83 84## Constraints 85 86- The implementation of HiTraceMeter functions and APIs depends on the ftrace functionality, a framework provided by the kernel. It enables developers to add more trace functions via plug-ins. Therefore, make sure that ftrace is enabled before you use HiTraceMeter. 87 For most Linux kernels, ftrace is enabled by default. For details, see the ftrace documentation you may obtain. 88- HiTraceMeter is available only for the mini system and standard system. 89 90 91 92# HiTraceMeter Development 93 94HiTraceMeter development focuses on two parts: JS/C++ event logging APIs and the hitrace CLI tool. 95 96 97 98## When to Use 99 100You may encounter unexpected issues like app freezing during app development or need to view the code's call chain during code debugging. With the APIs provided by HiTraceMeter, you'll be able to trace the application delay and call chain to identify performance problems. 101 102## Available APIs 103 104Only C++ APIs are now open for system developers. If you're developing a JS app, skip this section. The following table describes the APIs applicable to the standard system. You can find the APIs in [hitrace_meter.h](https://gitee.com/openharmony/hiviewdfx_hitrace/blob/master/interfaces/native/innerkits/include/hitrace_meter/hitrace_meter.h). 105 106**Table 1** Sync APIs 107 108| Sync trace | Function | Parameter Description | 109|:---------------------------------------------------------------------------- | --------- | --------------------------------------------------------------------- | 110| void StartTrace(uint64_t label, const std::string& value, float limit = -1); | Starts a synchronous trace.| **label**: trace category.<br>**value**: trace data that indicates the specific status, such as the memory size and queue length.| 111| void FinishTrace(uint64_t label); | Stops a synchronous trace.| **label**: trace category. | 112 113**StartTrace** and **FinishTrace** must be used in pairs, and **FinishTrace** matches the latest **StartTrace**. The two APIs can be used in nested mode. The stack data structure is used for matching during trace data parsing. The **limit** parameter is used for flow control, and you are advised to use the default value. 114 115**Table 2** Async APIs 116 117| Async trace | Function | Parameter Description | 118| ------------------------------------------------------------------------------------------------- | --------- | ---------------------------------------------------------------------------------------------------- | 119| void StartAsyncTrace(uint64_t label, const std::string& value, int32_t taskId, float limit = -1); | Starts an asynchronous trace.| **label**: trace category.<br>**value**: trace data that indicates the specific status, such as the memory size and queue length.<br>**taskId**: ID used to indicate the association of APIs in an asynchronous trace.| 120| void FinishAsyncTrace(uint64_t label, const std::string& value, int32_t taskId); | Stops an asynchronous trace.| **label**: trace category.<br>**value**: trace data that indicates the specific status, such as the memory size and queue length.<br>**taskId**: ID used to indicate the association of APIs in an asynchronous trace.| 121 122 123 124The trace data of **StartAsyncTrace** and **FinishAsyncTrace** is matched based on **value** and **taskId**, and therefore, the two APIs can be used without a strict sequence. In C++ applications, asynchronous traces are seldom used. 125 126**Table 3** Counter APIs 127 128| Counter Trace | Function | Parameter Description | 129| ------------------------------------------------------------------ | ------- | -------------------------------------------------------------- | 130| void CountTrace(uint64_t label, const std::string& name, int64_t); | Count trace.| **label**: trace category.<br>**name**: trace name displayed in the IDE.| 131 132## How to Develop 133 1341. Add the build dependencies to the build configuration file **base\hiviewdfx\hitrace\cmd\BUILD.gn**. 135 136 ``` 137 external_deps = [ "hitrace_native:hitrace_meter"] 138 ``` 139 1402. Add the header file dependencies. 141 142 ```cpp 143 #include "hitrace_meter.h"// Header file for defining APIs 144 ``` 145 1463. When calling an API, pass the trace value as an input parameter. The trace tags currently supported are listed in **hitrace_meter.h**. Assume that the trace tag is **OHOS** and trace data of **func1** and **func2** needs to be captured. After the hitrace command is executed in the shell, the trace data is automatically captured. The captured data includes the function call process and the memory and time consumed during this process. You can use the data to analyze the call process to identify performance problems. 147 148 ```cpp 149 #include "hitrace_meter.h" // Include hitrace_meter.h 150 using namespace std; 151 152 int main() 153 { 154 uint64_t label = BYTRACE_TAG_OHOS; 155 sleep(1); 156 CountTrace(label, "count number", 2000); // Integer trace 157 158 StartTrace(label, "func1Trace", -1); // Trace start point of func1Start 159 sleep(1); 160 StartTrace(label, "func2Trace", -1); // Trace start point of func2Start 161 sleep(2); 162 FinishTrace (label); // Trace end point of func2Trace 163 sleep(1); 164 FinishTrace(label); // Trace end point of func1Trace 165 166 StartAsyncTrace(label, "asyncTrace1", 1234); // Trace start point of asyncTrace1 167 FinishAsyncTrace(label, "asyncTrace1", 1234); // Trace end point of asyncTrace1 168 169 return 0; 170 } 171 ``` 172 1734. On completion of HiTraceMeter building and deployment, start a trace. After you run the application in the shell on the device, trace data will be captured automatically. 174 175 ``` 176 hdc_std shell hitrace -t 10 ohos > .\myapp_demo.ftrace 177 ``` 178 179 You can open the captured data by clicking **Open trace file** in the smartperf tool or dragging the data to the graphics area. For details, see [smartperf](https://toscode.gitee.com/openharmony-sig/smartperf). 180 181## Verification 182 183The following is a demo debugging process, where the **StartTrace** and **FinishTrace** APIs are used in synchronization mode. 184 1851. Write the test code file [hitrace_example.cpp](https://gitee.com/openharmony/hiviewdfx_hitrace/blob/master/cmd/example/hitrace_example.cpp) by adding the **StartTrace** and **FinishTrace** APIs to the code. 186 187 ```cpp 188 int main() 189 { 190 thread t1(ThreadFunc1); 191 t1.join(); 192 193 StartTrace(LABEL, "testStart"); 194 sleep(SLEEP_ONE_SECOND); 195 196 StartTrace(LABEL, "funcAStart", SLEEP_ONE_SECOND); // Trace start point 197 FuncA(); 198 FinishTrace(LABEL); 199 sleep(SLEEP_TWO_SECOND); 200 201 thread t2(ThreadFunc2); 202 t2.join(); 203 204 StartTrace(LABEL, "funcBStart", SLEEP_TWO_SECOND); 205 FuncB(); 206 FinishTrace(LABEL);// Trace end point 207 sleep(SLEEP_TWO_SECOND); 208 209 sleep(SLEEP_ONE_SECOND); 210 FinishTrace(LABEL); 211 FuncC(); 212 213 return 0; 214 } 215 ``` 216 2172. Modify the **base\hiviewdfx\hitrace\cmd\BUILD.gn** file, and start building. 218 219 ``` 220 ohos_executable("hitrace_example") { 221 sources = [ "example/hitrace_example.cpp" ] 222 223 external_deps = [ "hitrace_native:hitrace_meter" ] 224 225 subsystem_name = "hiviewdfx" 226 part_name = "hitrace_native" 227 } 228 229 group("hitrace_target") { 230 deps = [ 231 ":hitrace", 232 ":hitrace_example", 233 ] 234 } 235 ``` 236 2373. Place the **hitrace_example** executable file in the **/system/bin** directory of the device, and run the following commands in sequence in the shell: 238 239 ```shell 240 hitrace --trace_begin ohos 241 hitrace_exampe 242 hitrace --trace_dump 243 ``` 244 245 If the expected trace value is present in the trace data, the capture of trace data is successful. For example: 246 247 ``` 248 <...>-1651 (-------) [002] .... 327.194136: tracing_mark_write: S|1650|H:testAsync 111 249 <...>-1650 (-------) [001] .... 332.197640: tracing_mark_write: B|1650|H:testStart 250 <...>-1650 (-------) [001] .... 333.198018: tracing_mark_write: B|1650|H:funcAStart 251 <...>-1650 (-------) [001] .... 334.198507: tracing_mark_write: E|1650| 252 <...>-1654 (-------) [003] .... 341.201673: tracing_mark_write: F|1650|H:testAsync 111 253 <...>-1650 (-------) [001] .... 341.202168: tracing_mark_write: B|1650|H:funcBStart 254 <...>-1650 (-------) [001] .... 343.202557: tracing_mark_write: E|1650| 255 <...>-1650 (-------) [001] .... 346.203178: tracing_mark_write: E|1650| 256 <...>-1650 (-------) [001] .... 346.203457: tracing_mark_write: C|1650|H:count number 1 257 <...>-1650 (-------) [001] .... 347.203818: tracing_mark_write: C|1650|H:count number 2 258 <...>-1650 (-------) [001] .... 348.204207: tracing_mark_write: C|1650|H:count number 3 259 <...>-1650 (-------) [001] .... 349.204473: tracing_mark_write: C|1650|H:count number 4 260 <...>-1650 (-------) [001] .... 350.204851: tracing_mark_write: C|1650|H:count number 5 261 <...>-1655 (-------) [001] .... 365.944658: tracing_mark_write: trace_event_clock_sync: realtime_ts=1502021460925 262 <...>-1655 (-------) [001] .... 365.944686: tracing_mark_write: trace_event_clock_sync: parent_ts=365.944641 263 ``` 264 265 266 267# Using the hitrace CLI Tool 268 269The hitrace CLI tool is an executable binary program. On an OpenHarmony-powered device, you can run the following commands in the shell to capture kernel's running data. 270 271**Table 4** Command list 272 273| Option | Description | 274| ----------------------------- | -------------------------------------------------------- | 275| -h, --help | Views the help Information. | 276| -b *n*, --buffer_size *n* | Sets the buffer size for trace data in KB. The default value is **2048**. | 277| -t *n*, --time *n* | Sets the trace uptime in seconds, which depends on the time required for analysis. | 278| --trace_clock clock | Sets the type of the clock for adding a timestamp to a trace. The value can be **boot** (default), **global**, **mono**, **uptime**, or **perf**.| 279| --trace_begin | Starts capturing trace data. | 280| --trace_dump | Dumps trace data to the specified position. The default position is the console. | 281| --trace_finish | Stops capturing trace data and dumps trace data to the specified position. The default position is the console. | 282| -l, --list_categories | Lists the trace categories supported by the device. | 283| --overwrite | Sets the action to take when the buffer is full. If this option is used, the latest trace data is discarded. If this option is not used, the earliest trace data is discarded (default). | 284| -o *filename*, --output *filename*| Outputs trace data to the specified file. | 285| -z | Compresses the trace data. | 286 287Examples: 288 289- Query supported labels. 290 291 ``` 292 293 hitrace -l 294 295 ``` 296 297 Alternatively, run the following command: 298 299 ``` 300 301 hitrace --list_categories 302 303 ``` 304 305- Trace ability information for 10 seconds and store the trace data in a buffer of 4 MB. 306 307 ``` 308 309 hitrace -b 4096 -t 10 --overwrite ability > /data/log/mytrace.ftrace 310 311 ``` 312 313- Set the clock type to **mono**. 314 315 ``` 316 317 hitrace --trace_clock mono -b 4096 -t 10 --overwrite ability > /data/log/mytrace.ftrace 318 319 ``` 320 321- Compress the trace data. 322 323 ``` 324 325 hitrace -z -b 4096 -t 10 --overwrite ability > /data/log/mytrace.ftrace 326 327 ``` 328 329 330 331# FAQs 332 333### Incomplete or Empty Data Captured by hitrace 334 335#### Symptom 336 337The data captured by running the hitrace command is incomplete or no data is captured. 338 339#### **Root Cause** 340 341The value of **-t** or **-b** buffer is too small, leading to data loss. 342 343#### Solution 344 345You can set **-t** to **60** and **-b** to **204800** to increase the trace time and buffer size. 346 347 348 349# Reference 350 351For details about HiTraceMeter, see [hiviewdfx_hitrace: Lightweight Distributed Trace](https://gitee.com/openharmony/hiviewdfx_hitrace). 352