13

I've noticed several Coverity (static-analysis tool) errors of type 'Uninitialized scalar variable' that are high impact. A lot of them are just ints that don't get initialized.

Would initializing them to zero be any different than what C++ does by default?

PerryC
  • 1,233
  • 2
  • 12
  • 28
  • I edited to refocus on C++ for this question. I largely work in a C# code-base, but these issues are all in C++ code, sorry about the lack of clarity earlier. – PerryC Jul 13 '15 at 17:20
  • Well, int's are value types in both c++ and C#, they use X bytes of ram, and all 0 bits, they are 0. So whether you initialize them or not, in memory they are still 0. – Ryan Mann Jul 13 '15 at 17:21
  • 4
    Whether they are zero initialized or not depends on their storage type (static or automatic) and on how they are initialized. It might be easier to answer if you post a complete code sample. – juanchopanza Jul 13 '15 at 17:27
  • 1
    I'm unable to post any code samples (production code, NDAs, IP, etc.) -- otherwise I would. A lot of my struggle is asking myself, "Is there a safe/good default value to set the int to?". What happens if it's set to 0? Sometimes I've found there is no good default case or maybe it will very-very-rarely go down a path where it doesn't get set even though it wasn't initialized. Then it's just not worth initializing it to a value that might not be a good default. That said, I didn't want this question to go down a design path to make sure it's a clear and concise question. – PerryC Jul 13 '15 at 17:43
  • 1
    @PerryCampbell The problem is that reading from an uninitialized variable is undefined behaviour. So as long as you set the value to something before reading, you're fine. – juanchopanza Jul 13 '15 at 17:44
  • Note using a variable with [indeterminate value is undefined behavior](http://stackoverflow.com/q/23415661/1708801) – Shafik Yaghmour Jul 13 '15 at 18:05

5 Answers5

17

Does C++ initialize integers to zero automatically?

For automatic variables:

Some compilers might do it but the standard does not require it. A conforming implementation could leave them to be uninitialized garbage values.

For static variables:

They must be initialized to zero unless explicitly initialized otherwise.

R Sahu
  • 204,454
  • 14
  • 159
  • 270
  • 3
    "Some compilers might do it." Are you sure? Clang, gcc, and MSVC will all not initialize scalars in Release builds. – pmr Jul 13 '15 at 17:28
  • MSVC does, I believe. It may be only in Debug builds (not sure), but that still counts. – celticminstrel Jul 13 '15 at 17:29
  • 1
    In my opinion, compilers should never initialize a variable automatically, especially if it changes from one build to another. That would mean that you could have bugs that don't appear in debug builds, which defeats the point – KABoissonneault Jul 13 '15 at 17:30
  • Yup, some versions of msvc do that in debug mode. You'll be tearing your hair out if you hit a bug because of this. – SigTerm Jul 13 '15 at 17:32
  • @KABoissonneault It doesn't matter, because reading from such an uninitialized variable is undefined behaviour anyway. So whether a sompiler initializes to 0 or not is irrelevant 'cause you're not allowed to look. – juanchopanza Jul 13 '15 at 17:33
  • 1
    @celticminstrel I guess you're right because I don't see a point. I'm talking automatic storage, BTW. – juanchopanza Jul 13 '15 at 17:34
  • 2
    @KABoissonneault It would be very useful for the compiler to initialize them in debug build. To some value that is highly unlikely to be what you want: as you point out, initializing them to 0 is generally anti-productive, but initializing them to 0xDEADBEAF, or something like that, is a good idea (and I think that's what modern MVS does). – James Kanze Jul 13 '15 at 17:51
  • @JamesKanze I should have specified "initialize to 0", but yes you are right – KABoissonneault Jul 13 '15 at 18:14
14

C++ does not initialize integer variables to zero by default.

Some compilers may zero them out or fill with some default value while compiling your project in debug mode. In release mode that usually does not happen.

There is an exception with static variables, but by default it is safe to assume that anything unitialized holds a random value.

Beware of uninitialized variables. Finding this kind of bug is hard and can waste a lot of time. Usual symptoms: the program works fine in debug mode, but behaves strangely in release.

Martijn Pieters
  • 1,048,767
  • 296
  • 4,058
  • 3,343
SigTerm
  • 26,089
  • 6
  • 66
  • 115
  • But what about this? http://en.cppreference.com/w/cpp/language/zero_initialization It seems to say that in many cases ints are initialized to zero? – Robin May 10 '17 at 12:54
  • 1
    Yes, many cases, such as `static int myint;` and `int myint = int();` but not a plain old `int myint;` A plain old `int myint;` is NOT initialised to 0. – Will Sep 06 '17 at 10:20
1

Objects declared in static storage duration are zero initialized before any other initialization takes place (including default initializations).

To default-initialize an object of type T means:
— if T is a (possibly cv-qualified) class type (Clause 9), the default constructor for T is called (and the initialization is ill-formed if T has no accessible default constructor);
— if T is an array type, each element is default-initialized;
— otherwise, no initialization is performed
C.11 §8.5¶6

Note: Every object of static storage duration is zero-initialized at program startup before any other initialization takes place. In some cases, additional initialization is done later. — end note ]
C.11 §8.5¶9

jxh
  • 69,070
  • 8
  • 110
  • 193
0

Yes and no.

It depends how they are declared. If they are declared static, then yes, they are guaranteed to be zero-initialized. However, local variables in a function may not be zero-initialized. Nor are class member variables in most contexts (the exception being static).

Basically, if it's not static, you should assume it won't be initialized to 0. Since it's not initialized, it could have any value whatsoever.

celticminstrel
  • 1,637
  • 13
  • 21
0

errors of type 'Uninitialized scalar variable' that are high impact

Yes, they are high impact because an uninitialized automatic variable has indeterminate value and using an indeterminate value is undefined behavior so these are serious bugs if you attempt to produce a value from them before initialization.

Would initializing them to zero be any different than what C++ does by default?

Yes, for automatic scalar variables the C++ standard says they will have indeterminate value, the draft C++ standard from section 8.5 [dcl.init]:

If no initializer is specified for an object, the object is default-initialized. When storage for an object with automatic or dynamic storage duration is obtained, the object has an indeterminate value, and if no initialization is performed for the object, that object retains an indeterminate value until that value is replaced (5.17 [expr.ass])

A compiler may in debug mode initialize local variable, to aid in debugging, we can see that MSVC can do this using /RTC:

Initialization of local variables to a nonzero value. This helps identify bugs that do not appear when running in debug mode.[...]

Community
  • 1
  • 1
Shafik Yaghmour
  • 154,301
  • 39
  • 440
  • 740