記事ディレクトリ
Cはどのようにしてアセンブリになりましたか
Cコードは、実行可能ファイル(バイナリ)になるためにコンパイラで編集する必要があります。コンパイラはそれをどのように行いますか?
Cコード->コンパイラの構文チェック->コンパイラからアセンブリへ->…->バイナリファイル
理解する前に、まず次の知識を理解する必要があります。
1.ベア関数とは何ですか?
//先看一下裸函数怎么写,这个裸函数中什么都没有做,编译器编译的时候,
//也不会做任何事,那下一步就不知道做什么事了,于是就会报错
void __declspec(naked) Function()
{...}
上面的函数调用时,为什么会出错?
//该裸函数,什么也没做,但是最后ret了,编译器编译的时候,汇编就会是ret
//于是就不会报错
void __declspec(naked) Function()
{
__asm
ret
}
2.パラメータも戻り値もない関数フレームワーク
void __declspec(naked) Function()
{
__asm
{
push ebp // 开栈
mov ebp,esp
sub esp,0x40
push ebx //保护现场
push esi
push edi
lea edi,dword ptr ds:[ebp-0x40] //为缓冲器填充数据 (int 3)
mov eax,0xCCCCCCCC
mov ecx,0x10
rep stosd
pop edi //恢复堆栈
pop esi
pop ebx
mov esp,ebp //降低堆栈
pop ebp
ret //函数返回
}
}
3.パラメータと戻り値を持つ関数フレームワーク
int __declspec(naked) Function(int x,int y)
{
__asm
{
push ebp // 开栈
mov ebp,esp
sub esp,0x40
push ebx //恢复堆栈
push esi
push edi
lea edi,dword ptr ds:[ebp-0x40] //为缓冲器填充数据 (int 3)
mov eax,0xCCCCCCCC
mov ecx,0x10
rep stosd
mov eax,dword ptr ds:[ebp+8] // x,y两个数相加,这里x,y已经在进入函数前放入到了dword ptr ds:[ebp+8] dword ptr ds:[ebp+0xC]
add eax,dword ptr ds:[ebp+0xC]
pop edi
pop esi
pop ebx
mov esp,ebp
pop ebp
ret
}
}
4.ローカル変数を持つ関数フレームワーク
int __declspec(naked) Function(int x,int y)
{
__asm
{
push ebp
mov ebp,esp
sub esp,0x40
push ebx
push esi
push edi
lea edi,dword ptr ds:[ebp-0x40]
mov eax,0xCCCCCCCC
mov ecx,0x10
rep stosd
mov dword ptr ds:[ebp-4],2 //函数局部变量存放
mov dword ptr ds:[ebp-8],3
mov eax,dword ptr ds:[ebp+8] //函数外部变量(x,y)相加
add eax,dword ptr ds:[ebp+0xC]
pop edi
pop esi
pop ebx
mov esp,ebp
pop ebp
ret
}
}