Menjawab karena semua jawaban yang ada mengatakan bahwa itu adalah perilaku yang tidak ditentukan, yang tidak benar, jadi saya tidak memiliki apa pun yang dapat saya beri suara positif.
Di C89 (terima kasih kepada pmg untuk referensi ke draf standar), 5.1.2.2.3:
Pengembalian dari panggilan awal ke fungsi utama sama dengan memanggil fungsi keluar dengan nilai yang dikembalikan oleh fungsi utama sebagai argumennya. Jika }yang menghentikan fungsi utama tercapai, status penghentian yang dikembalikan ke lingkungan host tidak ditentukan.
Di C99, mengutip dari n1256, 5.1.2.2.3:
Jika tipe pengembalian dari fungsi utama adalah tipe yang kompatibel di dalamnya, pengembalian dari panggilan awal ke fungsi utama sama dengan memanggil fungsi keluar dengan nilai yang dikembalikan oleh fungsi utama sebagai argumennya; mencapai } yang menghentikan fungsi utama mengembalikan nilai 0. Jika jenis yang dikembalikan tidak kompatibel dengan int, status penghentian yang dikembalikan ke lingkungan host tidak ditentukan.
Jadi, ini bukan "perilaku tidak terdefinisi":perilakunya seperti main
mengembalikan fungsi, tetapi dalam C89 nilai yang dikembalikan tidak ditentukan oleh standar. Untuk program contoh Anda, pada implementasi Anda, nilai yang dikembalikan tampaknya secara konsisten adalah 12, mungkin karena alasan yang dikatakan Ben Voigt. Karena Anda menggunakan linux, mungkin bukan perubahan besar untuk mengkompilasi kode Anda sebagai C99 (atau bagaimanapun juga, kompilasi menggunakan mode C99 yang hampir sesuai dengan gcc).
Untuk setiap fungsi yang mengembalikan nilai, selain main
, itu adalah perilaku tidak terdefinisi, kecuali penelepon tidak menggunakan nilai pengembalian (n1256, 6.9.1/12):
Jika } yang mengakhiri fungsi tercapai, dan nilai pemanggilan fungsi digunakan oleh pemanggil, perilaku tidak terdefinisi.
Saya tidak yakin apakah panggilan awal ke main
harus disebutkan sebagai dikecualikan dari aturan umum ini. Tidak perlu:dari POV standar, panggilan itu tidak memiliki pemanggil, jadi menurut saya nilai pemanggilan fungsi tidak "digunakan oleh pemanggil", meskipun itu menjadi status terminasi untuk program.
Seperti kata swegi, ini adalah perilaku yang tidak ditentukan. Seperti yang dikatakan Steve Jessop et al, ini adalah nilai yang tidak ditentukan hingga C89, dan ditentukan dalam C99 (perilaku yang diamati tidak sesuai dengan C99)
Apa yang sebenarnya terjadi di sebagian besar lingkungan adalah nilai kembalian dari printf
terakhir dibiarkan dalam register yang digunakan untuk mengembalikan nilai.
Jadi, 11 untuk n ==0, 12 jika n adalah satu digit, 14 untuk dua digit n, 16 untuk tiga digit n, dst.