Re: C/C++ Option to Initialize Variables?

2013-02-22 Thread David Brown

On 18/02/13 18:08, Robert Dewar wrote:



Forgive me, but I don't see where anything is guaranteed to be zero'd
before use. I'm likely wrong somewhere since you disagree.


http://en.wikipedia.org/wiki/.bss


This is about what happens to work, and specifically notes that it is
not part of the C standard. There is a big difference between programs
that obey the standard, and those that don't but happen to work on some
systems. The latter programs have latent bugs that can definitely
cause trouble.

A properly written C program should avoid uninitialized variables, just
as a properly written Ada program should avoid them.

In GNAT, we have found the Initialize_Scalars pragma to be very useful
in finding uninitialized variables. It causes all scalars to be
initialized using a specified bit pattern that can be specified at
link time, and modified at run-time.

If you run a program with different patterns, it should give the same
result, if it does not, you have an uninitialized variable or other
non-standard aspect in your program which should be tracked down and
fixed.

Note that the BSS-is-always-zero guarantee often does not apply when
embedded programs are restarted, so it is by no means a universal
guarantee.




I believe the standards require that all statically allocated data 
without an explicit initialisation are initialised to a /value/ of zero. 
 The standards do not require values of zero to actually be zero bits - 
it is legal for null pointers, 0 integers, and 0.0 floats and doubles to 
have different representations.  It is also perfectly legal for the 
compiler to put uninitialised data somewhere other than ".bss".  But the 
standards do guarantee that a definition "int x;" has the same effect as 
"int x = 0;" - and similarly for all other statically allocated data.



In embedded systems, any C startup code (the code that is run before 
main() is called) that does not clear the bss is dangerously broken.  (I 
know of no real-world embedded processors where 0 is /not/ represented 
as zero bits.)  There are a few toolchains that /are/ broken in this way 
- Texas Instruments's "Code Composer" is a prime example.  The manual 
mentions this briefly at one point - to paraphrase, "the C startup code 
does not clear the bss at startup.  We know this is against every C 
standard - but we never claimed to follow any particular C standard anyway".


So if you know that you will be working with broken compilers that don't 
follow such fundamental parts of the C standards, then you should not 
rely on the automatic zero initialisation.  But if you are using real 
working toolchains, then you (as an embedded programmer) /should/ rely 
on it - because it leads to smaller and faster code than explicitly 
initialising them to zero.  (Of course, sometimes you want to be 
explicit in initialising to zero for clarity of the program - this 
trumps efficiency every time.)





Re: C/C++ Option to Initialize Variables?

2013-02-19 Thread Michael Matz
Hi,

On Mon, 18 Feb 2013, Alexander Monakov wrote:

> On Mon, 18 Feb 2013, Michael Matz wrote:
> > Automatic variables, as they are on the stack, are unlikely to usually get
> > the value 0 out of pure luck, so an option to initialize them to 0xDEADBEAF
> > doesn't make much sense.
> 
> Hm, but the following comment from init-regs.c indicates that GCC will set
> some uninitialized vars to zero, except at -O0:

Yes, that's for pseudos, i.e. scalar automatic variables, doesn't work for 
may-uninitialized or aggregates and would be unnecessary with -Werror, as 
must-uninitialized can be and are detected without false positives.  The 
value could be made configurable but I wouldn't see the point.


Ciao,
Michael.


Re: C/C++ Option to Initialize Variables?

2013-02-18 Thread Robert Dewar



Wrong.  It specifies that objects with static storage duration that
aren't explicitely initialized are initialized with null pointers, or
zeros depending on type.  6.7.8.10.


OK, that means that the comments of my last mesage don't apply to
variables of this type. So they should at least optionally be excluded
from any feature to initialize variables


Hence if .bss is to be used to place such objects then the runtime system
_must_ make sure that it's zero initialized.




Re: C/C++ Option to Initialize Variables?

2013-02-18 Thread Robert Dewar



Forgive me, but I don't see where anything is guaranteed to be zero'd
before use. I'm likely wrong somewhere since you disagree.


http://en.wikipedia.org/wiki/.bss


This is about what happens to work, and specifically notes that it is
not part of the C standard. There is a big difference between programs
that obey the standard, and those that don't but happen to work on some
systems. The latter programs have latent bugs that can definitely
cause trouble.

A properly written C program should avoid uninitialized variables, just
as a properly written Ada program should avoid them.

In GNAT, we have found the Initialize_Scalars pragma to be very useful
in finding uninitialized variables. It causes all scalars to be 
initialized using a specified bit pattern that can be specified at

