Qualcomm Robotics RB5 平台软件用户指南(16)
6.5 调试用户空间
本节介绍用户空间的调试过程。
6.5.1 运行系统跟踪
和跟踪系统Strace调用拦截并记录由进程调用的系统调用。
在用例期间运行命令来收集strace:
starce -p <PID>
6.5.2 通过用户空间中的代码触发回溯
要获取回溯,请包含<execinfo.h>头文件并调用 API int backtrace (void **buffer, int size)。
6.5.3 检查应用程序使用的内存
要按进程检查内存泄漏,请使用 Procrank 工具。 Procrank 工具是 QCB5165 设备的一部分。在用例期间循环运行 Procrank 工具并监控流程的 PSS。
6.5.4 收集Ftrace
FTrace 是分析平台系统级功耗和性能状态的首选工具。
运行以下脚本收集Ftrace:
echo 0 > /sys/kernel/debug/tracing/tracing_on
echo 90000 > /sys/kernel/debug/tracing/buffer_size_kb
cat /sys/kernel/debug/tracing/buffer_size_kb
echo "" > /sys/kernel/debug/tracing/set_event
echo "" > /sys/kernel/debug/tracing/trace
echo power:cpu_idle power:cpu_frequency power:cpu_frequency_switch_start >> /sys/kernel/debug/tracing/set_event
echo power:memlat_dev_update power:memlat_dev_meas power:clock_set_rate power:clock_enable power:clock_disable power:bw_hwmon_update power:bw_hwmon_meas >> /sys/kernel/debug/tracing/set_event
echo clk:clk_set_rate clk:clk_enable clk:clk_disable >> /sys/kernel/debug/tracing/set_event
echo irq:* >> /sys/kernel/debug/tracing/set_event
echo workqueue:workqueue_execute_end workqueue:workqueue_execute_start workqueue:workqueue_activate_work workqueue:workqueue_queue_work >> /sys/kernel/debug/tracing/set_event
echo kgsl:kgsl_pwrlevel kgsl:kgsl_buslevel kgsl:kgsl_pwr_set_state >> /sys/kernel/debug/tracing/set_event
echo regulator:regulator_set_voltage_complete regulator:regulator_disable_complete regulator:regulator_enable_complete >> /sys/kernel/debug/tracing/set_event
cat /sys/kernel/debug/tracing/set_event
cd /sys/kernel/debug/tracing/set_event
sleep 3 && echo 1 > tracing_on && sleep 30 && echo 0 > tracing_on && cat trace > /data/trace-cpu.txt &
Trace-cpu.txt文件包含跟踪打印,可以使用pytimechart等跟踪分析工具来分析它的瓶颈。
有关更多信息,请参阅https://pythonhosted.org/pytimechart/userguide.html。
6.5.5 运行时钟转储
时钟转储对于分析功耗和散热问题很有用。可以在用例期间运行以下脚本来获取所有子系统的频率。
-
使用以下命令连接 USB。
adb root
adb shell
sleep 5 && while true; do echo \=\=\=\=\=\=\=\=\=\=\=\=\=\=\=\=\=\=\=; cat /proc/uptime; cat /sys/kernel/debug/clk/enabled_clocks; sleep 20; done > /data/enabled_clks.txt & //Unplug USB when PID is shown. Wait for 10 minutes to collect the log.
-
10 分钟后将 USB 插回设备,并使用以下命令停止 PID。
adb shell "kill [PID]"
adb pull /data/enabled_clks.txt
笔记
如果/sys/kernel/debug/clk/enabled_clocks不可用,则使用路径/sys/kernel/debug/clk/clk_enabled_list。
6.5.6 调试GPU繁忙状态
要检查 GPU 的使用情况,请执行以下操作:
-
运行预期的用例。 有关更多信息,请参阅多媒体用例。
-
使用.pl扩展名保存以下脚本( busy.pl )。debugfs在运行脚本之前 检查节点。
#!/usr/bin/perl -w adb shell mount -t debugfs none /sys/kernel/debug`; while(1) { $oxili_gfx3d_clk_measure = `adb shell cat "/sys/kernel/debug/clk/gpucc_gfx3d_clk/clk_rate"`; chomp $oxili_gfx3d_clk_measure; $bmc_clk_rate = `adb shell "cat /sys/kernel/debug/clk/measure_only_mccc_clk/clk_measure"`; chomp $bmc_clk_rate; #$mmfab_clk_rate = `adb shell cat "/sys/kernel/debug/clk/mmss_mmssnoc_axi_clk/measure"`; 1.chomp $mmfab_clk_rate; $afab_clk_rate = `adb shell cat "sys/kernel/debug/clk/snoc_clk/clk_rate"`; chomp $afab_clk_rate; $cpu0 = `adb shell "cat /sys/devices/system/cpu/cpu0/cpufreq/scaling_cur_freq"`; chomp $cpu0; $cpu1 = `adb shell "cat /sys/devices/system/cpu/cpu1/cpufreq/scaling_cur_freq"`; chomp $cpu1; $cpu2 = `adb shell "cat /sys/devices/system/cpu/cpu2/cpufreq/scaling_cur_freq"`; chomp $cpu2; $cpu3 = `adb shell "cat /sys/devices/system/cpu/cpu3/cpufreq/scaling_cur_freq"`; chomp $cpu3; $text = sprintf("GPU %u BMIC %u AFAB %u", $oxili_gfx3d_clk_measure,$bmc_clk_rate, $afab_clk_rate); print "$text\n"; $text = sprintf("CPU0 %u CPU1 %u CPU2 %u CPU3 %u", $cpu0, $cpu1, $cpu2, $cpu3); #$text = sprintf("CPU0 %u CPU1 %u", $cpu0, $cpu1); print "$text\n"; &busy; print "\n"; sleep 1 ;
-
如果成功,将显示以下 GPU 繁忙输出消息。
6.5.7 检查可用内存
使用以下命令:
adb shell cat /proc/meminfo
Total free memory = MemFree + Cached
6.5.8 测量DDR时钟(DDR状态)
运行以下命令:
adb shell cat /sys/kernel/debug/clk/measure_only_mccc_clk/clk_measure
6.6 Valgrind调试程序
Valgrind 是一个用于内存调试、内存泄漏检测和分析的编程工具。默认情况下,Valgrind 二进制文件是作为 QRB5165 设备的一部分构建的。
Valgrind 工具套件提供了许多调试和分析工具(例如 Memcheck),有助于使您的程序更快、更正确。它可以检测 C 和 C++ 程序中常见的许多与内存相关的错误,这些错误可能导致崩溃和不可预测的行为。
Valgrind 可以检测以下与内存相关的问题:
- 使用未初始化的内存
- 释放内存后读/写内存
- 读/写分配块的末尾(上溢/下溢)
- 内存泄漏
- malloc/new/new[]vs的使用不匹配free/delete/delete[]
- 双重释放内存
以下命令用于运行 Valgrind:
$ valgrind <list of flags> <path to executable>
Valgrind 命令标志
- –tool=memcheck:检查未初始化的内存或访问已释放的内存。
- –leak-check=full:详细显示每个单独的泄漏。
- –show-leak-kinds=all:在完整报告中显示所有确定的、间接的、可能的、可到达的泄漏类型。
- –track-origins=yes:优先考虑有用的输出而不是速度。此参数跟踪未初始化值的来源,这对于内存错误可能很有用。如果 Valgrind 慢得令人无法接受,请考虑关闭。
- –log-file:写入文件。
6.6.1 运行 Valgrind
使用以下命令运行程序的 Valgrind。
valgrind <option flags> --log-file=<log file name> <executable>
例子:
valgrind --tool=memcheck --leak-check=yes --show-reachable=yes --num-callers
=20 --track-fds=yes gst-launch-1.0 -e qtiqmmfsrc name=qmmf ! video/x-h264,format
=NV12,width=1920,height=1080,framerate=30/1 ! filesink location="/data/vid.h264"
示例输出:
==5356== LEAK SUMMARY:
==5356== definitely lost: 16,384 bytes in 1 blocks
==5356== indirectly lost: 0 bytes in 0 blocks
==5356== possibly lost: 6,286 bytes in 79 blocks
==5356== still reachable: 1,720,821 bytes in 21,010 blocks
==5356== of which reachable via heuristic:
==5356== length64 : 120 bytes in 3 blocks
==5356== newarray : 1,552 bytes in 17 blocks
==5356== multipleinheritance: 152 bytes in 1 blocks
==5356== suppressed: 0 bytes in 0 blocks
==5356==
==5356== For counts of detected and suppressed errors, rerun with: -v
==5356== Use --track-origins=yes to see where uninitialised values come from
==5356== ERROR SUMMARY: 192 errors from 110 contexts (suppressed: 0 from 0)
笔记
示例使用 valgrind-3.15.0 版本。