strtol
is declared in header <stdlib.h>
as
long strtol( const char *restrict str, char **restrict str_end, int base );
// ^^^^^^^^ ^^^^^^^^ since C99
In the first posted snippet, <stdlib.h>
is not included and the function is called with one single argument, so that, if compiled with -Wall -Wextra -std=gnu11
, gcc produces the following explanatory warnings before outputting 0:
prog.c: In function 'main':
prog.c:5:21: warning: implicit declaration of function 'strtol' [-Wimplicit-function-declaration]
printf("%ld\n", strtol("99999999999999999999999"));
^~~~~~
prog.c:5:15: warning: format '%ld' expects argument of type 'long int', but argument 2 has type 'int' [-Wformat=]
printf("%ld\n", strtol("99999999999999999999999"));
~~^ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
%d
Which means that the library function is not called at all and an implicitly declared function with the same name is called, an int
with value 0 is returned and printed (with the wrong format specifier, which is itself undefined behavior).
Note that the same code fails to compile with clang, which reports the following:
prog.c:4:21: warning: implicitly declaring library function 'strtol' with type 'long (const char *, char **, int)' [-Wimplicit-function-declaration]
printf("%ld\n", strtol("99999999999999999999999"));
^
prog.c:4:21: note: include the header <stdlib.h> or explicitly provide a declaration for 'strtol'
prog.c:4:53: error: too few arguments to function call, expected 3, have 1
printf("%ld\n", strtol("99999999999999999999999"));
~~~~~~ ^
1 warning and 1 error generated.
In the second snippet, strtol
is called with the right number of arguments, but, as posted (with the #include
commented out), has the same missing header problem. To produce the expected output, LONG_MAX, header stdlib.h
has to be included.