• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1#!/usr/bin/env python3
2# -*- coding: utf-8 -*-
3# Copyright (C) 2024 Huawei Device Co., Ltd.
4# Licensed under the Apache License, Version 2.0 (the "License");
5# you may not use this file except in compliance with the License.
6# You may obtain a copy of the License at
7#
8#     http://www.apache.org/licenses/LICENSE-2.0
9#
10# Unless required by applicable law or agreed to in writing, software
11# distributed under the License is distributed on an "AS IS" BASIS,
12# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13# See the License for the specific language governing permissions and
14# limitations under the License.
15
16import pytest
17import subprocess
18import re
19import time
20import threading
21import sqlite3
22from string import Template
23import os
24
25
26def get_file_size(file_path):
27    size = os.path.getsize(file_path)
28    return size
29
30
31def task():
32    subprocess.check_output(f'hdc shell "hiprofiler_cmd -c /data/local/tmp/config_memory_plugin.txt -o /data/local/tmp/test_memory_kernel.htrace -t 60 -s -k"')
33
34
35
36def task_vminfo():
37    subprocess.check_output(f'hdc shell "hiprofiler_cmd -c /data/local/tmp/config_memory_vmeminfo.txt -o /data/local/tmp/test_memory_vmeminfo.htrace -t 60 -s -k"')
38
39
40def task_vmtracker():
41    subprocess.check_output(f'hdc shell "hiprofiler_cmd -c /data/local/tmp/config_memory_vmtracker.txt -o /data/local/tmp/test_memory_vmtracker.htrace -t 60 -s -k"')
42
43
44def write_str_file(file_path, large_string):
45    lines = large_string.split('\n')
46    with open(file_path, 'w') as file:
47        for line in lines:
48            file.write(line + '\n')
49
50
51class TestHiprofilerMemoryPlugin:
52    # 检查内核的 memory info
53    @pytest.mark.L0
54    def test_memory_plugin_kernel(self):
55        subprocess.check_output(f"hdc file send ..\inputfiles\memory_plugin\config_memory_plugin.txt /data/local/tmp/", shell=False,
56                                text=True, encoding="utf-8")
57        task_thread = threading.Thread(target=task, args=())
58        task_thread.start()
59
60        task_thread.join()
61        subprocess.run(f'hdc file recv /data/local/tmp/test_memory_kernel.htrace ../outputfiles/', shell=False,
62                         text=True, encoding="utf-8")
63        # 检查文件大小
64        file_size = get_file_size(f"../outputfiles/test_memory_kernel.htrace")
65        assert (file_size > 1024)
66        subprocess.check_output(
67            r"../inputfiles/trace_streamer_db.exe ../outputfiles/test_memory_kernel.htrace -e ../outputfiles/test_memory_kernel.db")
68        # 连接数据库文件
69        conn = sqlite3.connect(r'../outputfiles/test_memory_kernel.db')
70        # # 创建游标对象
71        cursor = conn.cursor()
72        cursor.execute("select * from sys_mem_measure,sys_event_filter where filter_id = id and name ='sys.mem.mapped'")
73        result = cursor.fetchall()
74        row_count = len(result)
75        #检查获得sys_mem 数据是否正确
76        assert(row_count > 0)
77        #检查是否存在map 的事件
78        for row in result:
79            assert(row[3] >= 0)
80        #检查是否存在sys_mem_total 事件
81        cursor = conn.cursor()
82        cursor.execute("select * from sys_mem_measure,sys_event_filter where filter_id = id and name ='sys.mem.total'")
83        result = cursor.fetchall()
84        row_count = len(result)
85        assert(row_count > 0)
86        for row in result:
87            assert(row[3] >= 0)
88        cursor.close()
89        conn.close()
90
91    # 检查内核的 virture memory info stats
92    @pytest.mark.L0
93    def test_memory_plugin_vmeminfo(self):
94        subprocess.check_output(f"hdc file send ..\inputfiles\memory_plugin\config_memory_vmeminfo.txt /data/local/tmp/", shell=False,
95                                text=True, encoding="utf-8")
96        task_thread = threading.Thread(target=task_vminfo, args=())
97        task_thread.start()
98
99        task_thread.join()
100        subprocess.run(f'hdc file recv /data/local/tmp/test_memory_vmeminfo.htrace ../outputfiles/', shell=False,
101                         text=True, encoding="utf-8")
102        # 检查文件大小
103        file_size = get_file_size(f"../outputfiles/test_memory_vmeminfo.htrace")
104        assert (file_size > 1024)
105        subprocess.check_output(
106            r"../inputfiles/trace_streamer_db.exe ../outputfiles/test_memory_vmeminfo.htrace -e ../outputfiles/test_memory_vmeminfo.db")
107        # 连接数据库文件
108        conn = sqlite3.connect(r'../outputfiles/test_memory_vmeminfo.db')
109        # # 创建游标对象
110        cursor = conn.cursor()
111        cursor.execute("select * from sys_mem_measure,sys_event_filter where filter_id = id and name ='sys.virtual.mem.nr.free.pages'")
112        result = cursor.fetchall()
113        row_count = len(result)
114        #检查获得free pages 数据是否正确
115        assert(row_count > 0)
116        #检查是否存在 free pages 的事件
117        for row in result:
118            assert(row[3] >= 0)
119        #检查是否存在active file  事件
120        cursor = conn.cursor()
121        cursor.execute("select * from sys_mem_measure,sys_event_filter where filter_id = id and name ='sys.virtual.mem.nr.active_file'")
122        result = cursor.fetchall()
123        row_count = len(result)
124        assert(row_count > 0)
125        for row in result:
126            assert(row[3] >= 0)
127        cursor.close()
128        conn.close()
129
130    # 检查某一个进程的vm ,观测点,DMA 数据,smaps 数据。
131    @pytest.mark.L0
132    def test_memory_plugin_vmtracker(self):
133        #获得32位还是64位
134        sys_bit = subprocess.run(f"hdc shell getconf LONG_BIT", stdout=subprocess.PIPE, text=True, check=True)
135        sysinfo = sys_bit.stdout
136        if sysinfo.strip() == "32":
137            subprocess.check_output(f"hdc shell aa start -a com.ohos.settings.MainAbility -b com.ohos.settings", shell=False, text=True, encoding="utf-8")
138            time.sleep(2)
139            pid_text = subprocess.run(f"hdc shell pidof 'com.ohos.settings'", stdout=subprocess.PIPE, text=True, check=True)
140        else:
141            #获得该应用的进程PID
142            pid_text = subprocess.run(f"hdc shell pidof 'com.ohos.launcher'", stdout=subprocess.PIPE, text=True, check=True)
143        pidinfo = pid_text.stdout
144        #读文本文件,修改对应的pid
145        file_content = Template('request_id: 1                             \n'
146                                ' session_config {                         \n'
147                                '  buffers {                               \n'
148                                '   pages: 16384                           \n'
149                                '  }                                       \n'
150                                ' }                                        \n'
151                                ' plugin_configs {                         \n'
152                                '  plugin_name: "memory-plugin"            \n'
153                                '  sample_interval: 5000                   \n'
154                                '  config_data {                           \n'
155                                '   report_process_tree: false             \n'
156                                '   report_sysmem_mem_info: false          \n'
157                                '   report_sysmem_vmem_info: false         \n'
158                                '   report_process_mem_info: true          \n'
159                                '   report_app_mem_info: false             \n'
160                                '   report_app_mem_by_memory_service: false\n'
161                                '   pid: ${s1}                             \n'
162                                '   report_purgeable_ashmem_info: true     \n'
163                                '   report_dma_mem_info: true              \n'
164                                '   report_gpu_mem_info: true              \n'
165                                '   report_smaps_mem_info: true            \n'
166                                '   report_gpu_dump_info: true             \n'
167                                '  }                                       \n'
168                                ' }                                        \n')
169        vmfile = file_content.safe_substitute(s1=pidinfo.strip())
170        #写入文件
171        write_str_file("../inputfiles/memory_plugin/config_memory_vmtracker.txt", vmfile)
172
173        subprocess.check_output(f"hdc file send ..\inputfiles\memory_plugin\config_memory_vmtracker.txt /data/local/tmp/", shell=False,
174                                text=True, encoding="utf-8")
175        task_thread = threading.Thread(target=task_vmtracker, args=())
176        task_thread.start()
177        task_thread.join()
178        subprocess.run(f'hdc file recv /data/local/tmp/test_memory_vmtracker.htrace ../outputfiles/', shell=False,
179                         text=True, encoding="utf-8")
180        # 检查文件大小
181        file_size = get_file_size(f"../outputfiles/test_memory_vmtracker.htrace")
182        assert (file_size > 1024)
183        subprocess.check_output(
184            r"../inputfiles/trace_streamer_db.exe ../outputfiles/test_memory_vmtracker.htrace -e ../outputfiles/test_memory_vmtracker.db")
185        # 连接数据库文件
186        conn = sqlite3.connect(r'../outputfiles/test_memory_vmtracker.db')
187        #抓取结束后,检查是否存在hidumper 进程
188        output_text = subprocess.run(f'hdc shell "ps -ef | grep hidumper"', stdout=subprocess.PIPE, text=True, check=True)
189        process_info = output_text.stdout
190        lines = process_info.strip().split('\n')
191        check_index = False
192        for line in lines:
193            if line.find("hidumper -s") != -1:
194                check_index = True
195        # 结束后不存在hidumper 子进程
196        assert (check_index == False)
197        # # 创建游标对象
198        cursor = conn.cursor()
199        cursor.execute("select * from memory_dma limit 0,10")
200        result = cursor.fetchall()
201        row_count = len(result)
202        #检查存在dma 数据
203        assert(row_count > 0)
204        for row in result:
205            assert(row[3] > 0 and row[4] > 0 and row[5] > 0 and row[6] > 0 and row[7] > 0 and row[8] > 0 and row[9] > 0)
206        #检查是否存在smaps
207        cursor.execute("select * from smaps limit 0,10")
208        result = cursor.fetchall()
209        row_count = len(result)
210        assert(row_count > 0)
211        for row in result:
212            assert(row[2] != '' and row[3] != '' and row[7] >= 0 and row[8] >= 0)
213        #检查是否存在GPU数据
214        cursor.execute("select * from memory_process_gpu limit 0,10")
215        result = cursor.fetchall()
216        row_count = len(result)
217        assert(row_count > 0)
218        for row in result:
219            assert(row[3] > 0 and row[7] > 0)
220        cursor.close()
221        conn.close()