473,406 Members | 2,633 Online
Bytes | Software Development & Data Engineering Community
Post Job

Home Posts Topics Members FAQ

Join Bytes to post your question to a community of 473,406 software developers and data experts.

offsetof macro and non-POD structures. Solution.

Hallo group members.

//p1.cpp
#include <stdio.h>
#include <linux/stddef.h>

struct Person {
int m_age;
char* m_name;
};

struct Child: public Person {
unsigned short m_school_year;
};

int main()
{
printf ("offset to m_name: %d\n", offsetof(Child, m_name));
printf ("offset to m_length: %d\n", offsetof(Child, m_school_year));
}

As You know the program above compiles with a warning:
prompt$ g++ -g -O0 -o /tmp/p1 p1.cpp

p1.cpp: In function `int main()':
p1.cpp:16: warning: invalid access to non-static data member `Person::m_name' of NULL object
p1.cpp:16: warning: (perhaps the `offsetof' macro was used incorrectly)
p1.cpp:17: warning: invalid access to non-static data member `Child::m_school_year' of NULL object
p1.cpp:17: warning: (perhaps the `offsetof' macro was used incorrectly)
As I read in this newsgroup, the reason is casting 0 to address non-POD structure.
Indeed, the following code produces the same warning:

int main()
{
#define BASE 0x0
printf ( "m_name: %d\n", &((Child*)BASE)->m_school_year );
}

My question is: can I safely ignore this warning for structures of the complexity above?

Again, I found in this newsgroup that solution would be just to turn off this warning
with -Wno-invalid-offsetof flag.

Another solution is, if BASE != 0, then warning is not produced, so that would be the solution.

offsetof macro would look like following:
#define OFFSETOF_BASE 0x1
#define Offsetof(TYPE, MEMBER) \
(size_t)((unsigned char*)(&(((TYPE*)OFFSETOF_BASE)->MEMBER)) - (unsigned char*)(TYPE*)OFFSETOF_BASE)

Regards,
Pawel
Oct 18 '06 #1
8 5831
Pawel <nu***@wp.plwrote:
Hallo group members.

//p1.cpp
#include <stdio.h>
#include <linux/stddef.h>
This is wrong; it should be <stddef.h>, without the linux.
struct Person {
int m_age;
char* m_name;
};

struct Child: public Person {
This is not C. (And it's not C++, either, because then both headers
above would be wrong.)
unsigned short m_school_year;
};

int main()
{
printf ("offset to m_name: %d\n", offsetof(Child, m_name));
This is wrong; there is no Child, and struct Child has no member called
m_name in C. It may in C++, but for information on that you need to ask
in comp.lang.c++, not here.
printf ("offset to m_length: %d\n", offsetof(Child, m_school_year));
If corrected to read struct Child, this is almost correct.

Both printf() statements also print a size_t, which is unsigned and of
unknown width, using %d. That, too, is wrong. You should either cast
offsetof() to unsigned long and use %lu, or use a C99 implemetation and
%zu. This is not likely to be your underlying problem, but it's still
wrong.
}

As You know the program above compiles with a warning:
Do I? As you _should_ know, different compilers issue different warnings
for different problems.
prompt$ g++ -g -O0 -o /tmp/p1 p1.cpp

p1.cpp: In function `int main()':
p1.cpp:16: warning: invalid access to non-static data member `Person::m_name' of NULL object
p1.cpp:16: warning: (perhaps the `offsetof' macro was used incorrectly)
p1.cpp:17: warning: invalid access to non-static data member `Child::m_school_year' of NULL object
p1.cpp:17: warning: (perhaps the `offsetof' macro was used incorrectly)
Neither of those make complete sense in a C context, but the latter a
bit more than the former.
In any case, with the two corrections I mentioned above, your _last_
call of offsetof() would be correct C, and should, for a non-broken
implementation, not give warnings. In theory an implementation is
allowed to print whatever warnings it likes, but as a QoI issue, it
ought not to for this case.
As I read in this newsgroup, the reason is casting 0 to address non-POD structure.
What is an "address non-POD structure"?

In any case, the offsetof() that got delivered with your implementation
in <stddef.h(_not_ <linux/stddef.h>!) should be usable without
warnings. If not, that is IMO a bug in the implementation, and you
should complain to your supplier.
Indeed, the following code produces the same warning:

int main()
{
#define BASE 0x0
printf ( "m_name: %d\n", &((Child*)BASE)->m_school_year );
}
Why not simply use NULL?
My question is: can I safely ignore this warning for structures of the complexity above?
No. The warning means that _you_ can't safely do this, on this
implementation. If you get that same warning for the normal, ISO C
offsetof() macro, the warning means that your implementation is broken.
Again, I found in this newsgroup that solution would be just to turn off this warning
with -Wno-invalid-offsetof flag.
That's as may be, but that is an implementation-dependent solution, and
I could not possibly comment on its value.
Another solution is, if BASE != 0, then warning is not produced, so that would be the solution.

offsetof macro would look like following:
#define OFFSETOF_BASE 0x1
#define Offsetof(TYPE, MEMBER) \
(size_t)((unsigned char*)(&(((TYPE*)OFFSETOF_BASE)->MEMBER)) - (unsigned char*)(TYPE*)OFFSETOF_BASE)
That, however, replaces a warning with definite undefined behaviour, and
is therefore a cure worse than the problem. Don't do this at all; you
may be inviting your program to crash at the most inopportune moment.
Instead, make sure that you get a full, correct implementation; in
particular, make sure that your headers and your compiler fit together,
and that you use the correct headers, not after-market ones.

Richard
Oct 18 '06 #2
Pawel wrote:
Hallo group members.

//p1.cpp
^^^^
Probably not a C translation unit. If not, it is not topical in comp.lang.c
#include <stdio.h>
#include <linux/stddef.h>
^^^^^^^^^^^^^^^^
implementation specific header, so not topical in comp.lang.c. If there
a reason not to use the topical <stddef.h>?
>
struct Person {
int m_age;
char* m_name;
};

struct Child: public Person {
^^^^^^^^^^^^^
':' syntax error
'public' undefined identifier
*Certainly* not topical in comp.lang.c. Are you perhaps confused,
thinking that the different programming language C++ should be of the
slightest interest in comp.lang.c?
[remaining silliness removed]
Oct 18 '06 #3
Richard Bos wrote:
Pawel <nu***@wp.plwrote:
#include <stdio.h>
#include <linux/stddef.h>

This is wrong; it should be <stddef.h>, without the linux.
struct Person {
int m_age;
char* m_name;
};

struct Child: public Person {

This is not C. (And it's not C++, either, because then both headers
above would be wrong.)

While the C-headers such as <stdio.hare deprecated in C++, they are
standard. In fact, I suspect that they will persist through many more
revisions of the C++ standard.


Brian
Oct 18 '06 #4
Default User <de***********@yahoo.comwrote:

(crossposted to comp.lang.c++, f'ups set)
While the C-headers such as <stdio.hare deprecated in C++, they are
standard. In fact, I suspect that they will persist through many more
revisions of the C++ standard.
I gather that the rest of the headers held over from C (<string.h>,
<stdlib.h>, etc.) are also standard?

--
C. Benson Manica | I *should* know what I'm talking about - if I
cbmanica(at)gmail.com | don't, I need to know. Flames welcome.
Oct 18 '06 #5
"Default User" <de***********@yahoo.comwrote:
Richard Bos wrote:
Pawel <nu***@wp.plwrote:
#include <stdio.h>
#include <linux/stddef.h>
This is wrong; it should be <stddef.h>, without the linux.
struct Person {
int m_age;
char* m_name;
};
>
struct Child: public Person {
This is not C. (And it's not C++, either, because then both headers
above would be wrong.)

While the C-headers such as <stdio.hare deprecated in C++, they are
standard. In fact, I suspect that they will persist through many more
revisions of the C++ standard.
I was under the impression that they're supposed to be called <cstdio.h>
or something like that?

Richard
Oct 19 '06 #6
Richard Bos said:
"Default User" <de***********@yahoo.comwrote:
<snip>
>>
While the C-headers such as <stdio.hare deprecated in C++, they are
standard. In fact, I suspect that they will persist through many more
revisions of the C++ standard.

I was under the impression that they're supposed to be called <cstdio.h>
or something like that?
Yes, the latter. :-)

--
Richard Heathfield
"Usenet is a strange place" - dmr 29/7/1999
http://www.cpax.org.uk
email: rjh at above domain (but drop the www, obviously)
Oct 19 '06 #7
rl*@hoekstra-uitgeverij.nl (Richard Bos) writes:
"Default User" <de***********@yahoo.comwrote:
[snip]
>While the C-headers such as <stdio.hare deprecated in C++, they are
standard. In fact, I suspect that they will persist through many more
revisions of the C++ standard.

I was under the impression that they're supposed to be called <cstdio.h>
or something like that?
I don't know, but I'm sure the folks in comp.lang.c++ do.

--
Keith Thompson (The_Other_Keith) ks***@mib.org <http://www.ghoti.net/~kst>
San Diego Supercomputer Center <* <http://users.sdsc.edu/~kst>
We must do something. This is something. Therefore, we must do this.
Oct 19 '06 #8
Richard Bos wrote:
"Default User" <de***********@yahoo.comwrote:
While the C-headers such as <stdio.hare deprecated in C++, they
are standard. In fact, I suspect that they will persist through
many more revisions of the C++ standard.

I was under the impression that they're supposed to be called
<cstdio.hor something like that?
See my message elsethread about this. Otherwise, drop me email or we
could continue this on clc++.


Brian
Oct 19 '06 #9

This thread has been closed and replies have been disabled. Please start a new discussion.

Similar topics

5
by: Hiroki Horiuchi | last post by:
Hello. I wrote a program, but g++ warns a.c:11: warning: invalid access to non-static data member `A::y' of NULL object a.c:11: warning: (perhaps the `offsetof' macro was used incorrectly) ...
6
by: Arthur J. O'Dwyer | last post by:
As far as I know, C89/C90 did not contain the now-standard offsetof() macro. Did C89 mandate that structs had to have a consistent layout? For example, consider the typical layout of the...
44
by: Simon Morgan | last post by:
Hi, Can somebody please help me grok the offsetof() macro? I've found an explanation on http://www.embedded.com/shared/printableArticle.jhtml?articleID=18312031 but I'm afraid it still...
13
by: luke | last post by:
hi all, i have another question. I've read the FAQ regarding my former question (sizeof struct and union) and in question 2.14 it talks about offset macro. #define offsetof(type, mem) ((size_t)...
7
by: Fred Zwarts | last post by:
Consider the following definition: typedef struct { int a; int b; } s; Now I have a function void f (int i) { ... }
11
by: Kavya | last post by:
offsetof(T,m) (size_t)&(((T*)0)->m) Why do we always start from 0 in this macro to access the offset of structure or union. Does standard guarantees that structure and union reside at address 0?...
24
by: Francine.Neary | last post by:
Just out of personal curiosity :) What do people use offsetof() for? I mean, I can understand why you'd want to be able to take the address of a member of a struct, but you can do that with just...
17
by: abhimanyu.v | last post by:
Hi Guys, I have one doubt. The test program is given below. It uses two way of finding out the offset of a variable in structure. I executed the program and found the same result. My question...
0
by: Charles Arthur | last post by:
How do i turn on java script on a villaon, callus and itel keypad mobile phone
0
by: emmanuelkatto | last post by:
Hi All, I am Emmanuel katto from Uganda. I want to ask what challenges you've faced while migrating a website to cloud. Please let me know. Thanks! Emmanuel
1
by: nemocccc | last post by:
hello, everyone, I want to develop a software for my android phone for daily needs, any suggestions?
0
by: Hystou | last post by:
There are some requirements for setting up RAID: 1. The motherboard and BIOS support RAID configuration. 2. The motherboard has 2 or more available SATA protocol SSD/HDD slots (including MSATA, M.2...
0
marktang
by: marktang | last post by:
ONU (Optical Network Unit) is one of the key components for providing high-speed Internet services. Its primary function is to act as an endpoint device located at the user's premises. However,...
0
by: Hystou | last post by:
Most computers default to English, but sometimes we require a different language, especially when relocating. Forgot to request a specific language before your computer shipped? No problem! You can...
0
Oralloy
by: Oralloy | last post by:
Hello folks, I am unable to find appropriate documentation on the type promotion of bit-fields when using the generalised comparison operator "<=>". The problem is that using the GNU compilers,...
0
agi2029
by: agi2029 | last post by:
Let's talk about the concept of autonomous AI software engineers and no-code agents. These AIs are designed to manage the entire lifecycle of a software development project—planning, coding, testing,...
0
isladogs
by: isladogs | last post by:
The next Access Europe User Group meeting will be on Wednesday 1 May 2024 starting at 18:00 UK time (6PM UTC+1) and finishing by 19:30 (7.30PM). In this session, we are pleased to welcome a new...

By using Bytes.com and it's services, you agree to our Privacy Policy and Terms of Use.

To disable or enable advertisements and analytics tracking please visit the manage ads & tracking page.