我想知道是否可以使用动态基地址而不是静态基地址来寻址一个类。基本思路如下:
有一个对象 A 定义如下:
class A
{
//member variables
...
//non-virtual member functions
...
//virtual methods
virtual void foo(...);
...
};
此类不能实例化为堆栈对象,并且没有标准的 new 运算符。
取而代之的是,该对象有一个新的位置,它将基地址和从基地址到内存的偏移量,并使用它来计算构造的绝对地址。
我想要做的是在代码中访问对象,如下所示:
A* clsA=new(base,offset) A();
...
clsA->foo( ... );
在哪里
(char*)clsA == (char*)(base+offset)
但还可以执行以下操作
base+=4;
...
clsA->foo( ... );
仍然有这个:
(char*)clsA == (char*)(base+offset)
保持真实。
我不知道这在 C++ 中是否可行。我知道它可以在 ASM (x86/amd64) 中完成,但我想要一个具有尽可能多的可移植性的解决方案(我承认它仍然几乎没有,但总比没有好)。有什么建议么?
编辑:所以我想我不太清楚我遇到的问题。这个想法是允许动态对象(在堆上分配的对象)在内存中移动。通常这不会有问题,但是由于无法通过堆栈内存实例化对象,因此访问对象的唯一方法是通过指向对象底层内存的指针。当数组移动时(在示例中,移动了四个字节),从数组借出的指针不再有效,需要更新。由于这个过程不仅会很长,而且会消耗比我希望的更多的内存,所以我希望能够让类在访问时重新计算它们的内存地址,而不是为每个借出的指针存储一个带有条目的重定位表。
一些可能代表这个概念的程序集是
;rax stores clsA
mov rcx, rax
shr rcx, 32
mov DWORD PTR[rdx], rax
lea rax, rdx+rcx
push rax
call foo
编辑 2:事实证明,对于这种确切的行为类型,还有一个 MSVC 修饰符。__based 声明一个相对于另一个指针的指针,因此可以移动底层内存并且指针保持有效。文章在这里。