Clearing of structs...

H

Hans B

Please bear with me if I ask silly questions....I am a somewhat newbie to
the C language....


If I had:

struct test1_{
unsigned char mycount1[256];
unsigned short mycount2[256];
unsigned short mycount3;
unsigned short mycount4;
unsigned short mycount5;
unsigned char mycount6;
unsigned char mycount7;
};

struct test2_{
unsigned int mycount8;
unsigned int mycount9;
unsigned short mycount10;
unsigned short mycount11;
unsigned short mycount12;
unsigned int mycount13;
unsigned int mycount14;
unsigned short mycount15;
unsigned short mycount16;
};

struct test3_{
unsigned int mycount17;
unsigned int mycount18;
unsigned short mycount19;
unsigned int mycount20;
};



struct my_data{
struct test1_ test1;
struct test2_ test2;
struct test3_ test3;
}mydatastruct;


I could do:
memset(&mydatastruct, 0, sizeof(mydatastruct));

To clear all variables listed in the struct. But what If I only would like
to clear the variables enclosed in struct test2 and test3, but keep/not
touch the values in test1?

Could this be done?

Best Regards
Hans
 
M

Mark A. Odell

Please bear with me if I ask silly questions....I am a somewhat newbie
to the C language.... [snip]
struct my_data{
struct test1_ test1;
struct test2_ test2;
struct test3_ test3;
}mydatastruct;


I could do:
memset(&mydatastruct, 0, sizeof(mydatastruct));

To clear all variables listed in the struct. But what If I only would
like to clear the variables enclosed in struct test2 and test3, but
keep/not touch the values in test1?

Be careful of floating point trap representations but didn't you:

memset(&mydatastruct.test2, 0, sizeof mydatastruct.test2);
memset(&mydatastruct.test3, 0, sizeof mydatastruct.test3);

? Remember sizeof is an operator, the ()'s are only required for types, as
in sizeof (int). You don't need them for objects.
 
T

Thomas Matthews

Hans said:
Please bear with me if I ask silly questions....I am a somewhat newbie to
the C language....


If I had:

struct test1_{
unsigned char mycount1[256];
unsigned short mycount2[256];
unsigned short mycount3;
unsigned short mycount4;
unsigned short mycount5;
unsigned char mycount6;
unsigned char mycount7;
}; [snip]

I could do:
memset(&mydatastruct, 0, sizeof(mydatastruct));

To clear all variables listed in the struct. But what If I only would like
to clear the variables enclosed in struct test2 and test3, but keep/not
touch the values in test1?

Keep in mind that memset is only guaranteed to work with contiguous
locations of characters.

Some implementations may have multi-byte short integers and integers
that represent the number Zero without those bytes set to 0.

Some floating point formats may not want all of their bits set to
zero to represent zero.

The most portable and successful method for clearing a struct is to
set each member to a known value.

--
Thomas Matthews

C++ newsgroup welcome message:
http://www.slack.net/~shiva/welcome.txt
C++ Faq: http://www.parashift.com/c++-faq-lite
C Faq: http://www.eskimo.com/~scs/c-faq/top.html
alt.comp.lang.learn.c-c++ faq:
http://www.raos.demon.uk/acllc-c++/faq.html
Other sites:
http://www.josuttis.com -- C++ STL Library book
 
H

Hans B

Thomas Matthews said:
Hans said:
Please bear with me if I ask silly questions....I am a somewhat newbie to
the C language....


If I had:

struct test1_{
unsigned char mycount1[256];
unsigned short mycount2[256];
unsigned short mycount3;
unsigned short mycount4;
unsigned short mycount5;
unsigned char mycount6;
unsigned char mycount7;
}; [snip]

I could do:
memset(&mydatastruct, 0, sizeof(mydatastruct));

To clear all variables listed in the struct. But what If I only would like
to clear the variables enclosed in struct test2 and test3, but keep/not
touch the values in test1?

Keep in mind that memset is only guaranteed to work with contiguous
locations of characters.

Some implementations may have multi-byte short integers and integers
that represent the number Zero without those bytes set to 0.

Some floating point formats may not want all of their bits set to
zero to represent zero.

The most portable and successful method for clearing a struct is to
set each member to a known value.

--
Thomas Matthews

C++ newsgroup welcome message:
http://www.slack.net/~shiva/welcome.txt
C++ Faq: http://www.parashift.com/c++-faq-lite
C Faq: http://www.eskimo.com/~scs/c-faq/top.html
alt.comp.lang.learn.c-c++ faq:
http://www.raos.demon.uk/acllc-c++/faq.html
Other sites:
http://www.josuttis.com -- C++ STL Library book

What I read from your reply, correct me if I'm wrong is that this method
would work as long as the structs only consists of unsigned char's, unsigned
short's and unsigned int's?

