获取虚拟表指针c ++

时间:2016-06-01 23:04:32

标签: c++ pointers

我有一个类

class Stuff
{
private:
int x;
virtual int buisness()
{
  return 42;
}
public:
 Stuff(){
  x = 5;
}

给出指向此类实例的指针

Stuff stuff;
void* thing = &stuff;

如何使用指针“thing”获取指向变量x的指针和指向该类的虚函数表的指针?

编辑:澄清这是一个发送给我的挑战,我确信这不是一个技巧问题。

3 个答案:

答案 0 :(得分:8)

  

如何使用指针“thing”获取指向变量x的指针和指向该类的虚函数表的指针?

如果不将thing转换回原始类型,则无法使用

Stuff* stuff2 = reinterpret_cast<Stuff*>(thing);

并且至少不会将您从该类的隐私政策中赎回,以及如何公开访问类成员指针。

实际布局是实现定义的,尝试使用 thing 和大小假设的偏移超出了标准的c ++机制。

听起来您想要绕过具有这些成员的已知布局的类的private成员访问策略。这是一个非常肮脏的黑客:
Disclamer:请勿在生产代码中执行此操作!!

#include <iostream>

class Stuff {
private:
    int x;
    virtual int business() {
        std::cout << "Have that 42 ... " << std::endl;
        return 42;
    }
public:
    Stuff() {
      x = 5;
    }
};

struct StuffProxy {
    // Make the layout public:
    int x;
    virtual int business();
};

int main() {
    Stuff stuff;
    void* thing = &stuff;

    // Here's the nasty stuff
    StuffProxy* stuffProxy = reinterpret_cast<StuffProxy*>(thing);
    int* addrX = &(stuffProxy->x); // Get the address of x
    std::cout << "x = " << *addrX << std::endl;

    typedef int (Stuff::*StuffFunc)();
    StuffFunc stuffFunc = (StuffFunc)(&StuffProxy::business);
    std::cout << "business() = " << (stuff.*stuffFunc)() << std::endl;
}

输出:

x = 5
Have that 42 ... 
business() = 42

Live Demo

上述方法有效,因为它保证{c}编译器实现中classstruct具有相同的布局,编译期间成员可见性的唯一区别。

因此,如果你有一个类的布局(例如来自标题),并且你愿意在项目的整个生命周期中保持这个,你可以提供上面这样的代理来访问private的东西。一堂课。

答案 1 :(得分:2)

访问private成员x

1)声明需要访问x的函数,作为类的朋友。

2)更改对public的访问权限。

3)编写公共 getter setter 函数。

4)改变你的设计;其他类不应该知道成员变量。

答案 2 :(得分:0)

这可能与编译器有关。 我刚从指针“thing”

创建了一个char数组
char *array;
array = (char*)thing;

然后遍历该数组,直到找到私有变量

int x = array[8];