文章目录
本系列文章:
Android STB 遥控器适配
Android STB ROM体积精简
Android STB 添加系统接口
Android STB 高效调试技巧
Android STB 海思平台调试
Android STB HDMI开发
Android STB 编译自定义jar
在进行机顶盒ROM开发时,海思是最经常接触到芯片平台之一,所以对于海思平台Debug方式的掌握,是十分有必要的。
一、产品参数
在运营商机顶盒ROM中,常见的海思的芯片产品有两款:Hi3798MV100和Hi3798MV300。
1.1 Hi3798MV100
产品参数如下:
1.2 Hi3798MV300
产品参数如下:
二、网络类&播放类
网络连接问题和播放问题严格来说不是一类问题,但常常关联出现,所以在此归为一大类。同时,这两类问题在日常开发及现网故障中出现的频率比较高,排查起来也比较耗时,因此将日常的调试方式总结一下,会有事半功倍的作用:
1>过滤时移的url
http.request.uri contains “.ts” || http.request.uri contains “.m3u8”
2>设置开机广告静帧
persist.sys.bootanim.playmode=freeze
3>查看PPPOE是否加密
sys.ethernet.password.encrypt值为true代表密码加密,false代表密码不加密。示例如下:
PPPOE密码不加密的log:
01-01 00:00:06.947 D/pppd ( 2166): sent [PAP AuthReq id=0x1 user=“sf” password=“12345678”]
PPPOE密码加密的log:
01-01 00:00:10.277 D/pppd ( 2431): sent [PAP AuthReq id=0x1 user=“sf” password=< hidden>]
4>确认是否具有容灾环境
说简单点,就是一个URL中有主备地址,用来保证视频的正常播放。URL带了"rrsip",即代表该URL具备容灾功能,主地址不通时,可以从备地址操作播放。
5>容灾重试
主备地址切换完还不能连上的,默认系统会继续重连。如果不需要失败后重连功能,需setprop media.hp.net.reconn 0,该属性值默认为1,即失败后重连。
6>DNS解析顺序优先级(Hi3798MV300)
sys.network.priority=4(IPv4优先)
sys.network.priority=6(IPv6优先)
7>双网管场景
即支持两个默认网关的组网环境,在DHCPv6获取地址完后会分别对两个网关进行NS/NA交互,可通过属性persist.sys.dhcpv6.resend.ns控制,该属性为true时,代表启用该功能。
8>错误帧处理
海思对错误帧的处理,默认是"零容忍"的,即播放的视频中,只要有错误帧,视频就不能播放。如果要兼容错误帧,需要将service.media.hiplayer.vdecerr设置为具体数值。例如setprop service.media.hiplayer.vdecerr 1。
9>Option16(Hi3798MV300)
如果进行Ipv6连接的时候需要Option16字段中携带认证信息,需要设置一个属性:setprop persist.ipv6.option16.rfc3315 true。
10>组播花屏事件中的RATIO数值
在花屏过程中收到多少个IPTV_PLAYER_EVT_VID_DATA_ERROR消息,除以这段时间应该收到的帧数,得到的就是ratio值。
11>部分rtsp流不能播放
setprop persist.sys.hiplayer.rtspusetcp true。
12>部分牌照方播放点播界面时花屏,回退卡死
有些APK图形超过720UI(1280x720), 需要预置 persist.graph.cropframe=true 。
13>MediaPlayer -38错误
上层应用调用MediaPlayer方法顺序不当导致。
14>IPV6流不能播放(Hi3798MV100)
media.hp.ipv6设为true。该属性值默认为false,播放IPV4流。
15>HLS切片下载
播放hls格式流时,下载一个切片前,会先判断该切片在不在最新的m3u8里面。如果在,就下这个切片,如果不在,就下最新的m3u8里的第一个切片。
16>service.media.hiplayer.graphic相关问题(Hi3798MV100)
该问题在Patch12版本上可能会有多种现象,比如:“点播频繁快速SEEK过程中概率性出现电视黑屏,视频没有正常显示出来”、“小窗口播放组播流出现掉帧现象”。该属性的意义如下:
true:网络播放,走overlay OTT
本地播放,走android标准输出
false: 网络走VO
由此可知,小窗口播放组播流出现掉帧现象的原因是:走了overlay,导致在同步的帧率计算处理一些问题,导致视频帧不停早丢弃,引起的卡顿。
17>增加直播缓存数据
设置两个属性:media.hp.hls.update.thread=enable & media.hp.hls.live.start=0。
18>获取时长为负数
setprop persist.hisi.media.hp.tsrdsz 256000,可以从片尾多获取一些数据。
19>双栈时概率性切台慢
该问题的原因是:IPV6地址发起连接请求不通时,需要直接跳转IPV4地址发起连接请求,需setprop media.hp.continue.ipv6 false。
20>静帧切台后,回看时上下键切台会黑屏,有声音无视频
setprop persist.sys.win.switch.black true。
21>直播有部分节目不能全屏播放
此时用的是卓影的中间件,解决方法为:persist.sys.video.cvrs 0。参考资料:Android双屏异显功能总结
22>小窗口黑屏
该问题的具体操作是:在详情页界面,未等小窗口加载完毕,切到其他界面然后返回,然后全屏播放,小窗口开始黑屏,然后切到不同界面,小窗口位置一直都是黑屏状态。产生该现象的原因是:静帧切台模式,再创建播放器时也新创建SurfaceView,原来的SurfaceView没有销毁,导致多个全屏window,无法enable,海思仅支持一个全屏的video output。解决方法:setprop media.hp.vod.blackmod true。
23>切台
一段视频播放log如下:
05-19 15:32:44.458 2463 2463 D PinyinIME: …onKeyDown…keyCode :…21 -->按键
05-19 15:32:44.458 2463 2463 D PinyinIME: …onKeyDown…out…21
05-19 15:32:45.413 2806 3286 V MediaPlayer: setDataSource(http://hwltc.tv.cdn.zj.chinamobile.com/PLTV/88888888/224/3221228281/42329182.smil/index.m3u8?fmt=ts2hls&STBID=00420100300400702002ACBB6156E1D0&USERID=72330000771213) —>设置播放url
05-19 15:32:45.469 2806 3286 W MediaPlayer: setDataSource videoRect:left=0 top=0 right=1920 bottom=1080
05-19 15:32:45.676 1512 7026 I HiPlayer: [15:32:45.676] [svr_pctrl.c:5720] report HI_SVR_PLAYER_EVENT_FIRST_FRAME_TIME!
05-19 15:32:45.676 1512 7026 V HisiMediaPlayer: [SWITCH-PG ] HI_SVR_PLAYER_EVENT_FIRST_FRAME_TIME, time:84
05-19 15:32:45.744 2806 3286 D MediaPlayer: recieve MEDIA_INFO_EXTEND_FIRST_FRAME_TIME -->第一帧显示
从按键按下–>设置URL–>显示第一帧,整个时间间隔就是切台时间。
三、系统类
该章节主要介绍一些海思平台上特殊的调试手段。
3.1 输出相关
模拟HDMI线插入事件命令:
1>echo event 16 > /proc/msp/hdmi0
2>hidisp setoutputenable 0 1
模拟HDMI线拔出事件命令:
1>echo event 17 > /proc/msp/hdmi0
2>hidisp setoutputenable 0 0
使用AV输出方式:
hidisp setoutputenable 1 1
HiDisplayManager.setOutputEnable(1,1)
3.2 CEC
CEC待机开关属性:
persist.sys.hdmi.cec,设置为true代表启动CEC待机功能,false关闭。
待机后,电视开机可以唤醒盒子属性:
persist.sys.cec.hardware,设置为true代表可以唤醒,false不能。
3.3 杜比
cat /proc/msp/sys命令可以用来查看终端是否支持杜比,示例如下:
SDK_VERSION: [HiSTBAndroidV600R003C01SPC031_patch5] Build Time: [May 21 2020, 15:38:32]
UNF_VERSION: 3.3.1
CHIP_VERSION: Hi3798MV300
PACKAGE_TYPE: BGA 14*14
DOLBY: NO
DTS: NO
ADVCA: NO
ROVI(Macrovision): NO
HDR10: YES
DolbyVision: NO
“DOLBY”后面的值是“NO”,表示该终端不支持杜比。
cat /proc/hisi/hiplayer00/fileinfo命令可以查看当前播放的视频的信息,其中可以看出文件格式,示例如下:
*****Hisilicon HiPlayer00 Media File Info Begin
Stream type: ES
Source type: LOCAL
File size: 32282624 bytes
Start time: 0:0:0
Duration: 0:3:19
bps: 1295450 bits/s
Is Divx File:NO
Program 0:
video 0 info:
stream idx: 0
stream pid: 480
format: MPEG2
w * h: 352 * 288
fps: 25.0
bps: 0 bits/s
duration: 0:3:19
audio 0 info:
stream idx: 1
stream pid: 128
format: AC3
samplerate: 48000 Hz
bitpersample: 0
channels: 2
bps: 448000 bits/s
lang:
subID: -1
duration: 0:3:18
***Hisilicon HiPlayer00 Media File Info End
“format”后面的值是“AC3”,表示该视频是AC3格式的,即是杜比格式视频。
除了上面的命令, cat /proc/msp/adec00命令也可以用来查看视频是否是杜比格式的,示例如下:
--------------------------- ADEC[00] State --------------------------
WorkState :start
CodecID :0x81f00055
DecoderName :ac3passthrough
Description :hisilicon ac3passthrough decode
*DecodeThreadID :7458
Volume :100
SampleRate :48000
BitWidth :16
Channels :2
*PcmSamplesPerFrame :0
*BitsBytePerFrame :0x1800
StreamFormat :non-packet
*TryDecodetimes :22314
FrameNum(Total/Error) :269/0
FrameUnsupportNum :0
StreamCorruptNum :0
StreamBuf(Total/Use/Percent)(Bytes) :2097152/2096640/99%
StreamBuf(readPos/writePos) :0x75b00/0x75900
OutFrameBuf(Total/Use/Percent) :8/7/87%
GetBuffer(Try/OK) :25276/1439
PutBuffer(Try/OK) :1439/1439
SendStream(Try/OK) :0/0
ReceiveFrame(Try/OK) :264/262
PtsLostNum :0
*DecodeThreadExecTimeOutCnt :0
*DecodeThreadScheTimeOutCnt :0
*DecodeThreadSleepTimeMS :10
AdecDelayMS :0
“DecoderName ”对应的值包含“ac3”,表示该视频是AC3格式的,即是杜比格式视频。
3.4 IGMP
cat /proc/net/igmp命令可以查看终端中IGMP相关信息。
cat /proc/sys/net/ipv4/conf/eth0/force_igmp_version命令可以查看默认使用的组播协议版本。
3.5 系统信息大汇总
/proc/msp是一个重要的目录,很多系统级别的信息,该目录下的文件如下:
*adsp
adec00
avplay00
cipher
demux_chan
demux_chanbuf
demux_filter
demux_main
demux_pcr
demux_port
demux_rec
demux_rec_index
disp0
disp1
hdmi0
hdmi0_ao
hdmi0_sink
hdmi0_vo
hi_gfx2d
hifb0
i2c
ir
isogeny
jpeg
keyled
log
low_delay_statistics
mce
module
omxvdec
pdm
pm
pm_core
pm_cpu
pm_gpu
pm_temp
png
pq
sci0
sci1
sound0
stat
sync00
sys
tde
tuner
tuner_diseqc
tuner_reg
vdec00
vdec_ctrl
vpss00
win0100
cat /proc/msp/log命令可以看不同方面内容相关的log级别,示例如下:
---------------- Log Path ------------------------
log path:
---------------- Store Path ----------------------
store path: /mnt
---------------- Module Log Level ----------------
Log module Level
HI_SYS 1(ERROR)
HI_MODULE 1(ERROR)
HI_LOG 1(ERROR)
HI_PROC 1(ERROR)
HI_MEM 1(ERROR)
HI_STAT 1(ERROR)
HI_PDM 1(ERROR)
HI_DEMUX 1(ERROR)
HI_ADEC 1(ERROR)
HI_AO 1(ERROR)
HI_AI 1(ERROR)
HI_AENC 1(ERROR)
HI_AIAO 1(ERROR)
HI_ADSP 1(ERROR)
HI_VFMW 1(ERROR)
HI_DISP 1(ERROR)
HI_HDMI 1(ERROR)
HI_VO 1(ERROR)
HI_VPSS 1(ERROR)
HI_VDEC 1(ERROR)
HI_VI 1(ERROR)
HI_VENC 1(ERROR)
HI_PQ 1(ERROR)
HI_TDE 1(ERROR)
jpeg 1(ERROR)
HI_JPGE 1(ERROR)
HI_FB 1(ERROR)
HI_PNG 1(ERROR)
HI_GFX2D 1(ERROR)
HI_PVR 1(ERROR)
HI_AVPLAY 1(ERROR)
HI_SYNC 1(ERROR)
VSYNC 1(ERROR)
ASYNC 1(ERROR)
HI_MCE 1(ERROR)
HI_IR 1(ERROR)
HI_I2C 1(ERROR)
HI_SCI 1(ERROR)
HI_GPIO 1(ERROR)
HI_GPIO_I2C 1(ERROR)
HI_TUNER 1(ERROR)
HI_KEYLED 1(ERROR)
HI_CIPHER 1(ERROR)
HI_OTP 1(ERROR)
ca 1(ERROR)
HI_PM 1(ERROR)
HI_KARAOKE 1(ERROR)
MALI 1(ERROR)
hidlna_1593 1(ERROR)
hiplayer_2452 1(ERROR)
hiplayer00_7453 1(ERROR)
echo hi_avplay=2 > /proc/msp/log
echo logsize=XXX > /proc/msp/log
the current logsize is (12)MB, range(1MB~120MB)
echo log=/mnt > /proc/msp/log
echo storepath=/mnt > /proc/msp/log
由上面内容,可以看出不同的log级别,及响应的修改方式。如修改HDMI相关log级别命令为echo hi_hdmi=4 > /proc/msp/log。
cat /proc/msp/disp*可以查看分辨率相关具体信息。
cat /proc/msp/hdmi*可以查看HDMI相关具体信息。
cat /proc/msp/pm_cpu可以查看CPU温度。
四、抓log脚本
4.1 通用型脚本
该类型脚本一般用来辅助排查播放类问题,该脚本中包含了日常问题排查中包含的所有常规log,排查具体问题时选取对应的命令使用即可。示例如下:
setprop persist.hisi.media.hp.loglevel 6
rm /sdcard/.pcap
rm /sdcard/.log
tcpdump -i any -p -s 0 -w /sdcard/tcpdump.pcap &
screenrecord /sdcard/screen.ts &
cat /proc/kmsg > /sdcard/kmsg.log &
logcat -c
logcat -v threadtime -f /sdcard/logcat.log &
{
cat /proc/cmdline /proc/msp/sys >> /sdcard/proc.log
getprop >> /sdcard/proc.log
pm list packages -f >> /sdcard/proc.log
setprop service.media.codec.debug true
setprop service.media.codec.logcat true
cat /sys/module/lowmemorykiller/parameters/adj >> /sdcard/proc.log
cat /sys/module/lowmemorykiller/parameters/minfree >> /sdcard/proc.log
while [ true ]
do
date >> /sdcard/proc.log ; echo >> /sdcard/proc.log
ls /proc/hisi/ /proc/hisi/msp/0 >> /sdcard/proc.log
if [ -d “/proc/hisi/hiplayer00/” ] ; then
echo "## cat /proc/hisi/hiplayer0*/" >> /sdcard/proc.log
cat /proc/hisi/hiplayer0/* >> /sdcard/proc.log
fi
echo “## cat /proc/media-mem” >> /sdcard/proc.log
cat /proc/media-mem >> /sdcard/proc.log
echo “## dumpsys meminfo” >> /sdcard/proc.log
dumpsys meminfo >> /sdcard/proc.log
echo “## procrank -p” >> /sdcard/proc.log
procrank -p >> /sdcard/proc.log
echo “## cat /proc/meminfo” >> /sdcard/proc.log
cat /proc/meminfo >> /sdcard/proc.log
echo “## busybox free” >> /sdcard/proc.log
busybox free >> /sdcard/proc.log
echo “## cat /proc/vmallocinfo” >> /sdcard/proc.log
cat /proc/vmallocinfo >> /sdcard/proc.log
echo “## cat /proc/slabinfo” >> /sdcard/proc.log
cat /proc/slabinfo >> /sdcard/proc.log
echo “## cat /proc/buddyinfo” >> /sdcard/proc.log
cat /proc/buddyinfo >> /sdcard/proc.log
echo "## cat /sys/kernel/debug/ion/heaps/" >> /sdcard/proc.log
cat /sys/kernel/debug/ion/heaps/
echo “## cat /sys/kernel/debug/mali/gpu_memory” >> /sdcard/proc.log
cat /sys/kernel/debug/mali/gpu_memory >> /sdcard/proc.log
echo “## cat /proc/pagetypeinfo” >> /sdcard/proc.log
cat /proc/pagetypeinfo >> /sdcard/proc.log
echo “## dumpsys SurfaceFlinger” >> /sdcard/proc.log
dumpsys SurfaceFlinger >> /sdcard/proc.log
echo “## dumpsys window windows >> /sdcard/proc.log” >> /sdcard/proc.log
dumpsys window windows >> /sdcard/proc.log
echo “## dumpsys activity activities >> /sdcard/proc.log” >> /sdcard/proc.log
dumpsys activity activities >> /sdcard/proc.log
echo “busybox ifconfig” >> /sdcard/log/proc.log
busybox ifconfig >> /sdcard/log/proc.log
echo “## top -m 5 -t -n 1” >> /sdcard/proc.log
top -m 5 -t -n 1 >> /sdcard/proc.log
echo “## cat /proc/msp/demux*” >> /sdcard/proc.log
cat /proc/msp/demux* >> /sdcard/proc.log
echo “## cat /proc/msp/omxvdec” >> /sdcard/proc.log
cat /proc/msp/omxvdec >> /sdcard/proc.log
echo “## cat /proc/msp/0 /proc/msp/disp1” >> /sdcard/proc.log
cat /proc/msp/0 /proc/msp/disp1 >> /sdcard/proc.log
echo “## cat /proc/msp/pm*” >> /sdcard/proc.log
cat /proc/msp/pm* >> /sdcard/proc.log
echo “## cat /proc/net/snmp /proc/net/dev” >> /sdcard/proc.log
cat /proc/net/snmp /proc/net/dev >> /sdcard/proc.log
himd.l 0xf9c30500 0x300 >> /sdcard/proc.log
sleep 2
done
} &
该脚本中内容简单介绍如下:
1>setprop persist.hisi.media.hp.loglevel 6
设置播放事件log等级。
2>rm /sdcard/.pcap;rm /sdcard/.log
删掉之前抓的log和网络包。
3>tcpdump -i any -p -s 0 -w /sdcard/tcpdump.pcap &
在后台抓网络包。
4>screenrecord /sdcard/screen.ts &
在后台录制视频。
5>cat /proc/kmsg > /sdcard/kmsg.log &
在后台保存内核log。
6>logcat -c
清除日志缓存。
7>logcat -v threadtime -f /sdcard/logcat.log &
在后天抓取logcat日志。
8>{ }&
在后台执行组合命令。
9>cat /proc/cmdline /proc/msp/sys >> /sdcard/proc.log
保存内核启动log、一些简要的系统信息。
10>getprop >> /sdcard/proc.log
保存所有的属性。
11>pm list packages -f >> /sdcard/proc.log
保存所有的应用及对应的包名。
12>setprop service.media.codec.debug true;setprop service.media.codec.logcat true
打开播放器编解码log显示开关。
13>cat /sys/module/lowmemorykiller/parameters/adj >> /sdcard/proc.log;cat /sys/module/lowmemorykiller/parameters/minfree >> /sdcard/proc.log
保存lowmemorykiller相关的一些信息。/sys/module/lowmemorykiller/parameters/minfree:里面是以”,”分割的一组数,每个数字代表一个内存级别
/sys/module/lowmemorykiller/parameters/adj:对应上面的一组数,每个数组代表一个进程优先级级别 。举个例子:
/sys/module/lowmemorykiller/parameters/minfree:18432,23040,27648,32256,55296,80640
/sys/module/lowmemorykiller/parameters/adj:0,100,200,300,900,906
代表的意思:两组数一一对应,当手机内存低于80640时,就去杀掉优先级906以及以上级别的进程,当内存低于55296时,就去杀掉优先级900以及以上的进程。
14>while [ true ] do done
循环执行一些脚本。
15>date >> /sdcard/proc.log
保存日期。
16>ls /proc/hisi/ /proc/hisi/msp/0 >> /sdcard/proc.log
保存播放相关的一些信息。
17>cat /proc/hisi/hiplayer0*/* >> /sdcard/proc.log
保存播放相关的一些信息。
18>cat /proc/media-mem >> /sdcard/proc.log
保存多媒体内存使用情况。
19>dumpsys meminfo >> /sdcard/proc.log
保存终端内存使用信息。
20>procrank -p >> /sdcard/proc.log
保存终端内存使用信息。
21>cat /proc/meminfo >> /sdcard/proc.log
保存较详细的内存使用信息。
22>busybox free >> /sdcard/proc.log
保存终端内存使用信息。
23>cat /proc/vmallocinfo >> /sdcard/proc.log
保存内存分配记录。
24>cat /proc/slabinfo >> /sdcard/proc.log
slab分配器相关信息
25>cat /proc/buddyinfo >> /sdcard/proc.log
保存linuxbuddy系统管理物理内存的debug信息。
26>cat /sys/kernel/debug/ion/heaps/. >> /sdcard/proc.log
保存协助排查内存泄漏相关信息。
27>cat /sys/kernel/debug/mali/gpu_memory >> /sdcard/proc.log
保存GPU内存使用情况。
28>cat /proc/pagetypeinfo >> /sdcard/proc.log
保存较详细的内存使用信息。
29>dumpsys SurfaceFlinger >> /sdcard/proc.log
保存系统图层相关信息。
30>dumpsys window windows >> /sdcard/proc.log
保存系统窗口相关信息。
31>dumpsys activity activities >> /sdcard/proc.log
保存系统Activity相关信息。
32>busybox ifconfig >> /sdcard/log/proc.log
保存网络相关信息。
33>top -m 5 -t -n 1 >> /sdcard/proc.log
保存内存占用较大进程信息
34>cat /proc/msp/demux* >> /sdcard/proc.log
保存码流信息。
35>cat /proc/msp/omxvdec >> /sdcard/proc.log
保存码流信息。
36>cat /proc/msp/0 /proc/msp/disp1 >> /sdcard/proc.log
保存显示相关信息。
37>cat /proc/net/snmp /proc/net/dev >> /sdcard/proc.log
保存网络包流量信息。
38>himd.l 0xf9c30500 0x300 >> /sdcard/proc.log
保存操作寄存器信息。
39>sleep 2
2秒不作任何操作。
4.2 特殊脚本
在抓取播放器相关log时,可能会再做一些特殊的操作,如设置一些播放方面的log等级:echo hi_avplay=3 > /proc/msp/log、echo hi_vo=2 > /proc/msp/log等。