Why main does not return 0 here?

CLinuxReturnMain

C Problem Overview


I was just reading

ISO/IEC 9899:201x Committee Draft — April 12, 2011

in which i found under 5.1.2.2.3 Program termination

..reaching the } that terminates the main function returns a value of 0. 

it means if you don't specify any return statement in main(), and if the program runs successfully, then at the closing brace } of main will return 0.

But in the following code i don't specify any return statement, yet it does not return 0

#include<stdio.h>
int sum(int a,int b)
{
return (a + b);
}

int main()
{
    int a=10;
    int b=5;
    int ans;    
    ans=sum(a,b);
    printf("sum is %d",ans);
}

compile

gcc test.c  
./a.out
sum is 15
echo $?
9          // here it should be 0 but it shows 9 why?

C Solutions


Solution 1 - C

That rule was added in the 1999 version of the C standard. In C90, the status returned is undefined.

You can enable it by passing -std=c99 to gcc.

As a side note, interestingly 9 is returned because it's the return of printf which just wrote 9 characters.

Solution 2 - C

It returns return value of printf which is number of characters really printed out.

Solution 3 - C

The return value from a function is normally stored in the eax register of the cpu, so the statement "return 4;" would usually compile to

mov eax, 4;
ret;

and return x (depending on your compiler) would be something like:

mov eax, [ebp + 4];
ret;

if you don't specify a return value then the compiler will still spit out the "ret" but doesn't change the value of eax. So the caller will think that what ever was left in the eax register previously is the return value. For this example it would usually be the return value printf, but different compilers will generate different machine code and use some registers differently.

This is a simplified explanation, different calling conventions and target platforms will play a vital role but it should be enough information to explain what is happening 'behind the scenes' in your example.

If you've got a basic understanding of assembler it's worth comparing the disassembly of different compilers. You may find that some compilers are clearing the eax register as a safeguard.

Attributions

All content for this solution is sourced from the original question on Stackoverflow.

The content on this page is licensed under the Attribution-ShareAlike 4.0 International (CC BY-SA 4.0) license.

Content TypeOriginal AuthorOriginal Content on Stackoverflow
QuestionJeegar PatelView Question on Stackoverflow
Solution 1 - CcnicutarView Answer on Stackoverflow
Solution 2 - CSummer_More_More_TeaView Answer on Stackoverflow
Solution 3 - Cnoggin182View Answer on Stackoverflow