C代码+汇编 C的for汇编学习分析
C语言的代码
int main()
{
char myString[30];
for(int i = 0;i < 30;i++){
myString[i] = '#';
}
return 0;
}
反汇编代码 (32位寄存器 VC++ 6.0反汇编代码)
0040B76E mov dword ptr [ebp-24h],0 //将 0 赋值给 ( ebp寄存器的内存地址-24H ) 内存地址 所指向的 值
0040B775 jmp main+30h (0040b780) //直接跳转到 0040b780的地址处
0040B777 mov eax,dword ptr [ebp-24h] //将 (ebp寄存器内存地址-24H)的内存地址 赋值给 eax的寄存器
0040B77A add eax,1 // eax = eax + 1
0040B77D mov dword ptr [ebp-24h],eax //将eax的内存地址 赋值给 (ebp寄存器-24H)指向的内存地址
0040B780 cmp dword ptr [ebp-24h],1Eh //1EH = 30(十进制) 判断 ebp寄存器-24H 所指向的内存地址的值 与 1EH(30)作比较
0040B784 jge main+40h (0040b790) //上面一句 如果大于等于 就跳转到 0040b790的内存地址
0040B786 mov ecx,dword ptr [ebp-24h] // (ebp寄存器-24H)指向的内存地址 赋值给ecx寄存器
0040B789 mov byte ptr [ebp+ecx-20h],23h // 23H 在ASCLL码表中 指 # , 含义为 将# 以单字节的形式 赋值给 ([ebp+ecx-20h)的内存地址
0040B78E jmp main+27h (0040b777) // 直接跳转到 0040b777 指向的内存地址
附图: (还不懂的话 我们接着来往下面)
让我们一句一句的来(代码按照执行逻辑分析)
1.mov dword ptr [ebp-24h],0
寄存器中 ESP寄存区指栈首 EBP寄存器指栈尾 将0以双字类型的形式添加到ebp-24H的内存地址
问题1:为什么是24H呢?
答:24H = 36(十进制),C代码中 char myString[30]; 数组的大小是30, 因为是32位寄存器,四字节,所以是32, 代码中有for循环需要计数, 多了一个计数器存值的内存(我也是看了汇编内存才知道的…)
2.jmp main+30h (0040b780)
直接跳转到 0040b780的内存地址,没有什么好说的. 符合for循环的执行逻辑
- cmp dword ptr [ebp-24h],1Eh
//1EH = 30(十进制) 判断 ebp寄存器-24H 所指向的内存地址的值(19FF1C) 与 1EH(30)作比较
也就是拿 第一句 ebx的值 与 30比较 // C语言代码 i < 30 - jge main+40h (0040b790)
参考上一句 如果ebx>=30则跳转到0040b790的内存地址 也是跳出循环
5.mov ecx,dword ptr [ebp-24h]
个人理解: ecx寄存器一般是计数寄存器,将 ebp寄存器-24H 所指向的内存地址的值(19FF1C) 0 赋值给 ecx寄存器,如图
6.mov byte ptr [ebp+ecx-20h],23h
23H 在ASCLL码表中 指 # , 含义为 将# 以单字节的形式 赋值给 ([ebp+ecx-20h)的内存地址,如图 - jmp main+27h (0040b777)
直接跳转到 0040b777 指向的内存地址 循环判断 执行
8.mov eax,dword ptr [ebp-24h]
9.add eax,1 // eax = eax + 1
将 (ebp寄存器内存地址-24H)的内存地址 赋值给 eax的寄存器,然后值在 +1 也就是计数器在+1.默认值是0
- mov dword ptr [ebp-24h],eax
将eax的值 赋值到了 [ebp-24h]指向的内存地址的值(19FF1C)
这时执行第三步 进行判断,然后重复执行直到退出循环
总结:
byte ptr [ebp+ecx-20h] //字节类型 00
word ptr [ebp-24h] /字类型 16位寄存器 0000
dword ptr [ebp-24h] //双字类型 32为寄存器 00000000
疑问 字节类型为什么是两个0?
答案 1byte=8bit
1 int = 4byte
字节类型 = 8byte 也就是2int 也就是 00
字类型 = 16byte 也就是4int’ 也就是 0000
双字类型 = 32byte 也就是8int 也就是 00000000
指令的参考//blog.csdn.net/qq_35349982/article/details/98872417
还没有评论,来说两句吧...