To make functions compatible, follow these rules:
For two function types to be compatible, their return types must be compatible. If either or both function types have prototypes, the rules are more complicated.
For two function types with prototypes to be compatible, they also must have the same number of parameters, including use of the ellipsis (…) notation, and the corresponding parameters must be parameter-compatible.
For an old-style function definition to be compatible with a function type with a prototype, the prototype parameters must not end with an ellipsis (…). Each of the prototype parameters must be parameter-compatible with the corresponding old-style parameter, after application of the default argument promotions.
For an old-style function declaration (not a definition) to be compatible with a function type with a prototype, the prototype parameters must not end with an ellipsis (…). All of the prototype parameters must have types that would be unaffected by the default argument promotions.
For two types to be parameter-compatible, the types must be compatible after the top-level qualifiers, if any, have been removed, and after a function or array type has been converted to the appropriate pointer type.