0.测试环境
gcc version 5.4.0 20160609 (Ubuntu 5.4.0-6ubuntu1~16.04.10)
1.引用
代码语言:javascript复制class Widget{
public:
virtual void show()=0;
int _w;
};
class Bell:public Widget{
public:
void show()
{
cout<<"Bell Bell..."<<endl;
}
};
void test()
{
Bell b;
Widget &w =b;
w.show();
}
test函数对应的汇编代码如下:
代码语言:javascript复制_Z4testv:
.LFB1022:
.cfi_startproc
pushl �p
.cfi_def_cfa_offset 8
.cfi_offset 5, -8
movl %esp, �p
.cfi_def_cfa_register 5
subl $24, %esp
movl %gs:20, �x
movl �x, -12(�p)
xorl �x, �x
subl $12, %esp
leal -20(�p), �x //eax=ebp-20,即eax=b.this
pushl �x //b首地址压栈
call _ZN4BellC1Ev //Bell::Bell()
addl $16, %esp
leal -20(�p), �x //eax=b.this
movl �x, -24(�p) //Widget &w=b
movl -24(�p), �x //eax=&w
movl (�x), �x //eax=vptr4Bell
movl (�x), �x //eax = vptr4Bell[0]
subl $12, %esp
pushl -24(�p) //w.this压栈
call *�x //virtual机制,w.show()
addl $16, %esp
nop
movl -12(�p), �x
xorl %gs:20, �x
je .L5
call __stack_chk_fail
.L5:
leave
.cfi_restore 5
.cfi_def_cfa 4, 4
ret
.cfi_endproc
test函数对应的伪码如下:
代码语言:javascript复制test()
{
Bell::Bell(&b);
Widget *w=&b;
(w->vptr[0])(w);
}