link time, and modified at run-time.

If you run a program with different patterns, it should give the same
result, if it does not, you have an uninitialized variable or other
non-standard aspect in your program which should be tracked down and
fixed.

Note that the BSS-is-always-zero guarantee often does not apply when
embedded programs are restarted, so it is by no means a universal
guarantee.



Re: C/C++ Option to Initialize Variables?

2013-02-18 Thread Alexander Monakov
On Mon, 18 Feb 2013, Michael Matz wrote:
> Automatic variables, as they are on the stack, are unlikely to usually get
> the value 0 out of pure luck, so an option to initialize them to 0xDEADBEAF
> doesn't make much sense.

Hm, but the following comment from init-regs.c indicates that GCC will set
some uninitialized vars to zero, except at -O0:

/* Check all of the uses of pseudo variables.  If any use that is MUST
   uninitialized, add a store of 0 immediately before it.  For
   subregs, this makes combine happy.  For full word regs, this makes
   other optimizations, like the register allocator and the reg-stack
   happy as well as papers over some problems on the arm and other
   processors where certain isa constraints cannot be handled by gcc.
   These are of the form where two operands to an insn my not be the
   same.  The ra will only make them the same if they do not
   interfere, and this can only happen if one is not initialized.

   There is also the unfortunate consequence that this may mask some
   buggy programs where people forget to initialize stack variable.
   Any programmer with half a brain would look at the uninitialized
   variable warnings.  */

However this seems to not touch variables with only may-uninitialized
accesses.

> And to initialize allocated variables with some bit pattern you can simply
> override malloc.

Or use MALLOC_PERTURB_ environment variable.

-- 
Alexander


Re: C/C++ Option to Initialize Variables?

2013-02-18 Thread Michael Matz
Hi,

On Mon, 18 Feb 2013, Jeffrey Walton wrote:

> On Mon, Feb 18, 2013 at 10:34 AM, Andrew Haley  wrote:
> > On 02/18/2013 03:07 PM, Jeffrey Walton wrote:
> >> On Mon, Feb 18, 2013 at 9:43 AM, Jonathan Wakely  
> >> wrote:
> >>> On 18 February 2013 13:28, Jeffrey Walton wrote:
> >
>  What if the ".BSS" section was
>  initialized to 0xFF rather than a page full of NULLs?
> >>>
> >>> That could break millions of perfectly valid programs, for no obvious 
> >>> benefit.
> >> Its hypothetical, and could be a bit humorous. Why are developers
> >> writing programs that rely upon undocumented features?
> >
> > BSS being zero is certainly not an undocumented feature.
>
> C/C++ makes no assurances on the value of an unitialized variable, 
> members, etc.

Wrong.  It specifies that objects with static storage duration that 
aren't explicitely initialized are initialized with null pointers, or 
zeros depending on type.  6.7.8.10.

Hence if .bss is to be used to place such objects then the runtime system 
_must_ make sure that it's zero initialized.

IOW: it's only automatic and allocated variables that start with an 
indeterminate value when not initialized explicitely.  Automatic 
variables, as they are on the stack, are unlikely to usually get the value 
0 out of pure luck, so an option to initialize them to 
0xDEADBEAF doesn't make much sense.  And to initialize allocated variables 
with some bit pattern you can simply override malloc.  So, this option 
seems to search for a problem it's supposed to help with.


Ciao,
Michael.


Re: C/C++ Option to Initialize Variables?

2013-02-18 Thread Uday Khedker



On Monday 18 February 2013 09:44 PM, Jeffrey Walton wrote:

On Mon, Feb 18, 2013 at 10:34 AM, Andrew Haley  wrote:

On 02/18/2013 03:07 PM, Jeffrey Walton wrote:

On Mon, Feb 18, 2013 at 9:43 AM, Jonathan Wakely  wrote:

On 18 February 2013 13:28, Jeffrey Walton wrote:



What if the ".BSS" section was
initialized to 0xFF rather than a page full of NULLs?


That could break millions of perfectly valid programs, for no obvious benefit.

Its hypothetical, and could be a bit humorous. Why are developers
writing programs that rely upon undocumented features?


BSS being zero is certainly not an undocumented feature.

C/C++ makes no assurances on the value of an unitialized variable, members, etc.

DATA section is initialized data. BSS section is unitialized data.

For statically allocated unitintialized object, it will go in BSS
section. For uninitialized stack variable, it will go on the stack.

Forgive me, but I don't see where anything is guaranteed to be zero'd
before use. I'm likely wrong somewhere since you disagree.


