-
-
[原创]对一个求素数的c语言程序的逆向分析
-
发表于:
2013-11-11 00:14
5449
-
(release版本)
sub_401020 proc near
mov edi, 65h ; 初值
loc_40102A:
mov eax, edi ; eax = edi = 65h
mov ecx, 2 ; ecx = 2
cdq
sub eax, edx
mov esi, eax ; esi = eax
sar esi, 1 ; esi = esi / 2
cmp esi, ecx
jl short loc_40104A ; esi < ecx ->
; esi >= ecx ->
; ecx <= esi
; 不满足条件则跳出内层循环
loc_40103C:
mov eax, edi
cdq
idiv ecx
test edx, edx ;内层循环的内容,如果eax % ecx == 0则跳
jz short loc_40104A ; esi在上面/2了,再+1,可以想到,这一段语句用到了被外提的代码
inc ecx
cmp ecx, esi
jle short loc_40103C ; 满足条件则跳回,被优化的for结构,do_while,如果不满足,向下执行就跳出循环
loc_40104A:
inc esi ; esi在上面/2了,再+1,可以想到,这一段语句用到了被外提的代码
cmp ecx, esi ; ecx在程序里都为递增变量
jl short loc_40105E ; 小于则跳->大于等于则执行
push edi
push offset aD ; "%d "
call printf
add esp, 8
inc ebx ; ebx++
loc_40105E:
mov eax, ebx ; eax = ebx
mov ecx, 0Ah ; ecx = 10
cdq
idiv ecx
test edx, edx ; eax % ecx ==0 则执行语句,否则跳转
jnz short loc_401079 ; 如果输出了10个,则换行
push offset asc_408038 ; "\n"
call printf
add esp, 4
loc_401027: ;
add edi, 2 ;edi+=2(while)
cmp edi, 0C8h ;临界值0C8h
jle short loc_401007 ;edi<=0C8h则跳(向上)
push offset asc_408038 ; "\n"
call printf
add esp, 4
pop edi
pop esi
pop ebx
retn
sub_401020 endp
对于这种双重for循环结构,外层循环被优化成do_while循环,最后一个jle为循环条件,根据《C++反汇编与逆向分析技术揭秘》的总结,跳转条件不取反,esi/2为代码外提的语句,首先与2比较,esi/2<ecx则跳,但是根据源码来想就很容易弄迷糊,刚才已经判断为for循环了,所以跳转语句应该是被反向过的,所以esi/2>=ecx时执行循环体内容,也就是不跳,但是ecx才是循环变量,所以应该在取反一次,变成ecx<=esi/2执行循环,这样反向了2次,内层循环的运算结束后为判断跳转语句,同样是do_while结构。
C语言源码:
//1、求出200~1000之间所有的素数,要求:
//调用函数判断某数是不是素数;
//输出结果,每行输出10个素数。
////////////////////////////////////////
#include<stdio.h>
#include<stdlib.h>
void PrimeFind();//声明求素数的函数
int main()
{
PrimeFind();//调用
system("pause");
return 0;
}
void PrimeFind()//定义
{
int min=101,max=200;//定义求素数的范围
int x,temp,count=0;//101-200内的遍历和2-x内的遍历
for(x=min;x<=max;x+=2)//x在101-200内的奇数递增
{
for(temp=2;temp<=x/2;temp++)//temp在x范围内递增
{
if(x%temp==0)
{
break;//x能被temp整除则跳出(此时证明x不是素数,temp<=x/2+1)
}
}
if(temp>=x/2+1)//for正常跳出,则x是素数【注意】是x/2,不是x
{
printf("%d ",x);
count++;
}
if(count%10==0)
{
printf("\n");
}
}
printf("\n");
}
[招生]科锐逆向工程师培训(2024年11月15日实地,远程教学同时开班, 第51期)