Take a look at VTBL's other content and write a piece of code first:
class CParent
{
public:
int parent_a;
int parent_b;
public:
virtual void parent_f1() {}
virtual void parent_f2() {}
public:
void parent_f3() {}
void parent_f4() {}
};
class CChild : public CParent
{
public:
int child_a;
int child_b;
public: // 子类的函数
virtual void child_f1() {}
virtual void child_f2() {}
public: // 不可重载的函数
void child_f3() {}
void child_f4() {}
public: // 重载父类的函数
virtual void parent_f2() {}
virtual void parent_f1() {}
};
CChild child, *pchild;
CParent parent, *pparent;
This is a single inheritance relationship.
Properties of 1.1.1 Vtbl
VTBL should be determined at the time of the link, and then no longer change, then it should have a read-only attribute to verify this first:
MEMORY_BASIC_INFORMATION mi;
::VirtualQueryEx(::GetCurrentProcess(), (void*)(*(unsigned int*)&parent), &mi, sizeof(mi));
This code will query the properties of the memory block where the VTBL resides, and the returned MI values are as follows:
BaseAddress 0x00416000 ___xc_a void *
AllocationBase 0x00400000 void *
AllocationProtect 0x00000080 unsigned long
RegionSize 0x00002000 unsigned long
State 0x00001000 unsigned long
Protect 0x00000002 unsigned long
Type 0x01000000 unsigned long
Protect the value of this member indicates that the memory block in which the VTBL resides has page_readonly properties, and MSDN explains the meaning of the attribute:
Enables read access to the committed region of pages. An attempt to write to the committed region results in access violation. If the system differentiates between read-only access and execute access, an attempt to execute code in the committed Regi On results in a access violation.
Thus the contents of the VTBL will not be changed.