http://en.wikipedia.org/wiki/.bss

Uday.


Re: C/C++ Option to Initialize Variables?

2013-02-18 Thread Jeffrey Walton
On Mon, Feb 18, 2013 at 10:34 AM, Andrew Haley  wrote:
> On 02/18/2013 03:07 PM, Jeffrey Walton wrote:
>> On Mon, Feb 18, 2013 at 9:43 AM, Jonathan Wakely  
>> wrote:
>>> On 18 February 2013 13:28, Jeffrey Walton wrote:
>
 What if the ".BSS" section was
 initialized to 0xFF rather than a page full of NULLs?
>>>
>>> That could break millions of perfectly valid programs, for no obvious 
>>> benefit.
>> Its hypothetical, and could be a bit humorous. Why are developers
>> writing programs that rely upon undocumented features?
>
> BSS being zero is certainly not an undocumented feature.
C/C++ makes no assurances on the value of an unitialized variable, members, etc.

DATA section is initialized data. BSS section is unitialized data.

For statically allocated unitintialized object, it will go in BSS
section. For uninitialized stack variable, it will go on the stack.

Forgive me, but I don't see where anything is guaranteed to be zero'd
before use. I'm likely wrong somewhere since you disagree.

Jeff


Re: C/C++ Option to Initialize Variables?

2013-02-18 Thread Andrew Haley
On 02/18/2013 03:07 PM, Jeffrey Walton wrote:
> On Mon, Feb 18, 2013 at 9:43 AM, Jonathan Wakely  
> wrote:
>> On 18 February 2013 13:28, Jeffrey Walton wrote:

>>> What if the ".BSS" section was
>>> initialized to 0xFF rather than a page full of NULLs?
>>
>> That could break millions of perfectly valid programs, for no obvious 
>> benefit.
> Its hypothetical, and could be a bit humorous. Why are developers
> writing programs that rely upon undocumented features?

BSS being zero is certainly not an undocumented feature.

Andrew.



Re: C/C++ Option to Initialize Variables?

2013-02-18 Thread Jeffrey Walton
On Mon, Feb 18, 2013 at 9:43 AM, Jonathan Wakely  wrote:
> On 18 February 2013 13:28, Jeffrey Walton wrote:
>> The reason I went looking for the flag is someone asked about a crash
>> on the OpenSSL mailing list. I knew it was due to an uninitialized
>> field (but they did not realize the value was not initialized). I
>> wanted to suggest a quick way to find what was not initialized.
>
> Valgrind.
That requires an additional package, and some developers don't use it.

>> How much code do you think would break because folks depend on getting
>> a 0 due to good graces or side effects (for example, the memory
>> manager returning a zeroized page)?
>
> It should break no valid programs.  The invalid programs that break
> would benefit from an easily reproducable failure.
Right.

>> What if the ".BSS" section was
>> initialized to 0xFF rather than a page full of NULLs?
>
> That could break millions of perfectly valid programs, for no obvious benefit.
Its hypothetical, and could be a bit humorous. Why are developers
writing programs that rely upon undocumented features?

As crazy as it sound, it probably portable though. Are there any OS
link/loaders which use a memory manager that does not serve zeroized
pages (at least on the first run when drawing from a fresh pool)?

It not just userland. I've looked at lots of kernel code that relies
on the same good graces and luck. I'd love to see the effects of the
memory manager returning a page filed with HASH(counter).

>> When building for tools such as Valgrind, don't specify the flag ;)
>
> You don't build for valgrind, it runs normal, uninstrumented binaries.
> That's one of its main advantages.
Yes, agreed. The switch would *not* be specified for production code
('release' builds). But I'm talking about development ('debug'
builds).

Jeff


Re: C/C++ Option to Initialize Variables?

2013-02-18 Thread Jonathan Wakely
On 18 February 2013 13:28, Jeffrey Walton wrote:
> The reason I went looking for the flag is someone asked about a crash
> on the OpenSSL mailing list. I knew it was due to an uninitialized
> field (but they did not realize the value was not initialized). I
> wanted to suggest a quick way to find what was not initialized.

Valgrind.

> How much code do you think would break because folks depend on getting
> a 0 due to good graces or side effects (for example, the memory
> manager returning a zeroized page)?

It should break no valid programs.  The invalid programs that break
would benefit from an easily reproducable failure.

> What if the ".BSS" section was
> initialized to 0xFF rather than a page full of NULLs?

That could break millions of perfectly valid programs, for no obvious benefit.

> When building for tools such as Valgrind, don't specify the flag ;)

