1

Create this x.c test file:

int main(void)
{
  char x[2] = {3};
  return x[2];
}

Then run

gcc x.c; ./a.out; echo $?

Result is: 64.

Why 64?

Incidentally, why if we use

return x[1];

we get 0? Why the {3} did not initialize x[1] too?

Sourav Ghosh
  • 133,132
  • 16
  • 183
  • 261
Igor Liferenko
  • 1,499
  • 1
  • 13
  • 28
  • You pry open a deposit box belong to someone else, which you don't have access to, and find $64 dollars. Why $64? Why isn't it empty? Why not 10 or 100 or 1000 or a chihuahua? Could it possibly be because the person who owns the deposit box is free to store whatever they please in there? – Lundin Jul 09 '20 at 06:52
  • Regarding partial initialization of arrays, please see this: https://stackoverflow.com/questions/15520880/initializing-entire-2d-array-with-one-value/15521368#15521368 – Lundin Jul 09 '20 at 06:53
  • @Lundin why if we add `x[2] = 5;` the return value is `5`? – Igor Liferenko Jul 10 '20 at 01:00
  • Because the police failed to catch you when you put $5 in a deposit box you have been breaking into. And you were lucky that the owner didn't show up to change the contents. – Lundin Jul 10 '20 at 06:14
  • @Lundin Isn't "segmentation fault" supposed to happen in such case? – Igor Liferenko Jul 10 '20 at 06:21
  • Often it will, but there are no guarantees. The police isn't guaranteed to catch 100% of all criminals. There's simply no mechanism protecting you from writing out of bounds of an array - C is low level and has less restrictions than other languages, but this freedom makes it dangerous at the same time. – Lundin Jul 10 '20 at 06:25
  • @Lundin My guess is that ``Segmentation fault'' happens only when one accesses memory outside of current process, but stepping over bound of an array may happen inside of current process's memory. – Igor Liferenko Aug 11 '20 at 08:44
  • That's highly system-specific. – Lundin Aug 11 '20 at 08:51

1 Answers1

6

How reading beyond end of buffer works in C? and Why 64?

It does not "work", it's the result of undefined behaviour. There does not exist an array element at x[2].

we get 0? Why the {3} did not initialize x[1] too?

That said, a statement like

 char x[2] = {3};

creates an array x, with two elements, accessed by x[0] and x[1], and initializes x[0] to 3 and any remaining element to 0 (as per the rules of initialization where there are less number of initializer element that the array elements). So, that {3} does not initialize all the array elements to a value 3, rather it sets the value of the first element only.

Quoting C11, chapter 6.7.9/P21

If there are fewer initializers in a brace-enclosed list than there are elements or members of an aggregate, or fewer characters in a string literal used to initialize an array of known size than there are elements in the array, the remainder of the aggregate shall be initialized implicitly the same as objects that have static storage duration.

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