首页 > 汇编语言 > 汇编指令 阅读:57,774

串操作指令

< 上一页 逻辑指令 控制转移指令 下一页 >

串处理:rep movs/stos/lods    cmps/scas

格式: REP string primitive

其中String Primitive可为MOVS LODSSTOS指令

执行的操作:

1)(CX)=0则退出REP ,否则往下执行。

2)(CX) <= (CX)-1

3)执行其中的串操作

4)重复1)~3)

CLD(Clear direction flag)该指令使DF=0,在执行串操作指令时可使地址自动增量;

STD(Set direction flag)该指令使DF=1,在执行串操作指令时可使地址自动减量。

 

REP MOVS  BYTE PTR[DI]BYTE PTR[SI]

上面指令将[si]中的值拷贝到[di]位置,然后disi同方向增加或者减少一个字节(由DF值决定),直到ecx中的值为0

 

MOVS 串传送指令

格式:

MOVS  DSTSRC

MOVSB(字节)

MOVSW()

其中第二、三种格式明确地注明是传送字节或字,第一种格式则应在操作数中表明是字还是字节操作,例如:MOVS  ES:BYTE PTR[DI]DS:[SI]

执行的操作:

1)((DI)) <= ((SI))

2)字节操作:

(SI) <= (SI)+(-)1(DI) <=(DI)+(-)1

当方向标志DF=0时用+,当方向标志DF=1时用-

3)字操作:

(SI) <= (SI)+(-)2(DI) <= (DI)+(-)2

当方向标志DF=0时用+,当方向标志DF=1时用-

该指令不影响条件码。

下面是通过汇编实现的字符串n个字节拷贝函数

void strncpy_asm(char *dst, char *src,size_t len)

{

     _asm{

 

     ;mov edi,dst;

     ;mov esi,src;

     ;mov ecx,len;

 

     mov edi, [ebp+8]//目标地址

     mov esi, [ebp+0xc]//源地址

     mov ecx,[ebp+0x10];//ecxrep的次数

 

     cld;//设置DF=0ESI,EDI ++

rep movs byte ptr [edi],byte ptr[esi]

     }

}

 

STOS 存入串指令

格式: 

STOS   DST

STOSB(字节)

STOSW()

执行的操作:

字节操作: ((DI)) <= (AL)(DI) <= (DI)+-1

字操作:   ((DI)) <= (AX)(DI) <= (DI)+-2

该指令把ALAX的内容存入由(DI)指定的附加段的某单元中,并根据DF的值及数据类型修改DI的内容,当它与REP 联用时,可把ALAX的内容存入一个长度为(CX)的缓冲区中。

 

LODS 从串取指令

格式: 

LODS   SRC

LODSB

LODSW

执行的操作:

字节操作:(AL) <= ((SI))(SI) <= (SI)+-1

字操作: (AX) <= ((SI))(SI) <= (SI)+-2

该指令把由(SI)指定的数据段中某单元的内容送到ALAX中,并根据方向标志及数据类型修改SI的内容。指令允许使用段跨越前缀来指定非数据段的存储区。该指令也不影响条件码。一般说来,该指令不和REP 联用。有时缓冲区中的一串字符需要逐次取出来测试时,可使用本指令。

 

lea           edi,[ebp-0C0h]

mov         ecx,30h

mov         eax,0CCCCCCCCh

rep stos   dword ptr es:[edi];

 

上面这段代码是C中函数调用的时候,将栈上局部变量空间,统一设置为CC的汇编代码。CC就是INT 3指令的机器码,所以,一旦有程序出现异常,执行到栈上位置,就会被中断下来,以便发现问题。

 

REPE/REPZREPNZ/REPNE联合工作的CMPSSCAS指令

REPE/REPZ 当相等/为零时重复串操作

格式:  REPE(REPZ) String Primitive

其中String Primitive可为CMPSSCAS指令。

执行的操作:

1)(CX)=0ZF=0(即某次比较的结果两个操作数不等)时退出,否则往下执行

2)(CX)ß(CX)-1

3)执行其后的串指令

4)重复1)~3)

REPNE/REPNZ   当不相等/不为零时重复串操作

格式:  REPNE(REPNZ)    String Primitive

其中String Primitive可为CMPSSCAS指令

执行的操作: 除退出条件(CX==0)ZF==1外,其他操作与REPE完全相同。

 

CMPS  串比较指令

格式:

CMP SRCDST

CMPSB

CMPSW

执行的操作:

1)((SI))-((DI))

2)字节操作:(SI) <= (SI)+-1(DI) <= (DI)+-1

字操作: (SI) <= (SI)+-2(DI) <= (DI)+-2

指令把由(SI)指向的数据段中的一个字(或字节)与由(DI)指向的附加段中的一个字(或字节)相减,但不保存结果,只根据结果设置条件码,指令的其他特性和MOVS 指令的规定相同。

 

SCAS 串扫描指令

格式:

SCAS DST

SCASB

SCASW

执行的操作:

字节操作:(AL)-((DI))(DI) <= (DI)+-1

字操作: (AL)-((DI))(DI) <= (DI)+-2

该指令把AL(AX)的内容与由(DI)指定的在附加段中的一个字节(或字)进行比较,并不保存结果,只根据结果置条件码。指令的其他特性和MOVS 的规定相同。

int strcmp_asm(char *s1, char *s2)

{

__asm{

        mov esi,s1;

        mov edi,s2;

        L1:

        lodsb;lodsb:[esi]<=al,esi=esi+1

        scasb;scasb:al-[edi],edi = edi+1

        jne L2;

        test al,al;判断esi中是否到达字符串末尾

        jne L1;

        xor eax,eax

        jmp L3;

        L2:

        sbb eax,eax;

        or al,1;

        L3:

 

}

}

< 上一页 逻辑指令 控制转移指令 下一页 >

周哥教IT,分享编程知识,提高编程技能,程序员的充电站。跟着周哥一起学习,每天都有进步。

通俗易懂,深入浅出,一篇文章只讲一个知识点。

当你决定关注「周哥教IT」,你已然超越了90%的程序员!

IT黄埔-周哥教IT技术交流QQ群:213774841,期待您的加入!

二维码
微信扫描二维码关注