C++通过virtual table访问类private成员函数

被声明为private的函数,在类外是无法被访问的,但是virtual table让一切变得不一样。

本来想研究————类的多个对象是否共享同一套虚表,答案是明确的:“Yes”。

在做实验的时候,意外的发现,可以通过虚表指针访问虚表中的函数(即使该函数被声明为私有的...)。

下面是实验内容,

#include <iostream>
using namespace std;

class A {
private:
virtual void a() {
cout << "haha" << endl;
}
};

typedef long long ll;
typedef void(*func)();

int main(int argc, char const *argv[]) {
A a1;

ll* vtbl_ptr = (ll*)*(ll*)(&a1);

func f = (func)(*vtbl_ptr);
f(); //haha

return 0;
}

实验结果,

MacBook-Pro:Desktop qingdujun$ g++ test.cpp 
MacBook-Pro:Desktop qingdujun$ ./a.out
haha

实验环境为,

MacBook-Pro:blog qingdujun$ g++ --version
Configured with: --prefix=/Library/Developer/CommandLineTools/usr --with-gxx-include-dir=/usr/include/c++/4.2.1
Apple LLVM version 10.0.0 (clang-1000.10.44.4)
Target: x86_64-apple-darwin17.7.0
Thread model: posix
InstalledDir: /Library/Developer/CommandLineTools/usr/bin


References: [1] C++单个类的所有对象是否共享虚函数表的验证 [2] 全凉经