Hatena::ブログ(Diary)

パケピョン

2008-05-13

呼び出し規約 __thiscall

__thiscallはクラスの関数だってことで。MSDNでは、スタックの破棄は関数側。__stdcallと同じ。引数スタックにつむ。ecxにthisポインタをストアって。なんかイメージできるかも。


こんなソース。

#include <tchar.h>
#include <windows.h>

class ClassC
{
public:
	DWORD __cdecl funcA(BYTE a, DWORD b, BYTE c, DWORD d)
	{
		return a + b + c + d;
	}
	DWORD __stdcall funcB(BYTE a, DWORD b, BYTE c, DWORD d)
	{
		return a + b + c + d;
	}
	DWORD __thiscall funcC(BYTE a, DWORD b, BYTE c, DWORD d)
	{
		return a + b + c + d;
	}
};

int _tmain(int argc, _TCHAR* argv[])
{
	ClassC c;
	c.funcA(1, 2, 3, 4);
	c.funcB(1, 2, 3, 4);
	c.funcC(1, 2, 3, 4);
	return 0;
}

こんな逆アセンブリ

test!wmain:
0042d6c0 55              push    ebp
0042d6c1 8bec            mov     ebp,esp
0042d6c3 81eccc000000    sub     esp,0CCh
0042d6c9 53              push    ebx
0042d6ca 56              push    esi
0042d6cb 57              push    edi
0042d6cc 8dbd34ffffff    lea     edi,[ebp-0CCh]
0042d6d2 b933000000      mov     ecx,33h
0042d6d7 b8cccccccc      mov     eax,0CCCCCCCCh
0042d6dc f3ab            rep stos dword ptr es:[edi]
0042d6de 6a04            push    4
0042d6e0 6a03            push    3
0042d6e2 6a02            push    2
0042d6e4 6a01            push    1
0042d6e6 8d45fb          lea     eax,[ebp-5]
0042d6e9 50              push    eax
0042d6ea e8a7d9ffff      call    test!ILT+145(?funcAClassCQAAKEKEKZ) (0042b096)
0042d6ef 83c414          add     esp,14h
0042d6f2 6a04            push    4
0042d6f4 6a03            push    3
0042d6f6 6a02            push    2
0042d6f8 6a01            push    1
0042d6fa 8d45fb          lea     eax,[ebp-5]
0042d6fd 50              push    eax
0042d6fe e8b9e0ffff      call    test!ILT+1975(?funcBClassCQAGKEKEKZ) (0042b7bc)
0042d703 6a04            push    4
0042d705 6a03            push    3
0042d707 6a02            push    2
0042d709 6a01            push    1
0042d70b 8d4dfb          lea     ecx,[ebp-5]
0042d70e e83fdcffff      call    test!ILT+845(?funcCClassCQAEKEKEKZ) (0042b352)
0042d713 33c0            xor     eax,eax
0042d715 52              push    edx
0042d716 8bcd            mov     ecx,ebp
0042d718 50              push    eax
0042d719 8d153cd74200    lea     edx,[test!wmain+0x7c (0042d73c)]
0042d71f e8b8deffff      call    test!ILT+1495(_RTC_CheckStackVars (0042b5dc)
0042d724 58              pop     eax
0042d725 5a              pop     edx
0042d726 5f              pop     edi
0042d727 5e              pop     esi
0042d728 5b              pop     ebx
0042d729 81c4cc000000    add     esp,0CCh
0042d72f 3bec            cmp     ebp,esp
0042d731 e85de6ffff      call    test!ILT+3470(__RTC_CheckEsp) (0042bd93)
0042d736 8be5            mov     esp,ebp
0042d738 5d              pop     ebp
0042d739 c3              ret
test!ClassC::funcA:
0042d780 55              push    ebp
0042d781 8bec            mov     ebp,esp
0042d783 81ecc0000000    sub     esp,0C0h
0042d789 53              push    ebx
0042d78a 56              push    esi
0042d78b 57              push    edi
0042d78c 8dbd40ffffff    lea     edi,[ebp-0C0h]
0042d792 b930000000      mov     ecx,30h
0042d797 b8cccccccc      mov     eax,0CCCCCCCCh
0042d79c f3ab            rep stos dword ptr es:[edi]
0042d79e 0fb6450c        movzx   eax,byte ptr [ebp+0Ch]
0042d7a2 034510          add     eax,dword ptr [ebp+10h]
0042d7a5 0fb64d14        movzx   ecx,byte ptr [ebp+14h]
0042d7a9 034518          add     eax,dword ptr [ebp+18h]
0042d7ac 03c1            add     eax,ecx
0042d7ae 5f              pop     edi
0042d7af 5e              pop     esi
0042d7b0 5b              pop     ebx
0042d7b1 8be5            mov     esp,ebp
0042d7b3 5d              pop     ebp
0042d7b4 c3              ret
test!ClassC::funcB:
0042d7d0 55              push    ebp
0042d7d1 8bec            mov     ebp,esp
0042d7d3 81ecc0000000    sub     esp,0C0h
0042d7d9 53              push    ebx
0042d7da 56              push    esi
0042d7db 57              push    edi
0042d7dc 8dbd40ffffff    lea     edi,[ebp-0C0h]
0042d7e2 b930000000      mov     ecx,30h
0042d7e7 b8cccccccc      mov     eax,0CCCCCCCCh
0042d7ec f3ab            rep stos dword ptr es:[edi]
0042d7ee 0fb6450c        movzx   eax,byte ptr [ebp+0Ch]
0042d7f2 034510          add     eax,dword ptr [ebp+10h]
0042d7f5 0fb64d14        movzx   ecx,byte ptr [ebp+14h]
0042d7f9 034518          add     eax,dword ptr [ebp+18h]
0042d7fc 03c1            add     eax,ecx
0042d7fe 5f              pop     edi
0042d7ff 5e              pop     esi
0042d800 5b              pop     ebx
0042d801 8be5            mov     esp,ebp
0042d803 5d              pop     ebp
0042d804 c21400          ret     14h
test!ClassC::funcC:
0042d820 55              push    ebp
0042d821 8bec            mov     ebp,esp
0042d823 81eccc000000    sub     esp,0CCh
0042d829 53              push    ebx
0042d82a 56              push    esi
0042d82b 57              push    edi
0042d82c 51              push    ecx
0042d82d 8dbd34ffffff    lea     edi,[ebp-0CCh]
0042d833 b933000000      mov     ecx,33h
0042d838 b8cccccccc      mov     eax,0CCCCCCCCh
0042d83d f3ab            rep stos dword ptr es:[edi]
0042d83f 59              pop     ecx
0042d840 894df8          mov     dword ptr [ebp-8],ecx
0042d843 0fb64508        movzx   eax,byte ptr [ebp+8]
0042d847 03450c          add     eax,dword ptr [ebp+0Ch]
0042d84a 0fb64d10        movzx   ecx,byte ptr [ebp+10h]
0042d84e 034514          add     eax,dword ptr [ebp+14h]
0042d851 03c1            add     eax,ecx
0042d853 5f              pop     edi
0042d854 5e              pop     esi
0042d855 5b              pop     ebx
0042d856 8be5            mov     esp,ebp
0042d858 5d              pop     ebp
0042d859 c21000          ret     10h

呼び出すところをちょっと詳しく。

push    4
push    3
push    2
push    1
lea     eax,[ebp-5]
push    eax
call    test!ILT+4950(?funcAClassCQAGKEKEKZ) (0042c35b)
add     esp,14h

push    4
push    3
push    2
push    1
lea     eax,[ebp-5]
push    eax
call    test!ILT+4960(?funcBClassCQAGKEKEKZ) (0042c365)

push    4
push    3
push    2
push    1
lea     ecx,[ebp-5]
call    test!ILT+4955(?funcCClassCQAEKEKEKZ) (0042c360)

ん〜〜。__thiscallがecxにthisポインタを入れてるとすると、先の2つはeaxからスタックに入れている。

thisポインタつかってねーじゃん?あ、クラスのメンバとかを参照してないからか。

でもクラスの仕組みがほんのちょっとわかったような。

thisポインタを使う例もやってみようかな。

スパム対策のためのダミーです。もし見えても何も入力しないでください
ゲスト


画像認証

トラックバック - http://d.hatena.ne.jp/pakepion/20080513/1210693354