• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1
2# Using HiDumper to Improve Performance
3
4## Introduction
5
6HiDumper is a command line tool that developers, testers, and IDE tool engineers can use to obtain system information necessary for analyzing and locating faults. During application development, you can use HiDumper to obtain the UI component tree information, which can be used with a graphical tool such as ArkUI Inspector to locate layout performance issues. You can also use HiDumper to obtain system data such as memory and CPU usage to evaluate application performance.
7
8This document provides a walkthrough of using HiDumper to analyze application performance. For more details about HiDumper, see [HiDumper](../../device-dev/subsystems/subsys-dfx-hidumper.md)
9
10
11## Viewing Component Information
12
13Compared with ArkUI Inspector, HiDumper allows you to obtain fine-grained component information more flexibly.
14
151. Enable the debug mode of ArkUI.
16    ```
17    hdc shell param set persist.ace.debug.enabled 1
18    ```
192. Restart the application.
203. Obtain the window ID of the current page.
21    ```
22    hdc shell hidumper -s WindowManagerService -a '-a'
23    ```
24
25   ![WinId](figures/hidumper-winid.PNG)
26
27
28   * **hidumper -s**: exports all ability information of the system.
29   * **idumper -s WindowManagerService -a ['-a']**: exports the ability information of the open window. **-a** indicates that the information is printed, and **['-a']** indicates the detailed information to be printed.
30   * **WindowName**: name of the open window. **demo0** is the default window name of the sample application.
31   * The table below lists the mapping between **WindowName** values and built-in application windows.
32
33     | WindowName           | Description  |
34     |----------------------|------|
35     | EntryView            | Home screen  |
36     | RecentView           | Recent Tasks screen|
37     | SystemUi_NavigationB | Three-button navigation|
38     | SystemUi_StatusBar   | Status bar |
39     | ScreenLockWindow     | Magazine unlock  |
40
414. Obtain the component tree file of the target page based on **WinId** (window ID).
42   ```
43   hdc shell hidumper -s WindowManagerService -a '-w 28 -element -c' // 28 is the obtained window ID.
44   ```
45
46   ![FilePath](figures/hidumper-filepath.PNG)
47
48
495. Download the component tree file to the local device. Due to the security mechanism, the path obtained is not a real path. You need to run the **find** command to search for the file.
50   ```
51   hdc shell find /data/ -name arkui.dump
52   ```
53
54   ![CorrectFilePath2](figures/hidumper-filepath2.PNG)
55
56   ```
57   hdc file recv /data/app/el2/100/base/com.example.demo/haps/entry/files/arkui.dump . // Obtain the file and save it to the local device.
58   ```
596. Open the component tree file, which lists the properties of each component, such as the number of child components (**childSize**), component ID, and background color (**BackgroundColor**).
60   ```
61   // Fragment of the arkui.dump file
62   |-> GridItem childSize:1
63     | ID: 22
64     | Depth: 9
65     | IsDisappearing: 0
66     | FrameRect: RectT (360.00, 0.00) - [180.00 x 29.00]
67     | BackgroundColor: #00000000
68     ...
69     |-> Stack childSize:1
70       | ID: 23
71       | Depth: 10
72       | IsDisappearing: 0
73       | FrameRect: RectT (0.00, 0.00) - [180.00 x 29.00]
74       | BackgroundColor: #FFFFFF00
75       ...
76       |-> Stack childSize:1
77         | ID: 24
78         | Depth: 11
79         | IsDisappearing: 0
80         | FrameRect: RectT (0.00, 0.00) - [180.00 x 29.00]
81         | BackgroundColor: #FF0000FF
82         ...
83         |-> Stack childSize:1
84           | ID: 25
85           | Depth: 12
86           | IsDisappearing: 0
87           | FrameRect: RectT (0.00, 0.00) - [180.00 x 29.00]
88           | BackgroundColor: #00000000
89           ...
90           |-> Text childSize:0
91               ID: 26
92               Depth: 13
93               IsDisappearing: 0
94               FrameRect: RectT (83.00, 0.00) - [14.00 x 29.00]
95               BackgroundColor: #00000000
96               ...
97   ```
98
99### Viewing the if/else Component
100
101When **if/else** is used, the **if/else** statement is regarded as a component and exists in the component tree as a node. When you run HiDumper commands, the printed component tree contains the **if/else** component information. (On contrast, in ArkUI Inspector, the **if/else** component is not displayed as a node in the component tree.) In the following code, the **if(this.isShow)** statement is used to create and destroy a **\<Row>** component.
102```
103@Entry
104@Component
105struct ConditionComponent {
106  @State isShow: boolean = true;
107
108  build() {
109    Column() {
110      Button ("Show/Hide")
111        .onClick(() => {
112          this.isShow = !this.isShow
113        })
114      if (this.isShow) {
115        Row()
116          .width(300).height(300).backgroundColor(Color.Pink)
117      }
118    }.width('100%')
119  }
120}
121```
122When **isShow** is set to **true**, the **\<Row>** component is shown. At this time, in the component tree file from HiDumper, you can find that the **if/else** component is created as a node, and the **\<Row>** component is nested as a child component.
123```
124|-> IfElse childSize:1
125  | ID: 9
126  | Depth: 6
127  | IsDisappearing: 0
128  |-> Row childSize:0
129      ID: 12
130      Depth: 7
131      IsDisappearing: 0
132      FrameRect: RectT (135.00, 60.00) - [450.00 x 450.00]
133      BackgroundColor: #FFFFC0CB
134      ParentLayoutConstraint: minSize: [[0.00 x 0.00]]maxSize: [[720.00 x 1136.00]]percentReference: [[720.00 x 1136.00]]parentIdealSize: [[720.00 x NA]]selfIdealSize: [[NA x NA]]
135      top: 60.000000 left: 135.000000
136      Active: 1
137      Visible: 0
138      ...
139```
140When **isShow** is set to **false**, the **\<Row>** component is hidden. At this time, in the component tree file from HiDumper, you can find that the **if/else** component is created as a node, but the **\<Row>** component is not loaded.
141```
142|-> IfElse childSize:0
143    ID: 9
144    Depth: 6
145    IsDisappearing: 0
146```
147
148### Viewing the visibility Attribute
149
150You can use the **visibility** attribute to control the visibility of components. In the following code, the **visibility(this.isVisible)** attribute is used to show and hide the **\<Row>** component.
151```
152@Entry
153@Component
154struct VisibilityComponent {
155  @State isVisible: Visibility = Visibility.Visible;
156
157  build() {
158    Column() {
159      Button("Visible")
160        .onClick(() => {
161          this.isVisible = Visibility.Visible
162        })
163      Button("Hidden")
164        .onClick(() => {
165          this.isVisible = Visibility.Hidden
166        })
167      Button("None")
168        .onClick(() => {
169          this.isVisible = Visibility.None
170        })
171      Row().visibility(this.isVisible)
172        .width(720).height(300).backgroundColor(Color.Pink)
173    }.width('100%')
174  }
175}
176```
177When **isVisible** is set to **Visible**, the **\<Row>** component is shown. At this time, in the component tree file from HiDumper, you can find that the value of **Visible** is **0**, and the width and height of the component in the **FrameRect** attribute are **450**.
178```
179|-> Row childSize:0
180    ID: 13
181    Depth: 6
182    IsDisappearing: 0
183    FrameRect: RectT (135.00, 180.00) - [450.00 x 450.00]
184    BackgroundColor: #FFFFC0CB
185    ParentLayoutConstraint: minSize: [[0.00 x 0.00]]maxSize: [[720.00 x 1136.00]]percentReference: [[720.00 x 1136.00]]parentIdealSize: [[720.00 x NA]]selfIdealSize: [[NA x NA]]
186    top: 180.000000 left: 135.000000
187    Active: 1
188    Visible: 0
189    ...
190```
191When **isVisible** is set to **Hidden**, the **\<Row>** component is hidden. At this time, in the component tree file from HiDumper, you can find that the value of **Visible** is **1**, and the width and height of the component in the **FrameRect** attribute are **450**.
192```
193|-> Row childSize:0
194    ID: 13
195    Depth: 6
196    IsDisappearing: 0
197    FrameRect: RectT (135.00, 180.00) - [450.00 x 450.00]
198    BackgroundColor: #FFFFC0CB
199    ParentLayoutConstraint: minSize: [[0.00 x 0.00]]maxSize: [[720.00 x 1136.00]]percentReference: [[720.00 x 1136.00]]parentIdealSize: [[720.00 x NA]]selfIdealSize: [[NA x NA]]
200    top: 180.000000 left: 135.000000
201    Active: 1
202    Visible: 1
203    ...
204```
205When **isVisible** is set to **None**, the **\<Row>** component is hidden. At this time, in the component tree file from HiDumper, you can find that the value of **Visible** is **2**, and the width and height of the component in the **FrameRect** attribute are **0**.
206```
207|-> Row childSize:0
208    ID: 13
209    Depth: 6
210    IsDisappearing: 0
211    FrameRect: RectT (135.00, 180.00) - [0.00 x 0.00]
212    BackgroundColor: #FFFFC0CB
213    ParentLayoutConstraint: minSize: [[0.00 x 0.00]]maxSize: [[720.00 x 1136.00]]percentReference: [[720.00 x 1136.00]]parentIdealSize: [[720.00 x NA]]selfIdealSize: [[NA x NA]]
214    top: 180.000000 left: 135.000000
215    Active: 1
216    Visible: 2
217    ...
218```
219By comparing the number of components in preceding cases, we can find that:
220* When the **visibility** attribute is used to control the visibility of a component, the component's **Visible** attribute changes based on the settings, but its other structures are created regardless of the settings.
221* When the **visibility** attribute is set to **Hidden**, the component is hidden, but still takes up space on the page.
222
223## Viewing Memory Information
224
225To obtain the memory information of an application:
226
2271. Open the application and run **hdc shell hidumper -s WindowManagerService -a '-a'** to obtain the PID of the application.
2282. Run **hidumper --mem [pid]**, replacing **[pid]** with the actual PID of the application, to obtain the memory information, as shown in the following figure.
229```
230hdc shell hidumper --mem [pid]
231```
232
233![Memory information](figures/hidumper-mem.png)
234
235In general cases, you only need to pay attention to the data in the **Pss Total** column, which provides the physical memory actually used by the application. In this example, the application occupies 53395 KB of memory, including 3411 KB of the ArkUI heap memory (**ark ts heap**) and 45846 KB of the native heap memory.
236
237## Viewing CPU Information
238
239With CPU information from HiDumper, you can identify performance issues regarding CPU usage, which is especially useful when your application involves large computing scenarios. The following example shows how to check the CPU information of the Chat application.
240
2411. Compile the project, install and open the Chat application, and run the following HiDumper command to obtain the PID of the application.
242    ```
243    hdc shell hidumper -s WindowManagerService -a '-a'
244    ```
2452. Run **hidumper --cpuusage [pid]** to obtain the CPU information of the Chat application.
246    ```
247    hdc shell hidumper --cpuusage [pid]
248    ```
249
250    ![CPU information](figures/hidumper-cpu.png)
251
252    Your primary concern would be **Total Usage**, **User Space**, and **Kernel Space**. **Total Usage** shows the total CPU usage of applications, **User Space** shows the CPU usage for simple calculation, and **Kernel Space** shows CPU usage for calling system resources. As shown in the preceding figure, the values of these three items are 11%, 11%, and 0%, indicating that the application does not call system resources. In this case, you only need to check the user space of the application. To view the CPU usage for a specific period of time, run the **hdc shell hidumper --cpuusage [pid]** command multiple times through the shell script, and then export the result to the **/data/log/hidumper** directory of the local device through **hdc shell hidumper --zip --cpuusage**.
253