1

I wrote some code:

#include <stdlib.h>
#include <stdio.h>

    int a_function(int *a, int a_length, int *returned_address)
    {
        returned_address=a+a_length-1;
        return 0;
    }

    int main(void)
    {
        int n=5;
        int *a;
        int *address=NULL;
        a=(int*)malloc(n*sizeof(*a));
        a_function(a,n,address);
        printf("%p",address);
        return 0;
    }

The expected result is that the pointer 'address' point to a block of memory at the address of a+4. But the result was that the pointer 'address' still pointed to NULL (the printed result on the screen was like '00000000'). However, when I started debugging, inside 'a_function' the 'returned_address' did point to the memory block at a+4. What am I missing?

  • 2
    Standard Warning : Please [do not cast](http://stackoverflow.com/q/605845/2173917) the return value of `malloc()` and family. – Sourav Ghosh Mar 09 '15 at 14:28
  • 2
    If you want to change the value stored in a pointer variable in the calling function from within a function, you have to pass a pointer to the pointer to the called function. Hence, you need `int **returned_address` as the third parameter, and `&address` as the third argument to the call. – Jonathan Leffler Mar 09 '15 at 14:31
  • @JonathanLeffler I got your answer now, thank you. – V.T.T. Pham. Mar 09 '15 at 14:44

4 Answers4

6

In c, arguments are passed by value. When you pass a pointer to a function then its address is copied to the function parameter. Only the modification to the content of the location that pointer points to is seen to the caller. It means that that parameter returned_address can point to other location.

So, returned_address=a+a_length-1; makes returned_address to point to a new location, i.e, its content is overwritten by new assignment leaving passed pointer address point to the NULL.

You can fix this by using pointer to pointer.

void a_function(int *a, int a_length, int **returned_address)
{
    *returned_address=a+a_length-1;
}  

and call it as

a_function(a, n, &address);
haccks
  • 104,019
  • 25
  • 176
  • 264
  • Thank you. I understand the concept now. However I wonder what if I still keep "int *returned_address" but call the function as a_function(a,n,&address), will it work? – V.T.T. Pham. Mar 09 '15 at 14:47
  • No. It will not work. `&address` is of type `int **` but your function expects `int *` type. – haccks Mar 09 '15 at 14:48
3

If you want to change the value stored in a pointer variable in the calling function from within a function, you have to pass a pointer to the pointer to the called function. Hence, you need int **returned_address as the third parameter, and &address as the third argument to the call.

void a_function(int *a, int a_length, int **returned_address)
{
    *returned_address = a + a_length - 1;
}

And the call:

a_function(a, n, &address);

Note that you don't use the value returned by the function, so it may as well be of type void.

Jonathan Leffler
  • 730,956
  • 141
  • 904
  • 1,278
0

It should be NULL. address itself is passed by value, isn't it?

inside a_function(), any changes to returned_address is local to a_function().

OTOH, any changes to *returned_address will be reflected back in main().

Sourav Ghosh
  • 133,132
  • 16
  • 183
  • 261
-2

The function should receive int *&returned_adress.

Paul Roub
  • 36,322
  • 27
  • 84
  • 93
bbb
  • 1