0

I'm passing a dynamic allocated variables into a function , and after returning from that function , when I run inputs on the code , some of those inputs makes the program to crash .

As you can see , I test the argv array , twice , once at the end of divide , and another time after I return from divide . In the first check I get all the values of argv from index 0 to argc , but in the 2nd check (after returning from divide back into main) index 0 make the for loop to crash .

So obviously I'm doing something wrong , any idea what ?

JAN
  • 21,236
  • 66
  • 181
  • 318

1 Answers1

1
argv =(char**) realloc(argv, (current+1)*sizeof(char*));

This is the likely culprit. Calling realloc() can allocate a new (presumably larger) block of memory into which the data from the old block is copied, and then deallocate the old block. The problem isn't that you're changing the value of argv in main(), it's that you're not changing it. You're deallocating the block that it points to without updating main()'s argv to point to the new block.

Caleb
  • 124,013
  • 19
  • 183
  • 272
  • Good one! I'll check this ASAP – JAN May 23 '12 at 19:15
  • I've changed to prototype of `main` . It has nothing to do with the code , I could have just left a blank `main()` . So I guess this is not the problem ? – JAN May 23 '12 at 19:24
  • 1
    No, it's still the problem. You're still calling `realloc()` in your `divide()` function, and that still results in `argv` becoming a dangling pointer in `main()`, and you're still using that bad pointer in `main()`, and (I presume that) it's still crashing. – Caleb May 23 '12 at 19:28
  • Okay ,of course you're right ,but how shall I fix it ? allocate that memory in `main` ? – JAN May 23 '12 at 19:47
  • 1
    The easiest fix is probably to pass the address of `argv` instead of the value: `divide(char *s , char *t , int *a , char*** argv , char d[])`. Then you can assign the new block: `*argv = realloc(*argv, (current+1)*sizeof(char*));`. This is the C equivalent of passing by reference. – Caleb May 23 '12 at 20:00
  • But I'd need to change `argv` in `main` , am I wrong ? from `**` into `***` ? and the rest of the `main` ... – JAN May 23 '12 at 20:27
  • 1
    No, you'd keep main()'s `argv` just as it is, but pass it into `divide()` as `&argv`, which means "take the address of 'argv'". If this is new to you, pull out your C book and read about [passing by reference in C](http://stackoverflow.com/q/2229498/643383). – Caleb May 23 '12 at 20:31
  • I've updated the original post . There's still a problem with the code after adding another `*` to the `argv` variable inside method `divide` . I'd appreciate if you could take a look . Thanks . – JAN May 23 '12 at 20:52
  • 1
    Please read up on pointers in C. You're doing `*argv[current]`, which is the same as `*(argv[current])`. You should instead say `(*argv)[current]`. See [Order of operations for dereference and bracket-ref in C](http://stackoverflow.com/q/3552844/643383). – Caleb May 23 '12 at 21:05
  • 1
    +100 for your explanation ! I've been trying to work this bug for the past day . You're indeed awesome , my friend! – JAN May 24 '12 at 03:04