2

I am using Valgrind to debug my code, and I am getting a warning when I test whether a struct is initialized by comparing it with NULL.

void main()
{
    int *unassignedPointer;
    if(unassignedPointer == NULL)
        printf("This Pointer is NULL\n");
}

This code compiles and runs, but when ran through Valgrind it gives a warning: Conditional jump or move depends on uninitialised value(s). The whole point of comparing it with NULL is to determine if it is initialized or not. Is this a dangerous practice, or should I just ignore these warnings?

trinaldi
  • 2,872
  • 2
  • 32
  • 37
Tony Ruth
  • 1,358
  • 8
  • 19
  • 3
    *The whole point of comparing it with NULL is to determine if it is initialized or not.* Huh?!?! That makes absolutely no sense. If it's not initialized, comparing it to *anything* is useless. – Andrew Henle Jun 26 '18 at 12:14
  • 1
    This is undefined behavior since the pointer does not have the address of the pointer itself taken. See [(Why) is using an uninitialized variable undefined behavior?](https://stackoverflow.com/questions/11962457/why-is-using-an-uninitialized-variable-undefined-behavior). – Lundin Jun 26 '18 at 12:35

4 Answers4

7

You should of course not ignore the warning, you should fix it by initializing the pointer:

int *pointer = NULL;

in general you cannot detect if a variable has been assigned to, there's no magic "no value" value, all bits of the variable are used to contain the actual value.

unwind
  • 391,730
  • 64
  • 469
  • 606
  • 2
    Unclear about the "all bits of the variable are used to contain the actual value" as I do not think pointers are specified to not contain padding. IAC, that last phrase looks unnecessary. – chux - Reinstate Monica Jun 26 '18 at 13:30
3

unassignedPointer is an unitialized local variable and reading such variable will lead to undefined behaviour, i.e. you will never know what will happen. On most of the architectures those variables will just contain memory garbage and your code will print nothing or "This pointer is NULL" depending on your luck. You should properly initialize the variable:

void main()
{
  int *unassignedPointer = NULL;
  if(unassignedPointer == NULL)
  printf("This Pointer is NULL\n");
}
sdobak
  • 399
  • 2
  • 9
2

Firstly here

int *unassignedPointer; /*here it can points to any unknown memory location */ 

unassignedPointer is not initialized and not pointing to valid memory location & dereferencing(if you tried) it causes undefined behavior. your compiler may warn you like

‘unassignedPointer’ is used uninitialized in this function [-Werror=uninitialized]

if you compiled your code with proper warning flag like -Wall etc. so first initialize unassignedPointer with NULL like

int *unassignedPointer = NULL;

Is this a dangerous practice, or should I just ignore these warnings? one should never ignore compiler warning. Better compile any simple code with

gcc -Wall -Wstrict-prototypes -Werror test.c   /* Werror, stops the compilation, convert warning into error */ 

Also read C language standard, draft n1256 section 5.1.2.2.1

Program startup: It shall be defined with a return type of int and with no parameters:

int main(void) { /*
...
*/ }

or with tw op arameters (referred to here as argc and argv ,though an yn ames may be used, as the ya re local to the function in which the ya re declared):

int main(int argc, char *argv[]) { /*
...
*/ }

This

void main() { 
   /*some code */
}

is not correct, instead use

int main(void) {
    /*some code */
}
Achal
  • 11,821
  • 2
  • 15
  • 37
  • "`unassignedPointer` ... & dereferencing it causes undefined behavior" is true yet OP's code does not dereference `unassignedPointer`. – chux - Reinstate Monica Jun 26 '18 at 13:37
  • Yes true @chux I was just hinting if OP tries to dereference uninitialized pointer, that causes to UB, though OP didn't did in code. – Achal Jun 26 '18 at 13:39
  • yes agree @chux dereferencing both `int *unassignedPointer;` and `int *unassignedPointer = NULL` cause UB. – Achal Jun 26 '18 at 13:51
1

When a variable is uninitialized, that means it wasn't explicitly given an initial value. That means it could have any value, including NULL or some other value.

Formally, an uninitialized variable that does not have static storage duration (i.e. a local variable not marked static) has an indeterminate value.

Also, as a general rule, warnings in C should never be ignored. The language assumes you know what you're doing and doesn't have any safeguards in place that other language have.

dbush
  • 205,898
  • 23
  • 218
  • 273