Strange behaviour with overflow and initialize of int variables

I just sat down to prepare my lessons, emphasizing the importance of choosing proper data types. The example I selected was this:

void setup() {
  Serial.begin(9600);
  Serial.println(__FILE__);
  Serial.print("Arduino: ");
  Serial.println(ARDUINO);
  Serial.print("Version ");
  Serial.println(__VERSION__);
  int intVar = 0;
  Serial.print("size of intVar [bytes] = ");
  Serial.println(sizeof intVar);
  int foo;
  for (int i = 0; i < 25; i++) {
    Serial.print(i);
    Serial.print(" ");
    Serial.println(intVar);
    intVar = intVar + 5000;
  }
}

void loop() {}

but to my surprise no overflow happened. See the results:

Arduino: 10812
Version 7.3.0
size of intVar [bytes] = 2
0 0
1 5000
2 10000
3 15000
4 20000
5 25000
6 30000
7 35000
8 40000
and so on ...

There should have been an overflow after 30000.
(Using Arduino 1.0.6 I got the overflow as expected.)
Checking with avr-objdump.exe I found a call of the multiply routine. But my code does not contain any multiplies.
As I stepped deeper into the matter I tried this:

/*
 * foo1 and bar1 not initialized,
 * initial value unknown.
 * foo3 initialized, but bar3 is not,
 * foo3 remains zero.
 * the other foo's overflow as expected.
 */

void setup() {
  Serial.begin(9600);
  Serial.println("i\tfoo1\tfoo2\tfoo3\tfoo4");
  int foo1;
  int foo2; // seems to be zero
  int foo3 = 0;
  int foo4 = 0;
  int bar1; // seems to be zero
  int bar2 = 0;
  int bar3;
  for (int i = 0; i < 25; i++) {
    Serial.print(i);
    Serial.print("\t");
    Serial.print(foo1);
    Serial.print("\t");
    Serial.print(foo2);
    Serial.print("\t");
    Serial.print(foo3);
    Serial.print("\t");
    Serial.print(foo4);
    Serial.println();
    // updating the foo's:
    foo1 = foo1 + 5000 + bar1;
    foo2 = foo2 + 5000 + bar2;
    foo3 = foo3 + 5000 + bar3;
    foo4 = foo4 + 5000;
  }
}

void loop() {}

See the results:

i	foo1	foo2	foo3	foo4
0	32512	0	0	0
1	-28024	5000	0	5000
2	-23024	10000	0	10000
3	-18024	15000	0	15000
4	-13024	20000	0	20000
5	-8024	25000	0	25000
6	-3024	30000	0	30000
7	1976	-30536	0	-30536
8	6976	-25536	0	-25536
9	11976	-20536	0	-20536
10	16976	-15536	0	-15536
11	21976	-10536	0	-10536
12	26976	-5536	0	-5536
13	31976	-536	0	-536
14	-28560	4464	0	4464
15	-23560	9464	0	9464
16	-18560	14464	0	14464
17	-13560	19464	0	19464
18	-8560	24464	0	24464
19	-3560	29464	0	29464
20	1440	-31072	0	-31072
21	6440	-26072	0	-26072
22	11440	-21072	0	-21072
23	16440	-16072	0	-16072
24	21440	-11072	0	-11072

All my assumptions about initalizing of variables were proven false.
Should I better go back coding in assembler language?
What happened to gcc?

when I ran you're original code I got the following

C:\stuff\SW\Arduino\_Others\Download\Tst\Tst.ino
Arduino: 10801
Version 4.9.2
size of intVar [bytes] = 2
0 0
1 5000
2 10000
3 15000
4 20000
5 25000
6 30000
7 -30536
8 -25536
9 -20536
10 -15536
11 -10536
12 -5536
13 -536
14 4464
15 9464
16 14464
17 19464
18 24464
19 29464
20 -31072
21 -26072
22 -21072
23 -16072
24 -11072

but i'm also a big fan of maximizing error/warnings from the compiler and got the following warnings (see File->Preferences Compiler warnings). New code shouldn't have warnings.

C:\stuff\SW\Arduino\_Others\Download\Tst\Tst.ino: In function 'void setup()':

C:\stuff\SW\Arduino\_Others\Download\Tst\Tst.ino:12:9: warning: unused variable 'foo' [-Wunused-variable]

     int foo;

         ^

C:\stuff\SW\Arduino\_Others\Download\Tst\Tst.ino:18:31: warning: iteration 6 invokes undefined behavior [-Waggressive-loop-optimizations]

         intVar = intVar + 5000;

                               ^

C:\stuff\SW\Arduino\_Others\Download\Tst\Tst.ino:14:5: note: containing loop

     for (int i = 0; i < 25; i++) {

     ^

C:\Tools\Arduino\hardware\arduino\avr\cores\arduino\main.cpp: In function 'main':

C:\stuff\SW\Arduino\_Others\Download\Tst\Tst.ino:18:31: warning: iteration 6 invokes undefined behavior [-Waggressive-loop-optimizations]

         intVar = intVar + 5000;

                               ^

C:\stuff\SW\Arduino\_Others\Download\Tst\Tst.ino:14:5: note: containing loop

     for (int i = 0; i < 25; i++) {

     ^

Sketch uses 1996 bytes (6%) of program storage space. Maximum is 32256 bytes.
Global variables use 286 bytes (13%) of dynamic memory, leaving 1762 bytes for local variables. Maximum is 2048 bytes.