C++クラスオブジェクト呼び出し時のアセンブリ表現

Cコード

Class.h

class Creature
{
    
    
	public:
		int hp;
		int mp;
		char* name;
		void Attack();
		void Defend();
		void Dead();
		Creature(char* name);
};

class Player:public Creature
{
    
    
public:
	int nSmart;
	int nPower;
	void Buy();
	Player(char* name);
};

Class.cpp

void Creature::Attack()
{
    
    
	printf("I am Attacking...\n");
}
void Creature::Defend()
{
    
    
	printf("I am Defending...\n");
}
void Creature::Dead()
{
    
    
	printf("I am Dead.\n");
}
Creature::Creature(char* name)
{
    
    
	this->name = name;
	hp = 100;
	mp = 50;
}
void Player::Buy()
{
    
    
	printf("I am Buying.\n");
}
Player::Player(char *name):Creature(name)
{
    
    
	nSmart = 10;
	nPower = 7;
	printf("hp=%d,mp=%d,nSmart=%d,nPower=%d\n", hp, mp, nSmart, nPower);
}

main.cpp

int main()
{
    
    
	Player p((char*)"sanqiu");	
	p.Buy();
	p.Attack();
	getchar();

}

本体

push ebp
mov ebp,esp
sub esp,54
push ebx
push esi
push edi
push x86test.5D5BA8
lea ecx,dword ptr ss:[ebp-14]
call x86test.5D12BC				//Player()
lea ecx,dword ptr ss:[ebp-14]
call x86test.5D12E4				//Buy()
lea ecx,dword ptr ss:[ebp-14]
call x86test.5D1131				//attack()
call dword ptr ds:[<&getchar>]
xor eax,eax
pop edi
pop esi
pop ebx
mov esp,ebp
pop ebp
ret 

プレーヤーコンストラクター

push ebp
mov ebp,esp
sub esp,44
push ebx
push esi
push edi
mov dword ptr ss:[ebp-4],ecx	//Player对象指针当作第一个局部变量暂存
mov eax,dword ptr ss:[ebp+8]	//传入参数"sanqiu"
push eax
mov ecx,dword ptr ss:[ebp-4]	//传入Player对象指针
call x86test.5D10F0				//调用父类(Creature)的构造函数
mov eax,dword ptr ss:[ebp-4]
mov dword ptr ds:[eax+C],A		/Player.nSmart=10;
mov eax,dword ptr ss:[ebp-4]
mov dword ptr ds:[eax+10],7		//Player.nPower=7;
mov eax,dword ptr ss:[ebp-4]
mov ecx,dword ptr ds:[eax+10]	//接下来就开始printf了
push ecx
mov edx,dword ptr ss:[ebp-4]
mov eax,dword ptr ds:[edx+C]
push eax
mov ecx,dword ptr ss:[ebp-4]
mov edx,dword ptr ds:[ecx+4]
push edx
mov eax,dword ptr ss:[ebp-4]
mov ecx,dword ptr ds:[eax]
push ecx
push x86test.5D5B80
call x86test.5D10AA
add esp,14
mov eax,dword ptr ss:[ebp-4]
pop edi
pop esi
pop ebx
mov esp,ebp
pop ebp
ret 4

プレーヤー内部機能 購入する

push ebp
mov ebp,esp
sub esp,44
push ebx
push esi
push edi
mov dword ptr ss:[ebp-4],ecx	//暂存Player对象指针
push x86test.5D5B70
call x86test.5D10AA				//printf
add esp,4
pop edi
pop esi
pop ebx
mov esp,ebp
pop ebp
ret 

プレイヤーの親クラス関数 Attack

push ebp
mov ebp,esp
sub esp,44
push ebx
push esi
push edi
mov dword ptr ss:[ebp-4],ecx //暂存Player对象指针
push x86test.5D5B30
call x86test.5D10AA			//printf
add esp,4
pop edi
pop esi
pop ebx
mov esp,ebp
pop ebp
ret 

Player 親クラスのコンストラクター

push ebp
mov ebp,esp
sub esp,44
push ebx
push esi
push edi
mov dword ptr ss:[ebp-4],ecx	//Player对象指针
mov eax,dword ptr ss:[ebp-4]
mov ecx,dword ptr ss:[ebp+8]	
mov dword ptr ds:[eax+8],ecx	//Playe.name = "sanqiu"
mov eax,dword ptr ss:[ebp-4]
mov dword ptr ds:[eax],64		//Player.hp = 100
mov eax,dword ptr ss:[ebp-4]
mov dword ptr ds:[eax+4],32		//Player.mp = 50;
mov eax,dword ptr ss:[ebp-4]
pop edi
pop esi
pop ebx
mov esp,ebp
pop ebp
ret 4

まとめ
1. 親クラスの関数を呼び出す動作は、
サブクラス自体の関数を呼び出す動作と全く同じ 2. C と異なり、クラスの関数を使用する場合、クラスオブジェクトのポインタは必ず ecx に渡され、一時的に最初のローカル変数として関数内に格納さます


おすすめ

転載: blog.csdn.net/sanqiuai/article/details/124525875