-1
int main()
{
   int i,j,k;
   i=1;j=2;k=3;
   int *p =&k;
   *(p-1)=0;
   printf("%d%d%d",i,j,k);
   getch();
}

the output is 1 2 3.

mtvec
  • 17,846
  • 5
  • 52
  • 83
Ashok
  • 1
  • 1
    First of all, why would you it give a runtime error? – user703016 Apr 29 '12 at 08:01
  • memory access violation may be. – Ashok Apr 29 '12 at 08:01
  • Why do you think it should? p points to k on the stack, p-1 points to one integer before k on your stack. It isn't necessary an access violation. It is a dangerous and undefined behavior though. – unexpectedvalue Apr 29 '12 at 08:02
  • even if you replace the line *(p-1)=0; by *(p-1000)=0; I get the same output 123 – Ashok Apr 29 '12 at 08:04
  • Try `*(p+1)=0`. I'd expect it to print 103. – Secure Apr 29 '12 at 08:06
  • yes the output is 103. That answers the above question but for *(p-1) shouldnt i get a runtime error? – Ashok Apr 29 '12 at 08:10
  • 1
    You're writing to the yet empty and unused stack space with `p-1`. Nothing of importance is there at this time, so why should you get an error? It is undefined behaviour, and not crashing is well defined UB as well. – Secure Apr 29 '12 at 08:13
  • Ok,I get it now. The stack grows downwards. Thanks – Ashok Apr 29 '12 at 08:18
  • Try writing 0s upward until you hit the return address of the main call. Then you should get your crash. ;) – Secure Apr 29 '12 at 08:20
  • @Ashok 'Stack growing' ain't defined in C. This is clear UB, unicorns may fly or god servant may appear. No need to theoreticize what went wrong imho. – Tomas Pruzina Apr 29 '12 at 13:40
  • @Ashok: The stack grows downwards on your particular implementation; it's not guaranteed to behave that way on all platforms. Don't assume this will behave the same way everywhere. – John Bode Apr 29 '12 at 13:44

3 Answers3

3

Your program exhibits undefined behavior, the pointer arithmetics you're doing is invalid.

You can only do pointer arithmetics on pointers that actually point into an array, and the result of the addition or subtraction must still point inside the array (or one past its end, if you don't intend to dereference it).

So anything could happen, the compiler can generate whatever code it feels like for that code.

Mat
  • 202,337
  • 40
  • 393
  • 406
  • I tried this code because int i; float *p= (float*) &i; *p=100.00; printf("%d",i); gives no run time error. So should I expect unexpected behaviour for the above code? – Ashok Apr 29 '12 at 08:06
  • That's invalid code too, you're violating aliasing rules. See http://stackoverflow.com/questions/98340/what-are-the-common-undefined-unspecified-behavior-for-c-that-you-run-into – Mat Apr 29 '12 at 08:09
2

You are not allowed to refer to p-1 after assigning it &k this is an invalid pointer for you, and the behavior of using it is undefined.

MByD
  • 135,866
  • 28
  • 264
  • 277
  • Well, really you are allowed to refer to any address. The unknown is what will happen when you do. So you should not. It's a fine point but maybe the one the OP is asking about. It's not Java. – joshp Apr 29 '12 at 08:11
  • Actually, according to the standard you are not allowed to use it at all. not even assign it to another variable, and such action results in undefined behavior. – MByD Apr 29 '12 at 08:25
  • I defer to your knowlege. When I did the most C there was no standard. I think his compiler is letting him do it. That's what I mean by allowed. It's a bad thing to do whatever you call it. – joshp Apr 29 '12 at 08:33
  • OK, when I said allowed - I meant that the behavior is defined. I obviously used the wrong term. sorry for the confusion. – MByD Apr 29 '12 at 08:43
0

A run-time error only occurs if your stray pointer hits something that raises that error, such as some protected memory or a location that will later become a divisor in some calculation (0), for example.

joshp
  • 1,886
  • 2
  • 20
  • 28