The following code and its output:
#include <stdio.h>
int x = 0;
#define offsetof(TYPE, MEMBER) ((size_t) &((TYPE *)x)->MEMBER)
#define offsetof_1(TYPE, MEMBER) ((size_t) &((TYPE *)1)->MEMBER)
#define offsetof_2(TYPE, MEMBER) ((size_t) &((TYPE *)2)->MEMBER)
#define offsetof_3(TYPE, MEMBER) ((size_t) &((TYPE *)0)->MEMBER)
struct test{};
struct m {
int b;
char w;
struct test t;
int c;
};
int main(void) {
printf("Checking:%x\n",offsetof(struct m,b));
printf("Checking:%x\n",offsetof_1(struct m,b));
printf("Checking:%x\n",offsetof_2(struct m,b));
printf("Checking:%x\n",offsetof_3(struct m,b));
return 0;
}
Output:
Checking:0
Checking:1
Checking:2
Checking:0
I am trying to understanding the typecasting used here. I think, how compiler does is it treats (type *)(value)
as that type starting at address (value). Hence for the given structure the expected value is 0,i.e. offsetof is b, but as we have used different values for typecasting we get different offset. Please let me know if my understanding is correct. I am just trying to understand how literals are typecasted and its implications. This is used in Linux kernel. Hence tagging them as well.