汇编语言学习003
学习汇编语言的目的,其实更多是为了学习逆向,因此汇编语言大致就学了这些就要过去了。
下面是一些命令的用法
| 指令名称 |
指令用法 |
备注 |
| test |
test reg,00000001 |
逻辑与add命令相同【按位相同为1才为1】,不同点是不会将结果写入寄存器,所以reg中的值不会改变但是会修改标志位,结果为0,则zf=0 |
| cmp |
cmp o1,o2 |
用于比较整数和字符,会修改标志位;o1>o2,zf=0,cf=0;o1<o2,zf=0,cf=1;o1=o2,zf=1,cf=0 |
| jcc系列 |
|
|
| loop |
loop l1 |
l1表示将要跳到的地址位置;ecx!=0就循环 |
| loopz |
loopz l1 |
ecx!=0&&zf==1;一般用于加减法导致的符号位 |
| loope |
loope l1 |
ecx!=0&&zf==1;一般用于cmp导致的符号位 |
| loopnz |
loopnz l1 |
ecx!=0&&zf==0 |
| loopne |
loopne l1 |
ecx!=0&&zf==0 |
下面是关于选择结构
.if eax>esi
inc eax
.else
inc esi
.endif
下面是while循环
.while ecx > 0
mov esi,esp
dec ecx
.endw
下面是do-while
mov eax,2
xor ecx,ecx
.repeat
mov esi,eax
inc eax
add ecx,1
.until ecx > 3
逻辑移位及算术移位
在左移中,逻辑移位与算术移位相同,都是在低位【最右端】补0
在左移中,逻辑移位在高位【最左端】补0
算术移位在高位【最右端】补符号位
| 指令 |
指令用法 |
备注 |
| shl |
shl eax,1 |
逻辑左移 |
| shr |
shr eax,1 |
逻辑右移 |
| sal |
sal eax,1 |
算术左移 |
| sar |
sar eax,1 |
算术右移 |
| rol |
rol eax,1 |
循环左移 |
| ror |
ror eax,1 |
循环右移;左边的最低位移到右边的最高位 |
| rcl |
rcl eax,1 |
带进位的循环左移 |
| rcr |
rcr eax,1 |
带进位的循环右移;cf也会进入移位的单元 |
| shld |
shld o1,o2,立即数 |
双精度左移;第一个数不能是byte类型,立即数是几,o2中的几位数就好用来补充o1的低位 |
| shrd |
shrd o1,o2,o3 |
双精度右移 |
乘法与除法
无符号乘法
mov a1,5h
mov bl,10h
mul bl ;只有一个参数,代表乘数,被乘数由系统默认
;当乘数位数所在寄存器位数为8:被乘数存储在al中;为16:被乘数存储在ax;为32:被乘数存储在eax
;结果也由系统默认存储
;8*8:结果放在ax中
;16*16:结果的高16位放在dx中,低16位放在ax中
;32*32:结果的高32位放在edx中,低32位放在eax中
有符号乘法
mov eax,12345h
mov ebx,10000h
imul eax,ebx ;结果第一个操作数所在寄存器中,此时of=1;eax=23450000h
imul edx,eax,10000h;第三个操作数一定是立即数,此时,后二者的积存放在第一个寄存器中;edx=23450000h
无符号除法
mov ax,101
mov bl,10
div bl ;只有一个参数,代表除数,被除数由系统默认
;当除数位数所在寄存器位数为8:被除数存储在ax中;为16:被除数存储在dx:ax;为32:被除数存储在edx:eax
;结果也由系统默认存储
;16div8:商放在al中,余数放在ah中
;16div16:商放在ax中,余数放在dx中
;32div32:商放在eax中,余数放在edx中
mov dx,0000h
mov ax,007fh
mov bx,100h
div bx ;ax=00h;dx=7fh
xor edx,edx
mov eax,0000ffffh
mov ebx,0000fff0h
div ebx ;eax=00000001h;edx=0000000fh
扩展加法和减法
;adc 扩展加法
xor edx,edx
mov al,0ffh
add al,0ffh ;al=fe----[11111110] cf=1
adc dl,0 ;dl = dl+0+cf=1=01h
;sbb 扩展减法
mov edx,8
mov eax,1
sub eax,2 ;eax=0ffffffffh cf=1
sbb edx,0 ;edx = edx-0-1=7
通过以上减法计算,就会得到一个结果
0000000800000001h - 0000000000000002h = 00000007ffffffffh ;64位数的减法
ASCII之间的运算
如3344----->33 33 34 34
压缩十进制
如3344----->03 03 04 04
;加法 aaa
mov ah,0 ;方便观察
mov al,'3'
add al,'8'
aaa
or ax,3030h ;加法都是与3030h做或运算
;减法 aas
mov ah,0
mov al,'8'
sub al,'3'
aas
pushf
or al,30h ax值0035h
popf
;乘法---压缩10进制
mov al,3
mov bl,4
mul bl ;ax=0012
aam ;ax值0102h
push 0
过程相关的伪指令
INVOKE
CALL
字符串相关
传送、比较、扫描、保存、加载
;传送: MOVSB MOVSW MOVSD / byte word dword
string1 db "hello world",0
string2 byte 12 dup(?)
cld
mov esi,offset string1
mov edi,offset string2
mov ecx,12
rep movsb ;字符串复制
mov eax,eax
;比较: CMPSB CMPSW CMPSD CMP / STRING BYTE
val1 dword 7000h
val2 dword 6000h
cld
l1:
mov esi,offset val1
mov edi,offset val2
cmpsd
ja l1
mov eax,eax
;扫描: SCASB SCASW SCASD
string db "ABCDEF",0
l1:
mov edi,offset string
mov al,'a'
mov ecx,sizeof string
cld
repne scasb
jnz l1
mov eax,eax
;保存 :STOSB STOSW STOSD
string db 100 dup(?)
mov al,0ffh
mov edi,offset string
mov ecx,100 ;运行100次
cld
rep stosb ;将al的值重复保存
mov eax,eax
;加载 LODSB LODSW LODSD ;从esi指针加载到AL,AX,EAX
结构体与宏定义
;结构体
.data
ni struct
val1 dword ?
val2 dword ?
ni ends
stu ni <>
.code
mov stu.val1,1
mov eax,stu.val1
mov eax,eax
;宏定义
.data
me MACRO charc
mov eax,charc
ENDM
.code
ni 9 ;eax=9
浮点数
浮点数运算指令:F+普通运算指令
内联汇编
C语言中使用汇编语言
int main(void){
_asm mov eax,1
_asm mov esi,eax
return 0;
}
int main(void){
int val = 0;
char a[] = {'h','e','l','l','o'}
_asm{
mov eax,val ;内部可以用外部的变量
mov esi,eax
;赋值为字符串
lea esi,a
}
}
汇编语言暂时停在此处,后再补充。
来源:https://www.cnblogs.com/youxunle/p/14022547.html |