user2684198
user2684198

Reputation: 852

How is the pointer (tree) returning 2 different values in 2 different lines?

I have the following code in my program:

/*Making a tree using linked lists.
*/
#define _CRT_SECURE_NO_WARNINGS
#include <stdio.h>
typedef struct node
{
    int value;
    struct node * left;
    struct node * right;
}Node;
Node * tree;
Node * maketree(int number)
{
    Node p = { number, NULL, NULL };
    return &p;
}
int main()
{
    int a[5] = { 1, 2, 3, 1, 4 };
    int number;
    number = a[0];
    tree = maketree(number);
    printf("Root has a value of %d\n", tree->value);
    printf("Root has a value of %d\n", tree->value);
}

Output:

Root has a value of 1

Root has a value of "Some garbage value!"

I can't understand how tree points to some other address (or printing some garbage value somehow) when I'm not at all playing with it and printing its value in 2 successive lines!

Upvotes: 0

Views: 33

Answers (2)

hivert
hivert

Reputation: 10667

In the function

Node * maketree(int number)
{
    Node p = { number, NULL, NULL };
    return &p;
}

You are returning the adress of a local variable namely p. Being local means that the memory location of the variable p is no more reserved for p after the end of the function. Nothing prevent it to be overwriten. This is called an undefined behavior.

You should use a dynamic allocation:

 Node * maketree(int number)
 {
    Node *pp;
    pp = malloc(sizeof(*pp));
    if(pp != NULL)
    {
        pp->value = number;
        pp->left = NULL;
        pp->right = NULL;
    }
    return pp;
 }

Upvotes: 1

unwind
unwind

Reputation: 400009

You are returning &p, the address of a local variable.

This variable goes out of scope as maketree() exits, making it undefined behavior to dereference the pointer.

In practice you're dereferencing a pointer to stack space that was allocated by maketree(), but has been de-allocated and very likely re-used (by printf(), which is quite a heavy function) since. This is totally invalid code.

The fix is to allocate the new node on the heap:

Node * maketree(int number)
{
  Node *p = malloc(sizeof *p);
  if(p != NULL)
  {
    p->value = number;
    p->left = p->right = NULL;
  }
  return p;
}

Upvotes: 4

Related Questions