You don't build for valgrind, it runs normal, uninstrumented binaries.
That's one of its main advantages.


Re: C/C++ Option to Initialize Variables?

2013-02-18 Thread Michael Veksler

On 02/18/2013 03:28 PM, Jeffrey Walton wrote:

On Mon, Feb 18, 2013 at 7:42 AM, Michael Veksler
 wrote:

On 02/18/2013 02:02 PM, Alec Teal wrote:

On 18/02/13 11:40, Jeffrey Walton wrote:

Hi All,


http://gcc.gnu.org/onlinedocs/gcc/C-Dialect-Options.html#C-Dialect-Options

Is there an option to initialize variables to known values in a C/C++
program?

My use case is 'debug' builds and finding use of uninitialized values
that get lucky by being 0 most of the time. For example:

void DoSomeithWithFoo(FOO** ppf) {
if(ppf && *ppf == NULL) {
  *ppf = new FOO;
  ...
}
}

FOO* p;
DoSomeithWithFoo(&p);

So I would like something that initializes to known, but non-NULL,
such as 0xCDCDCDCD or 0xFDFDFDFD (similar to Visual Studio behavior).


...



I believe Jeff thinks the above is a bug in *his* code, and he wants a flag
to
help him spot it. By assigning non-NULL values to unintialized variables
will,
supposedly, make the code behave wrongly, making it easier to detect.

The reason I went looking for the flag is someone asked about a crash
on the OpenSSL mailing list. I knew it was due to an uninitialized
field (but they did not realize the value was not initialized). I
wanted to suggest a quick way to find what was not initialized.

How much code do you think would break because folks depend on getting
a 0 due to good graces or side effects (for example, the memory
manager returning a zeroized page)? What if the ".BSS" section was
initialized to 0xFF rather than a page full of NULLs?


I agree that having gcc deliberately put garbage into uninitialized
variables can
be very helpful in shortening the compile-test-debug-fix loop. I run
valgrind only
occasionally, even though I run unit-tests after every modification. This
means
that bugs due to unintialized memory are sometimes detected many days after
they were first introduced, which makes it more difficult to understand the
bug. Testing code compiled with this flag will probably result in less bugs
of
this kind left to  testing by valgrind.

Yes, it's a great feature of Visual Studio. It helps you find the
point of first failure (or the potential point) quickly.


