lua虚拟机字节码修改_【技术分享】Lua程序逆向之Luac字节码与反汇编

作者:非虫

预估稿费:800RMB

投稿方式:发送邮件至linwei#360.cn,或登陆网页版在线投稿

传送门

简介

在了解完了Luac字节码文件的整体结构后,让我们把目光聚焦,放到更具体的指令格式上。Luac字节码指令是整个Luac最精华、也是最具有学习意义的一部分,了解它的格式与OpCode相关的知识后,对于逆向分析Luac,会有事半功倍的效果,同时,也为自己开发一款虚拟机执行模板与引擎打下良好的理论基础。

指令格式分析

Luac指令在Lua中使用Instruction来表示,是一个32位大小的数值。在Luac.bt中,我们将其定义了为Inst结构体,回顾一下它的定义与读取函数:

typedef struct(int pc) {

local int pc_ = pc;

local uchar inst_sz = get_inst_sz();

if (inst_sz == 4) {

uint32 inst;

} else {

Warning("Error size_Instruction.");

}

} Inst ;

定义的每一条指令为uint32,这与ARM处理器等长的32位指令一样,但不同的是,Lua 5.2使用的指令只有40条,也就是说,要为其Luac编写反汇编引擎,比起ARM指令集,在工作量上要少出很多。

Luac指令完整由:OpCode、OpMode操作模式,以及不同模式下使用的不同的操作数组成。

官方5.2版本的Lua使用的指令有四种格式,使用OpMode表示,它的定义如下:

enum OpMode {iABC, iABx, iAsBx, iAx};

其中,i表示6位的OpCode;A表示一个8位的数据;B表示一个9位的数据,C表示一个9位的无符号数据;后面跟的x表示数据组合,如Bx表示B与C组合成18位的无符号数据,Ax表示A与B和C共同组成26位的无符号数据。sBx前的s表示是有符号数,即sBx是一个18位的有符号数。

ABC这些字节大小与起始位置的定义如下:

#define SIZE_C9

#define SIZE_B9

#define SIZE_Bx(SIZE_C + SIZE_B)

#define SIZE_A8

#define SIZE_Ax(SIZE_C + SIZE_B + SIZE_A)

#define SIZE_OP6

#define POS_OP0

#define POS_A(POS_OP + SIZE_OP)

#define POS_C(POS_A + SIZE_A)

#define POS_B(POS_C + SIZE_C)

#define POS_BxPOS_C

#define POS_AxPOS_A

从定义中可以看来,从位0开始,ABC的排列为A->C->B。

以小端序为例,完整的指令格式定义如下表所示:

先来看最低6位的OpCode,在Lua中,它使用枚举表示,5.2版本的Lua支持40条指令,它们的定义如下所示:

typedef enum {

/*----------------------------------------------------------------------

nameargsdescription

------------------------------------------------------------------------*/

OP_MOVE,/*A BR(A) := R(B)*/

OP_LOADK,/*A BxR(A) := Kst(Bx)*/

OP_LOADBOOL,/*A B CR(A) := (Bool)B; if (C) pc++*/

OP_LOADNIL,/*A BR(A) := ... := R(B) := nil*/

OP_GETUPVAL,/*A BR(A) := UpValue[B]*/

OP_GETGLOBAL,/*A BxR(A) := Gbl[Kst(Bx)]*/

OP_GETTABLE,/*A B CR(A) := R(B)[RK(C)]*/

OP_SETGLOBAL,/*A BxGbl[Kst(Bx)] := R(A)*/

OP_SETUPVAL,/*A BUpValue[B] := R(A)*/

OP_SETTABLE,/*A B CR(A)[RK(B)] := RK(C)*/

......

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值