Search code examples
cgccclangwarnings

warning: type of ‘n’ defaults to ‘int’ [-Wimplicit-int] warning in 'gcc' , but no warning in 'clang'


I've written a simple code to print n numbers recursively:

  1 #include<stdio.h>
  2 
  3 void print(n)
  4 {
  5 printf("%d\t", n);
  6 if(n>=1)
  7     {
  8 print(n-1);
  9     }
 10     
 11 return;
 12 }
 13 
 14 
 15 int main()
 16 {
 17 int n;
 18 
 19 print(6);
 20 
 21return 0;
 22 }

It is compiled without any warning by clang, but gcc complains and I get the warning:

warning: type of ‘n’ defaults to ‘int’ [-Wimplicit-int]

The code is executed flawlessly even when it's compiled by gcc. I want to know:

  • Why do I get the warning?
  • Why do compilers behave differently?

P.S. I use these command to compile them:

cc 1.c -o 1

clang 1.c -o 1

compilers' version:

clang version 10.0.0-4ubuntu1
gcc (Ubuntu 9.3.0-17ubuntu1~20.04) 9.3.0


Solution

  • A compiler conforming to the C standard must issue a diagnostic for the missing declaration, per the constraint in C 2018 6.9.1 6 (bold and footnotes are mine):

    If the declarator includes an identifier list1, each declaration in the declaration list2 shall have at least one declarator, those declarators shall declare only identifiers from the identifier list, and every identifier in the identifier list shall be declared

    A declarator for n in the declaration list would be the appearance of n in a declaration such as int n;. Since there is none, this violates the constraint, and a conforming compiler must issue a diagnostic (per 5.1.1.3 1).

    Clang’s default mode is not conforming to the C standard. You can request better adherence with -pedantic, after which Clang reports:

    warning: parameter 'n' was not declared, defaulting to type 'int'
    

    I suggest using at least the switches -Wmost -Werror -pedantic -O3 -std=c17.

    I also prefer -Wno-shift-op-parentheses -Wno-logical-op-parentheses.

    Footnotes

    1 An identifier list is a list of identifiers for function parameters, without types. The n in void print(n) is an identifier list.

    2 A declaration list is a list of declarations after the ) that ends the function parameters and before the { that starts the function body. The declaration list for the print function in the code in the question is empty.