Best Regards
Hans
 
K

Kevin Goodsell

Hans said:
Please bear with me if I ask silly questions....I am a somewhat newbie to
the C language....


If I had:

struct test1_{
unsigned char mycount1[256];
unsigned short mycount2[256];
unsigned short mycount3;
unsigned short mycount4;
unsigned short mycount5;
unsigned char mycount6;
unsigned char mycount7;
};

struct test2_{
unsigned int mycount8;
unsigned int mycount9;
unsigned short mycount10;
unsigned short mycount11;
unsigned short mycount12;
unsigned int mycount13;
unsigned int mycount14;
unsigned short mycount15;
unsigned short mycount16;
};

struct test3_{
unsigned int mycount17;
unsigned int mycount18;
unsigned short mycount19;
unsigned int mycount20;
};



struct my_data{
struct test1_ test1;
struct test2_ test2;
struct test3_ test3;
}mydatastruct;


I could do:
memset(&mydatastruct, 0, sizeof(mydatastruct));

You could do this:

static const struct my_data zero = {0};
mydatastruct = zero;

This is more reliable than your method. As far as I know, memset to 0 is
only required to work correctly for char types.
To clear all variables listed in the struct. But what If I only would like
to clear the variables enclosed in struct test2 and test3, but keep/not
touch the values in test1?

Could this be done?

With 'zero' variables of the appropriate types you could just do this:

mydatastruct.test1 = test1_zero;

-Kevin
 
X

Xenos

Thomas Matthews said:
Hans said:
Please bear with me if I ask silly questions....I am a somewhat newbie to
the C language....


If I had:

struct test1_{
unsigned char mycount1[256];
unsigned short mycount2[256];
unsigned short mycount3;
unsigned short mycount4;
unsigned short mycount5;
unsigned char mycount6;
unsigned char mycount7;
}; [snip]

I could do:
memset(&mydatastruct, 0, sizeof(mydatastruct));

To clear all variables listed in the struct. But what If I only would like
to clear the variables enclosed in struct test2 and test3, but keep/not
touch the values in test1?

Keep in mind that memset is only guaranteed to work with contiguous
locations of characters.

Some implementations may have multi-byte short integers and integers
that represent the number Zero without those bytes set to 0.

Some floating point formats may not want all of their bits set to
zero to represent zero.

The most portable and successful method for clearing a struct is to
set each member to a known value.
I would just:

static const struct test1_ test1_init = {0};

..
..
..
mydatastruct = test1_init;


This would ensure proper initialization of all ints, float, pointers.
 
M

Mark R.Bannister

Hans B said:
Please bear with me if I ask silly questions....I am a somewhat newbie to
the C language....


If I had:

struct test1_{
unsigned char mycount1[256];
unsigned short mycount2[256];
unsigned short mycount3;
unsigned short mycount4;
unsigned short mycount5;
unsigned char mycount6;
unsigned char mycount7;
};

struct test2_{
unsigned int mycount8;
unsigned int mycount9;
unsigned short mycount10;
unsigned short mycount11;
unsigned short mycount12;
unsigned int mycount13;
unsigned int mycount14;
unsigned short mycount15;
unsigned short mycount16;
};

struct test3_{
unsigned int mycount17;
unsigned int mycount18;
unsigned short mycount19;
unsigned int mycount20;
};



struct my_data{
struct test1_ test1;
struct test2_ test2;
struct test3_ test3;
}mydatastruct;


I could do:
memset(&mydatastruct, 0, sizeof(mydatastruct));

To clear all variables listed in the struct. But what If I only would like
to clear the variables enclosed in struct test2 and test3, but keep/not
touch the values in test1?

Could this be done?

Best Regards
Hans


You can't assume knowledge of how the data will be represented in
memory. The only portable way of doing this is by manually setting
each variable to zero. And this would be easier to do if you used
arrays rather than individual variable names.

Best regards,
Mark.
 
P

Peter Nilsson

Hans B said:
Please bear with me if I ask silly questions....I am a somewhat newbie to
the C language....


If I had:

struct test1_{
unsigned char mycount1[256];
unsigned short mycount2[256];
unsigned short mycount3;
unsigned short mycount4;
unsigned short mycount5;
unsigned char mycount6;
unsigned char mycount7;
};

struct test2_{
unsigned int mycount8;
unsigned int mycount9;
unsigned short mycount10;
unsigned short mycount11;
unsigned short mycount12;
unsigned int mycount13;
unsigned int mycount14;
unsigned short mycount15;
unsigned short mycount16;
};

struct test3_{
unsigned int mycount17;
unsigned int mycount18;
unsigned short mycount19;
unsigned int mycount20;
};



struct my_data{
struct test1_ test1;
struct test2_ test2;
struct test3_ test3;
}mydatastruct;