I see the main issue with such flags in their interaction with tools like
valgrind. Such a flag could defeat valgrind's algorithm for detecting
unintialized local variables, unless it is made aware of the flag
(which I don't see how it could be done, without special hints from gcc).

When building for tools such as Valgrind, don't specify the flag ;)

I like when things just work, without weird dependencies. But the trade-off
sounds reasonable to me in this case, but I am not a GCC developer and
have no moral right to justify this claim.

Instead of joining your request for a new GCC feature I have a suggestion to
you. How about writing a plug-in for GCC to do that? I am no expert, but
writing a melt plug-in does not sound too complicated:
http://gcc-melt.org/
It is possible that you could add an initialization to every 
uninitialized variable

in a simple melt plug-in.

I have never written a plug-in so I may be completely wrong, and it is not
that simple. I think that it is worth having a look.

Michael


Re: C/C++ Option to Initialize Variables?

2013-02-18 Thread Jeffrey Walton
On Mon, Feb 18, 2013 at 7:42 AM, Michael Veksler
 wrote:
> On 02/18/2013 02:02 PM, Alec Teal wrote:
>>
>> On 18/02/13 11:40, Jeffrey Walton wrote:
>>>
>>> Hi All,
>>>
>>>
>>> http://gcc.gnu.org/onlinedocs/gcc/C-Dialect-Options.html#C-Dialect-Options
>>>
>>> Is there an option to initialize variables to known values in a C/C++
>>> program?
>>>
>>> My use case is 'debug' builds and finding use of uninitialized values
>>> that get lucky by being 0 most of the time. For example:
>>>
>>> void DoSomeithWithFoo(FOO** ppf) {
>>>if(ppf && *ppf == NULL) {
>>>  *ppf = new FOO;
>>>  ...
>>>}
>>> }
>>>
>>> FOO* p;
>>> DoSomeithWithFoo(&p);
>>>
>>> So I would like something that initializes to known, but non-NULL,
>>> such as 0xCDCDCDCD or 0xFDFDFDFD (similar to Visual Studio behavior).
>>>
>> ...
>>
>>
> I believe Jeff thinks the above is a bug in *his* code, and he wants a flag
> to
> help him spot it. By assigning non-NULL values to unintialized variables
> will,
> supposedly, make the code behave wrongly, making it easier to detect.
The reason I went looking for the flag is someone asked about a crash
on the OpenSSL mailing list. I knew it was due to an uninitialized
field (but they did not realize the value was not initialized). I
wanted to suggest a quick way to find what was not initialized.

How much code do you think would break because folks depend on getting
a 0 due to good graces or side effects (for example, the memory
manager returning a zeroized page)? What if the ".BSS" section was
initialized to 0xFF rather than a page full of NULLs?

> I agree that having gcc deliberately put garbage into uninitialized
> variables can
> be very helpful in shortening the compile-test-debug-fix loop. I run
> valgrind only
> occasionally, even though I run unit-tests after every modification. This
> means
> that bugs due to unintialized memory are sometimes detected many days after
> they were first introduced, which makes it more difficult to understand the
> bug. Testing code compiled with this flag will probably result in less bugs
> of
> this kind left to  testing by valgrind.
Yes, it's a great feature of Visual Studio. It helps you find the
point of first failure (or the potential point) quickly.

> I see the main issue with such flags in their interaction with tools like
> valgrind. Such a flag could defeat valgrind's algorithm for detecting
> unintialized local variables, unless it is made aware of the flag
> (which I don't see how it could be done, without special hints from gcc).
When building for tools such as Valgrind, don't specify the flag ;)

Jeff


Re: C/C++ Option to Initialize Variables?

2013-02-18 Thread Michael Veksler

On 02/18/2013 02:02 PM, Alec Teal wrote:

On 18/02/13 11:40, Jeffrey Walton wrote:

Hi All,

http://gcc.gnu.org/onlinedocs/gcc/C-Dialect-Options.html#C-Dialect-Options 



Is there an option to initialize variables to known values in a C/C++ 
program?


My use case is 'debug' builds and finding use of uninitialized values
that get lucky by being 0 most of the time. For example:

void DoSomeithWithFoo(FOO** ppf) {
   if(ppf && *ppf == NULL) {
 *ppf = new FOO;
 ...
   }
}

FOO* p;
DoSomeithWithFoo(&p);

So I would like something that initializes to known, but non-NULL,
such as 0xCDCDCDCD or 0xFDFDFDFD (similar to Visual Studio behavior).

Jeff

Probably not, put =0, if I say "int x;" I am just saying there is an 
int, it's name is x, deal with it. I may assign to it later, sticking 
=0 at the end implicitly wouldn't be good for anything really.
However! calloc initializes the memory to zero change malloc(size to 
calloc(1,size and you're done.


Does that help?

Alec


I believe Jeff thinks the above is a bug in *his* code, and he wants a 
flag to
help him spot it. By assigning non-NULL values to unintialized variables 
will,

supposedly, make the code behave wrongly, making it easier to detect.

I agree that having gcc deliberately put garbage into uninitialized 
variables can
be very helpful in shortening the compile-test-debug-fix loop. I run 
valgrind only
occasionally, even though I run unit-tests after every modification. 
This means

that bugs due to unintialized memory are sometimes detected many days after
they were first introduced, which makes it more difficult to understand the
bug. Testing code compiled with this flag will probably result in less 
bugs of

this kind left to  testing by valgrind.

I see the main issue with such flags in their interaction with tools like
valgrind. Such a flag could defeat valgrind's algorithm for detecting
unintialized local variables, unless it is made aware of the flag
(which I don't see how it could be done, without special hints from gcc).

Michael


Re: C/C++ Option to Initialize Variables?

2013-02-18 Thread Alec Teal

On 18/02/13 11:40, Jeffrey Walton wrote:

Hi All,

http://gcc.gnu.org/onlinedocs/gcc/C-Dialect-Options.html#C-Dialect-Options

Is there an option to initialize variables to known values in a C/C++ program?

My use case is 'debug' builds and finding use of uninitialized values
that get lucky by being 0 most of the time. For example:

void DoSomeithWithFoo(FOO** ppf) {
   if(ppf && *ppf == NULL) {
 *ppf = new FOO;
 ...
   }
}

FOO* p;
DoSomeithWithFoo(&p);

So I would like something that initializes to known, but non-NULL,
such as 0xCDCDCDCD or 0xFDFDFDFD (similar to Visual Studio behavior).

Jeff

Probably not, put =0, if I say "int x;" I am just saying there is an 
int, it's name is x, deal with it. I may assign to it later, sticking =0 
at the end implicitly wouldn't be good for anything really.
However! calloc initializes the memory to zero change malloc(size to 
calloc(1,size and you're done.


Does that help?

Alec