[英]How does this C struct pointer casting to other struct works?
#define MACHINE_GET_CLASS(obj) \
OBJECT_GET_CLASS(MachineClass, (obj), TYPE_MACHINE)
#define OBJECT_GET_CLASS(class,obj,name) OBJECT_CLASS_CHECK(class, object_get_class(OBJECT(obj)), name)
#define OBJECT_GET_CLASS(class, obj, name) \
OBJECT_CLASS_CHECK(class, object_get_class(OBJECT(obj)), name)
#define OBJECT(obj) ((Object *)(obj))
struct MachineState {
/*< private >*/
Object parent_obj;
Notifier sysbus_notifier;
//...
}
struct Object
{
/*< private >*/
ObjectClass *class;
ObjectFree *free;
GHashTable *properties;
uint32_t ref;
Object *parent;
};
MachineState *machine;
MachineClass *machine_class = MACHINE_GET_CLASS(machine);
通過遵循宏,
MACHINE_GET_CLASS(machine) = OBJECT_GET_CLASS(MachineClass, (machine), TYPE_MACHINE) =
OBJECT_CLASS_CHECK(MachineClass, object_get_class(OBJECT(machine)), TYPE_MACHINE)
看到OBJECT(machine) = ((Object *)(machine))
我們如何將結構指針MachineState*
轉換為Object *
?
我想我在這里遺漏了一些東西,我對 C++ 更加熟悉。 另外,object 周圍的額外括號是什么意思? 就像在(machine)
中的OBJECT_GET_CLASS(MachineClass, (machine), TYPE_MACHINE)
據我了解,這只是合法且有效,因為struct MachineState
的第一個成員是struct Object
類型,並且在轉換編譯器時只會給您一個指針,您可以通過該指針從給定地址訪問struct Object
的大小 - 無論地址類型你提供的。
因此,應該非常小心地使用這種技術,因為它很容易導致未定義的行為。
考慮以下:
struct structA {
int i;
char c;
};
struct structB {
struct structA sA;
int i;
};
struct structC {
int i;
};
int main() {
struct structA A = { 42, 'a' };
struct structB B = { {43, 'b'}, 44 };
struct structC C = { 45 };
struct structA *pA1 = (struct structA*)&B;
struct structA *pA2 = (struct structA*)&C;
printf ("pA1: %d %c\n", pA1->i, pA1->c);
printf ("pA2: %d %c\n", pA2->i, pA2->c);
return 0;
}
因此,當轉換(struct structA*)&B
時,我得到了預期的結果,因為指針類型與struct structB
開頭的成員完全匹配,但是當轉換(struct structA*)&C
時,我將訪問未定義的 memory 部分。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.