I could do:
memset(&mydatastruct, 0, sizeof(mydatastruct));

To clear all variables listed in the struct. But what If I only would like
to clear the variables enclosed in struct test2 and test3, but keep/not
touch the values in test1?

Could this be done?

memset(&mydatastruct.test2, 0, sizeof mydatastruct.test2);
memset(&mydatastruct.test3, 0, sizeof mydatastruct.test3);

or...

#include <stddef.h>

memset( &mydatastruct.test2, 0,
sizeof mydatastruct - offsetof(struct my_data, test2));
 
J

Jack Klein

Hans said:
Please bear with me if I ask silly questions....I am a somewhat newbie to
the C language....


If I had:

struct test1_{
unsigned char mycount1[256];
unsigned short mycount2[256];
unsigned short mycount3;
unsigned short mycount4;
unsigned short mycount5;
unsigned char mycount6;
unsigned char mycount7;
}; [snip]

I could do:
memset(&mydatastruct, 0, sizeof(mydatastruct));

To clear all variables listed in the struct. But what If I only would like
to clear the variables enclosed in struct test2 and test3, but keep/not
touch the values in test1?

Keep in mind that memset is only guaranteed to work with contiguous
locations of characters.

Some implementations may have multi-byte short integers and integers
that represent the number Zero without those bytes set to 0.

No, no, no, nononono, this nonsense must die! See below...

Some floating point formats may not want all of their bits set to
zero to represent zero.
OK.

The most portable and successful method for clearing a struct is to
set each member to a known value.

Fortunately the C Standard Committee has already approved a wording
change in response to a defect report over this silliness. It will be
added to the next TC or standard update:

======
DR#263.

Append to 6.2.6.2#5:
For any integer type, the object representation where all the bits
are zero shall be a representation of the value zero in that type.
======

--
Jack Klein
Home: http://JK-Technology.Com
FAQs for
comp.lang.c http://www.eskimo.com/~scs/C-faq/top.html
comp.lang.c++ http://www.parashift.com/c++-faq-lite/
alt.comp.lang.learn.c-c++ ftp://snurse-l.org/pub/acllc-c++/faq
 
A

Alan Balmer

No, no, no, nononono, this nonsense must die! See below...

Thank you, sir! This was getting to the point where it was downright
misleading to beginners hoping to make sense of the language.

I maintain hundreds of thousands of lines of code written by
programmers who were quite confident that setting all bytes of an
integer to zero resulted in a value of zero. So far they have not been
proved wrong.
 
R

Richard Heathfield

Alan said:
I maintain hundreds of thousands of lines of code written by
programmers who were quite confident that setting all bytes of an
integer to zero resulted in a value of zero. So far they have not been
proved wrong.

It is, however, only relatively recently that this practice was codified by
the Standard. A certain amount of inertia on the part of comp.lang.c is
inevitable.
 
E

Eric Sosman

Richard said:
It is, however, only relatively recently that this practice was codified by
the Standard. A certain amount of inertia on the part of comp.lang.c is
inevitable.

Inertia is the group's middle name (I bet you thought
it was "lang"). Why, this very week I saw someone explain
that casting the result of malloc() was a bad idea because
the cast could hide a bug! That is *so* last century ...
 
J

Jack Klein

Thank you, sir! This was getting to the point where it was downright
misleading to beginners hoping to make sense of the language.

I maintain hundreds of thousands of lines of code written by
programmers who were quite confident that setting all bytes of an
integer to zero resulted in a value of zero. So far they have not been
proved wrong.

I have just finished writing the first release of a small, fast, light
weight real time multitasking kernel to replace a deceased legacy
operating system on a new platform.

The kernel, believe it or not, is in 100% strictly conforming C. The
hardware abstraction layer, about 150 bytes of highly processor
specific assembly language is not, but the kernel is.

When the kernel is initialized, is uses memset() on a large variety of
control structures, and depends on all the integer types contained in
those structures containing valid values of 0. It does not depend on
pointers in those structures being set to NULL by the memset(), even
though on the particular platform it is true.

There is a lot of my code that would break if somebody ported it to a
platform where all bits 0 was not the value zero for some integer
types. I would never program on such a platform. Unless somebody
paid me. A lot.

Even if the committee had not accepted the DR, I would have written my
kernel the way I did. But then it would have only been 98% strictly
conforming.

--
Jack Klein
Home: http://JK-Technology.Com
FAQs for
comp.lang.c http://www.eskimo.com/~scs/C-faq/top.html
comp.lang.c++ http://www.parashift.com/c++-faq-lite/
alt.comp.lang.learn.c-c++ ftp://snurse-l.org/pub/acllc-c++/faq
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

Forum statistics

Threads
473,769
Messages
2,569,582
Members
45,067
Latest member
HunterTere

Latest Threads

Top