HACK#74 SystemTap脚本的重复利用

本节使用SystemTap的别名和Tapset功能,重复使用脚本。

Hack#73介绍了捕捉键盘和鼠标的输入的方法。可以直接在这个脚本的基础上不断扩大规模,但是想要重复使用这段输入代码等时,必须多次复制相同的代码,或者必须将大量的代码耗费在不必要的输入处理上。这就使得脚本看起来很复杂。

SystemTap中准备了别名功能和Tapset库功能,各个开发人员就可以重点进行自己想进行的操作,并提高代码的使用性。这里首先介绍别名。

使用别名分离逻辑

别名是为了更方便地重复使用SystemTap的处理程序而设置的别名定义功能。SystemTap,如果只是重复使用部分代码,可以作为函数提取出来,但是处理程序本身就不能这样。这时就可以使用别名为处理程序的预处理部分加上易懂的名字。

别名的格式是probe格式的扩展。在probe后面写上别名,然后在“=”后面写上想要命名的处理程序。下面使用别名来编写用键盘和鼠标移动“@”的程序。


Alias Part

probe input.move.keyboard=kernel.function("input_event"){

rx=0;ry=0

if($type!=1||$code>=256||$value!=1)

next

if($code==103)

ry—

else if($code==108)

ry++

else if($code==105)

rx—

else if($code==106)

rx++

}

global mpos_x=0,mpos_y=0

probe input.move.mouse=kernel.function("input_event"){

rx=0;ry=0

if($type==2){#Relative position

if($code==0)

rx=$value

else if($code==1)

ry=$value

}else if($type==1&&$code==0x145&&$value==0){

Take a finger—Reset position

mpos_x=0;mpos_y=0

}else if($type==3){#Absolute-check slide

if($code==0){

if(mpos_x!=0)

rx=$value-mpos_x

mpos_x=$value;

}else if($code==1){

if(mpos_y!=0)

ry=$value-mpos_y

mpos_y=$value;

}

}

rx/=10;ry/=10;

}

probe input.move=input.move.*{

if(rx==0&&ry==0)

next

}

Logic Part

global x=20,y=20

probe input.move{

x+=rx;y+=ry

}

probe timer.ms(100){

if(x<=0)

x=1

else if(x>=41)

x=40

if(y<=0)

y=1

else if(y>=41)

y=40

ansi_clear_screen()

ansi_cursor_move(x, y)

print("@")

}


可以向别名赋予以字母开头,包括字母、数字和“.”的名称。别名内的局部变量,在使用别名的一方也可以继续使用。另外,还可以将功能上相似的别名组合起来用在其他别名中。在上例中,是将input.move.keyboard和input.move.mouse组合起来作为input.move别名。如别名input.move的定义,指定别名时也可以使用通配符。

通过使用别名,将想做的事情(#Logic Part)简单地表现出来。