【shell】linux设备 通过捕捉event实现简单UI自动化
Posted
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了【shell】linux设备 通过捕捉event实现简单UI自动化相关的知识,希望对你有一定的参考价值。
参考技术A 这边收到了很多ai硬件设备,需要做压力测试、稳定性测试。苦于非安卓系统,不能借助input tap等方式进行ui自动化,也没找到合适的工具。上网查了资料加上自己多次测试排了一些坑,基本可以通过捕捉event实现简单UI自动化。/dev/input目录下的事件都是在驱动中调用input_register_device(struct input_dev *dev)产生的。
每个event将上报指定的事件:
比如:
通常触摸屏事件就会上报坐标轴事件,电源键比如按下是 1,松开是 0。而与event对应的相关设备信息位于/proc/bus/input/devices。可以直接cat 查看devces信息。小米手机为例:
首先要会捕捉触摸屏以及所需要控制的按键事件,安卓系统比较简单,用自带的getevent就可以了。这边用小米手机为例:
我这边使用的触摸屏事件,打印的event1信息,可以理解为event1上报触摸屏事件。同样,使用电源键、音量键、home键也会用不同的event信息打印:
这里对应event0、event3、event4
但是在绝大多数linux是没有的!!!(有时候BSP对带,which一下就知道了)
如果没有的话只能编译一个放进去,这里推荐evtest
编译方法:
注:arm设备需要使用特定的交叉编译工具,否则可能无法执行;
方法:evtest /dev/input/event
通过evtest.c可以查看设备事件消息,通过TouchScreen.c可以实现点触摸屏某个坐标
[参考文档]( https://download.csdn.net/download/asd2479745295/10712830 )
编译文件push到设备。./touch xxx yyy
这边在使用时懒得充值,没找到合适的免费资源,找到了另一种解决方法。
( https://www.jianshu.com/p/6b5a172e064a )
可以参考之前一篇模拟快速点击的方法;
捕捉:
使用dd指令
模拟:
1、反向使用
2、可以使用追加
此方法可以模拟点击、滑屏、快速点击,各种实体按键短按、长按、快速点击等。暂时没有找到触摸屏长按的方法,原因是 无法控制长按的时间(追加的速度过快),但是可以通过脚本循环实现。
一个简单的循环,测试可以实现长按,但是不好控制时间,有一个思路是获取获取linux系统时间,在循环体中,true修改成时间条件但是可能打断长按事件。
还有一种可行性高,就是单独做成一个脚本供调用,另一个主脚本控制时间,到时间后kill进程来控制。方法很多,因为工作中没有用到这一项就没测试了。
1、ubuntu下编译解决。
2、捕捉的evest为空
数据量太少,dd的版本较低。更新busybox或者dd版本
3、while((1))报错
设备没有bash,只有sh,修改为while((true))可以解释通过。
shell脚本进阶之信号的捕捉
shell脚本之信号的捕捉? trap,翻译过来就是陷阱的意思,shell脚本中的陷阱是专门用来捕捉信号的。啥信号呢?比如经常使用的kill -9,kill -15,CTRL+C等都属于信号
1、查看所有可用的信号
trap -l或kill -l即可
[root@linux1 ~]# kill -l
63) SIGRTMAX-1 64) SIGRTMAX
[root@linux1 ~]# trap -l
1) SIGHUP 2) SIGINT 3) SIGQUIT 4) SIGILL 5) SIGTRAP
6) SIGABRT 7) SIGBUS 8) SIGFPE 9) SIGKILL 10) SIGUSR1
11) SIGSEGV 12) SIGUSR2 13) SIGPIPE 14) SIGALRM 15) SIGTERM
......
2、常见的信号如下:
Signal Value Comment
─────────────────────────────
SIGHUP 1 终止进程,特别是终端退出时,此终端内的进程都将被终止
SIGINT 2 中断进程,几乎等同于sigterm,会尽可能的释放执行clean-up,释放资源,保存状态等(CTRL+C)
SIGQUIT 3 从键盘发出杀死(终止)进程的信号
SIGKILL 9 强制杀死进程,该信号不可被捕捉和忽略,进程收到该信号后不会执行任何clean-up行为,所以资源不会释放,状态不会保存
SIGTERM 15 杀死(终止)进程,几乎等同于sigint信号,会尽可能的释放执行clean-up,释放资源,保存状态等
SIGSTOP 19 该信号是不可被捕捉和忽略的进程停止信息,收到信号后会进入stopped状态
SIGTSTP 20 该信号是可被忽略的进程停止信号(CTRL+Z)
真正的信号名字不是SIGXXX,而是去除SIG后的单词,每个信号还有对应的代号
比如向PID为12345的进程发起1信号
kill -1 12345
kill -HUB 12345
kill -SIGHUB 12345
3、trap的选项
trap -l列出当前系统支持的信号列表,上面已经使用过,根kill -l一样
trap -p等价于trap,查看shell已经布置好的陷阱
可以看到shell默认有三个陷阱,表示忽略20,21,22信号
[root@linux1 ~]# trap
trap -- ‘‘ SIGTSTP
trap -- ‘‘ SIGTTIN
trap -- ‘‘ SIGTTOU
4、陷阱捕捉到信号后干嘛
- 忽略信号
- 捕捉到信号后做相应的处理。主要是清理一些脚本创建的临时文件,然后退出。
5、设置一个可以忽略CTRL+C和15信号的陷阱
CTRL信号对应的是SIGINT 15信号对应的是SIGTERM
[root@linux1 ~]# trap ‘‘ SIGINT SIGTERM
[root@linux1 ~]# trap
trap -- ‘‘ SIGINT
trap -- ‘‘ SIGTERM
trap -- ‘‘ SIGTSTP
trap -- ‘‘ SIGTTIN
trap -- ‘‘ SIGTTOU
这样,当前shell就不能被kill -15杀死
6、设置一个陷阱,捕捉到-15信号时,就打印“我抓到你啦~”
[root@linux1 ~]# trap ‘echo "我抓到你啦~"‘ TERM
[root@linux1 ~]# trap
trap -- ‘‘ SIGINT
trap -- ‘echo "我抓到你啦~"‘ SIGTERM
trap -- ‘‘ SIGTSTP
trap -- ‘‘ SIGTTIN
trap -- ‘‘ SIGTTOU
效果,当我对当前bash发起kill -15信号时就打印出来了
[root@linux1 ~]# echo $$
8827
[root@linux1 ~]# kill -15 8827
我抓到你啦~
[root@linux1 ~]# kill -15 8827
我抓到你啦~
[root@linux1 ~]# kill -15 8827
我抓到你啦~
7、在脚本中设置一个能忽略CTRL+C和CTRL+Z信号的脚本
CTRL+C是2信号,即SIGINT
CTRL+Z是20信号,即SIGTSTP
脚本:
脚本沉睡10s,然后打印success,脚本忽略INT和TSTP信号
[root@linux1 ~]# cat trap.sh
#!/bin/bash
trap ‘‘ SIGINT SIGTSTP
sleep 10
echo success
效果:
<font color=red>CTRL+C也不能阻止我睡觉</font>
[root@linux1 ~]# bash trap.sh
^C^C^Z^Z^C^C^Z^Zccc^Z^Z^Z^C^C^C
success
8、布置一个当脚本被终端时能清理垃圾并立即退出脚本的陷阱
脚本如下:
[root@linux1 ~]# cat trap1.sh
#!/bin/bash
trap ‘echo trap handing...;rm -rf /tmp/$BASHPID;echo TEMP files cleaned;exit‘ SIGINT SIGTERM SIGQUIT SIGHUP
mkdir -p /tmp/$$/
touch /tmp/$$/a..c.txt
sleep 10
echo first sleep success
sleep 10
echo second sleep success
这样,脚本除了SIGKILL信号(kill -9),总能清理掉临时垃圾
效果
刚开始一直不能终止,后来执行了下trap发现前面shell自己设置了一个忽略CTRL+C的陷阱,退出shell重进即可
[root@linux1 ~]# bash trap1.sh
^Ctrap handing...
TEMP files cleaned
9、陷阱的守护对象
陷阱的守护对象是shell进程本身,不会守护shell环境内的子进程。但如果是信号忽略型陷阱,则会守护整个shell进程组使其忽略给定信号。
[root@linux1 ~]# cat trap2.sh
#!/bin/bash
trap ‘echo trap_handle_time: $(date +"%F %T")‘ SIGINT SIGTERM
echo time_start: $(date +"%F %T")
sleep 10
echo time_end1: $(date +"%F %T")
sleep 10
echo time_end2: $(date +"%F %T")
#执行脚本后,新开终端使用kill -15杀死它
[root@linux1 ~]# killall -s SIGTERM trap2.sh
#查看输出情况
[root@linux1 ~]# ./trap2.sh
time_start: 2019-08-27 10:43:48
trap_handle_time: 2019-08-27 10:43:58
time_end1: 2019-08-27 10:43:58
time_end2: 2019-08-27 10:44:08
? 可以发现,kill执行完后,屏幕没有立即打印trap_handle,而是等sleep 10运行完后才打印的。sleep进程都被忽略型trap守护了
? 只要是向shell进程发送的信号,都会等待当前正在运行的命令结束后才处理信号,然后继续脚本向下运行。(实际上,只有当shell脚本中正在执行的操作是信号安全的系统调用时,才会出现信号无法中断进程的情况,而在shell下的各种命令,我们是没法直接知道哪些命令中正在执行的系统调用是系统调用的)。
但sleep命令发起的sleep()调用,是一个信号安全的,所以上面脚本中执行sleep的过程中,信号不会直接中断它们的运行,而是等待它运行完之后再执行信号处理命令。
10、如果shell中针对某信号设置了陷阱,则该shell进程接收到该信号时,<font color=red>会等待其内正在运行的命令结束才开始处理陷阱</font>
11、CTRL+C和SIGINT不是等价的。当某一时刻按下CTRL+C,它是在向整个当前运行的进程组发送SIGINT信号。对shell脚本来说,SIGINT不仅发送给shell脚本进程,还发送给脚本中当前正在运行的进程
[root@linux1 ~]# cat trap2.sh
#!/bin/bash
trap ‘echo trap_handle_time: $(date +"%F %T")‘ SIGINT SIGTERM
echo time_start: $(date +"%F %T")
sleep 10
echo time_end1: $(date +"%F %T")
sleep 10
echo time_end2: $(date +"%F %T")
#执行脚本后,立马CTRL+C
[root@linux1 ~]# bash trap2.sh
time_start: 2019-08-27 10:20:53
^Ctrap_handle_time: 2019-08-27 10:20:54
time_end1: 2019-08-27 10:20:54
time_end2: 2019-08-27 10:21:04
可以发现,CTRL+C后,不仅trap进行处理了,sleep也立马结束了;说明CTRL+C不仅让脚本进程收到了SIGINT信号,也让当前进程收到了SIGINT信号
有点难理解,以后再来看
以上是关于【shell】linux设备 通过捕捉event实现简单UI自动化的主要内容,如果未能解决你的问题,请参考以下文章