1 /* $NetBSD: chk.c,v 1.19 2008/04/26 19:38:30 christos Exp $ */
4 * Copyright (c) 1996 Christopher G. Demetriou. All Rights Reserved.
5 * Copyright (c) 1994, 1995 Jochen Pohl
8 * Redistribution and use in source and binary forms, with or without
9 * modification, are permitted provided that the following conditions
11 * 1. Redistributions of source code must retain the above copyright
12 * notice, this list of conditions and the following disclaimer.
13 * 2. Redistributions in binary form must reproduce the above copyright
14 * notice, this list of conditions and the following disclaimer in the
15 * documentation and/or other materials provided with the distribution.
16 * 3. All advertising materials mentioning features or use of this software
17 * must display the following acknowledgement:
18 * This product includes software developed by Jochen Pohl for
20 * 4. The name of the author may not be used to endorse or promote products
21 * derived from this software without specific prior written permission.
23 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
24 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
25 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
26 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
27 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
28 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
29 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
30 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
31 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
32 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
35 #if HAVE_NBTOOL_CONFIG_H
36 #include "nbtool_config.h"
39 #include <sys/cdefs.h>
40 #if defined(__RCSID) && !defined(lint)
41 __RCSID("$NetBSD: chk.c,v 1.19 2008/04/26 19:38:30 christos Exp $");
50 static void chkund(hte_t
*);
51 static void chkdnu(hte_t
*);
52 static void chkdnud(hte_t
*);
53 static void chkmd(hte_t
*);
54 static void chkvtui(hte_t
*, sym_t
*, sym_t
*);
55 static void chkvtdi(hte_t
*, sym_t
*, sym_t
*);
56 static void chkfaui(hte_t
*, sym_t
*, sym_t
*);
57 static void chkau(hte_t
*, int, sym_t
*, sym_t
*, pos_t
*,
58 fcall_t
*, fcall_t
*, type_t
*, type_t
*);
59 static void chkrvu(hte_t
*, sym_t
*);
60 static void chkadecl(hte_t
*, sym_t
*, sym_t
*);
61 static void printflike(hte_t
*,fcall_t
*, int, const char *, type_t
**);
62 static void scanflike(hte_t
*, fcall_t
*, int, const char *, type_t
**);
63 static void badfmt(hte_t
*, fcall_t
*);
64 static void inconarg(hte_t
*, fcall_t
*, int);
65 static void tofewarg(hte_t
*, fcall_t
*);
66 static void tomanyarg(hte_t
*, fcall_t
*);
67 static int eqtype(type_t
*, type_t
*, int, int, int, int *);
68 static int eqargs(type_t
*, type_t
*, int *);
69 static int mnoarg(type_t
*, int *);
73 * If there is a symbol named "main", mark it as used.
80 if ((hte
= hsearch("main", 0)) != NULL
)
85 * Performs all tests for a single name
90 sym_t
*sym
, *def
, *pdecl
, *decl
;
100 /* Get definition, prototype declaration and declaration */
101 def
= pdecl
= decl
= NULL
;
102 for (sym
= hte
->h_syms
; sym
!= NULL
; sym
= sym
->s_nxt
) {
103 if (def
== NULL
&& (sym
->s_def
== DEF
|| sym
->s_def
== TDEF
))
105 if (pdecl
== NULL
&& sym
->s_def
== DECL
&&
106 TP(sym
->s_type
)->t_tspec
== FUNC
&&
107 TP(sym
->s_type
)->t_proto
) {
110 if (decl
== NULL
&& sym
->s_def
== DECL
)
114 /* A prototype is better than an old style declaration. */
118 chkvtui(hte
, def
, decl
);
120 chkvtdi(hte
, def
, decl
);
122 chkfaui(hte
, def
, decl
);
126 chkadecl(hte
, def
, decl
);
130 * Print a warning if the name has been used, but not defined.
138 if (!hte
->h_used
|| hte
->h_def
)
141 if ((fcall
= hte
->h_calls
) != NULL
) {
142 /* %s used( %s ), but not defined */
143 msg(0, hte
->h_name
, mkpos(&fcall
->f_pos
));
144 } else if ((usym
= hte
->h_usyms
) != NULL
) {
145 /* %s used( %s ), but not defined */
146 msg(0, hte
->h_name
, mkpos(&usym
->u_pos
));
151 * Print a warning if the name has been defined, but never used.
158 if (!hte
->h_def
|| hte
->h_used
)
161 for (sym
= hte
->h_syms
; sym
!= NULL
; sym
= sym
->s_nxt
) {
162 if (sym
->s_def
== DEF
|| sym
->s_def
== TDEF
) {
163 /* %s defined( %s ), but never used */
164 msg(1, hte
->h_name
, mkpos(&sym
->s_pos
));
171 * Print a warning if the variable has been declared, but is not used
179 if (hte
->h_syms
== NULL
|| hte
->h_used
|| hte
->h_def
)
183 if (TP(sym
->s_type
)->t_tspec
== FUNC
)
186 if (sym
->s_def
!= DECL
)
187 errx(1, "internal error: chkdnud() 1");
188 /* %s declared( %s ), but never used or defined */
189 msg(2, hte
->h_name
, mkpos(&sym
->s_pos
));
193 * Print a warning if there is more than one definition for
206 for (sym
= hte
->h_syms
; sym
!= NULL
; sym
= sym
->s_nxt
) {
208 * ANSI C allows tentative definitions of the same name in
209 * only one compilation unit.
211 if (sym
->s_def
!= DEF
&& (!sflag
|| sym
->s_def
!= TDEF
))
217 pos1
= xstrdup(mkpos(&def1
->s_pos
));
218 /* %s multiply defined\t%s :: %s */
219 msg(3, hte
->h_name
, pos1
, mkpos(&sym
->s_pos
));
225 * Print a warning if the return value assumed for a function call
226 * differs from the return value of the function definition or
227 * function declaration.
229 * If no definition/declaration can be found, the assumed return values
230 * are always int. So there is no need to compare with another function
231 * call as it's done for function arguments.
234 chkvtui(hte_t
*hte
, sym_t
*def
, sym_t
*decl
)
242 if (hte
->h_calls
== NULL
)
250 t1
= (tp1
= TP(def
->s_type
)->t_subt
)->t_tspec
;
251 for (call
= hte
->h_calls
; call
!= NULL
; call
= call
->f_nxt
) {
252 tp2
= TP(call
->f_type
)->t_subt
;
253 eq
= eqtype(tp1
, tp2
, 1, 0, 0, (dowarn
= 0, &dowarn
));
254 if (!call
->f_rused
) {
255 /* no return value used */
256 if ((t1
== STRUCT
|| t1
== UNION
) && !eq
) {
258 * If a function returns a struct or union it
259 * must be declared to return a struct or
260 * union, also if the return value is ignored.
261 * This is necessary because the caller must
262 * allocate stack space for the return value.
263 * If it does not, the return value would over-
265 * XXX Following massage may be confusing
266 * because it appears also if the return value
267 * was declared inconsistently. But this
268 * behaviour matches pcc based lint, so it is
271 pos1
= xstrdup(mkpos(&def
->s_pos
));
272 /* %s value must be decl. before use %s :: %s */
274 pos1
, mkpos(&call
->f_pos
));
279 if (!eq
|| (sflag
&& dowarn
)) {
280 pos1
= xstrdup(mkpos(&def
->s_pos
));
281 /* %s value used inconsistenty\t%s :: %s */
282 msg(4, hte
->h_name
, pos1
, mkpos(&call
->f_pos
));
289 * Print a warning if a definition/declaration does not match another
290 * definition/declaration of the same name. For functions, only the
291 * types of return values are tested.
294 chkvtdi(hte_t
*hte
, sym_t
*def
, sym_t
*decl
)
306 tp1
= TP(def
->s_type
);
307 for (sym
= hte
->h_syms
; sym
!= NULL
; sym
= sym
->s_nxt
) {
311 tp2
= TP(sym
->s_type
);
313 if (tp1
->t_tspec
== FUNC
&& tp2
->t_tspec
== FUNC
) {
314 eq
= eqtype(xt1
= tp1
->t_subt
, xt2
= tp2
->t_subt
,
317 eq
= eqtype(xt1
= tp1
, xt2
= tp2
, 0, 0, 0, &dowarn
);
319 if (!eq
|| (sflag
&& dowarn
)) {
321 pos1
= xstrdup(mkpos(&def
->s_pos
));
322 /* %s value declared inconsistently\t%s :: %s */
323 msg(5, hte
->h_name
, tyname(b1
, sizeof(b1
), xt1
),
324 tyname(b2
, sizeof(b2
), xt2
), pos1
,
332 * Print a warning if a function is called with arguments which does
333 * not match the function definition, declaration or another call
334 * of the same function.
337 chkfaui(hte_t
*hte
, sym_t
*def
, sym_t
*decl
)
339 type_t
*tp1
, *tp2
, **ap1
, **ap2
;
341 fcall_t
*calls
, *call
, *call1
;
346 if ((calls
= hte
->h_calls
) == NULL
)
350 * If we find a function definition, we use this for comparison,
351 * otherwise the first prototype we can find. If there is no
352 * definition or prototype declaration, the first function call
358 if ((tp1
= TP(def
->s_type
))->t_tspec
!= FUNC
)
361 } else if (decl
!= NULL
&& TP(decl
->s_type
)->t_proto
) {
362 if ((tp1
= TP(decl
->s_type
))->t_tspec
!= FUNC
)
364 pos1p
= &decl
->s_pos
;
368 calls
= calls
->f_nxt
;
369 if ((tp1
= TP(call1
->f_type
))->t_tspec
!= FUNC
)
371 pos1p
= &call1
->f_pos
;
375 for (call
= calls
; call
!= NULL
; call
= call
->f_nxt
) {
376 if ((tp2
= TP(call
->f_type
))->t_tspec
!= FUNC
)
381 while (*ap1
!= NULL
&& *ap2
!= NULL
) {
382 if (def
!= NULL
&& def
->s_va
&& n
>= def
->s_nva
)
385 chkau(hte
, n
, def
, decl
, pos1p
, call1
, call
,
391 /* equal # of arguments */
392 } else if (def
!= NULL
&& def
->s_va
&& n
>= def
->s_nva
) {
394 * function definition with VARARGS; The # of
395 * arguments of the call must be at least as large
396 * as the parameter of VARARGS.
398 } else if (*ap2
!= NULL
&& tp1
->t_proto
&& tp1
->t_vararg
) {
400 * prototype with ... and function call with
401 * at least the same # of arguments as declared
405 pos1
= xstrdup(mkpos(pos1p
));
406 /* %s: variable # of args\t%s :: %s */
407 msg(7, hte
->h_name
, pos1
, mkpos(&call
->f_pos
));
412 /* perform SCANFLIKE/PRINTFLIKE tests */
413 if (def
== NULL
|| (!def
->s_prfl
&& !def
->s_scfl
))
415 as
= def
->s_prfl
? def
->s_nprfl
: def
->s_nscfl
;
416 for (ai
= call
->f_args
; ai
!= NULL
; ai
= ai
->a_nxt
) {
420 if (ai
== NULL
|| !ai
->a_fmt
)
423 printflike(hte
, call
, n
, ai
->a_fstrg
, ap2
);
425 scanflike(hte
, call
, n
, ai
->a_fstrg
, ap2
);
431 * Check a single argument in a function call.
433 * hte a pointer to the hash table entry of the function
434 * n the number of the argument (1..)
435 * def the function definition or NULL
436 * decl prototype declaration, old style declaration or NULL
437 * pos1p position of definition, declaration of first call
438 * call1 first call, if both def and decl are old style def/decl
440 * arg1 currently checked argument of def/decl/call1
441 * arg2 currently checked argument of call
445 chkau(hte_t
*hte
, int n
, sym_t
*def
, sym_t
*decl
, pos_t
*pos1p
,
446 fcall_t
*call1
, fcall_t
*call
, type_t
*arg1
, type_t
*arg2
)
448 int promote
, asgn
, dowarn
;
452 char tyname1
[64], tyname2
[64];
455 * If a function definition is available (def != NULL), we compair the
456 * function call (call) with the definition. Otherwise, if a function
457 * definition is available and it is not an old style definition
458 * (decl != NULL && TP(decl->s_type)->t_proto), we compair the call
459 * with this declaration. Otherwise we compair it with the first
460 * call we have found (call1).
463 /* arg1 must be promoted if it stems from an old style definition */
464 promote
= def
!= NULL
&& def
->s_osdef
;
467 * If we compair with a definition or declaration, we must perform
468 * the same checks for qualifiers in indirected types as in
471 asgn
= def
!= NULL
|| (decl
!= NULL
&& TP(decl
->s_type
)->t_proto
);
474 if (eqtype(arg1
, arg2
, 1, promote
, asgn
, &dowarn
) && (!sflag
|| !dowarn
))
478 * Other lint implementations print warnings as soon as the type
479 * of an argument does not match exactly the expected type. The
480 * result are lots of warnings which are really not necessary.
481 * We print a warning only if
482 * (0) at least one type is not an interger type and types differ
483 * (1) hflag is set and types differ
484 * (2) types differ, except in signedness
485 * If the argument is an integer constant whose msb is not set,
486 * signedness is ignored (e.g. 0 matches both signed and unsigned
487 * int). This is with and without hflag.
488 * If the argument is an integer constant with value 0 and the
489 * expected argument is of type pointer and the width of the
490 * interger constant is the same as the width of the pointer,
491 * no warning is printed.
495 if (isityp(t1
) && isityp(t2
) && !arg1
->t_isenum
&& !arg2
->t_isenum
) {
498 * XXX Here is a problem: Althrough it is possible to
499 * pass an int where a char/short it expected, there
500 * may be loss in significant digits. We should first
501 * check for const arguments if they can be converted
502 * into the original parameter type.
506 } else if (t1
== CHAR
|| t1
== SCHAR
) {
508 } else if (t1
== UCHAR
) {
509 t1
= tflag
? UINT
: INT
;
510 } else if (t1
== SHORT
) {
512 } else if (t1
== USHORT
) {
514 t1
= INT_MAX
< USHRT_MAX
|| tflag
? UINT
: INT
;
518 if (styp(t1
) == styp(t2
)) {
521 * types differ only in signedness; get information
526 * treat a definition like a call with variable
529 ai1
= call1
!= NULL
? call1
->f_args
: NULL
;
532 * if two calls are compared, ai1 is set to the
533 * information for the n-th argument, if this was
534 * a constant, otherwise to NULL
536 for ( ; ai1
!= NULL
; ai1
= ai1
->a_nxt
) {
541 * ai is set to the information of the n-th arg
542 * of the (second) call, if this was a constant,
545 for (ai
= call
->f_args
; ai
!= NULL
; ai
= ai
->a_nxt
) {
550 if (ai1
== NULL
&& ai
== NULL
) {
551 /* no constant at all */
554 } else if (ai1
== NULL
|| ai
== NULL
) {
558 if (ai
->a_zero
|| ai
->a_pcon
)
559 /* same value in signed and unsigned */
561 /* value (not representation) differently */
564 * two constants, one signed, one unsigned;
565 * if the msb of one of the constants is set,
566 * the argument is used inconsistently.
568 if (!ai1
->a_ncon
&& !ai
->a_ncon
)
573 } else if (t1
== PTR
&& isityp(t2
)) {
574 for (ai
= call
->f_args
; ai
!= NULL
; ai
= ai
->a_nxt
) {
579 * Vendor implementations of lint (e.g. HP-UX, Digital UNIX)
580 * don't care about the size of the integer argument,
581 * only whether or not it is zero. We do the same.
583 if (ai
!= NULL
&& ai
->a_zero
)
587 pos1
= xstrdup(mkpos(pos1p
));
588 /* %s, arg %d used inconsistently\t%s[%s] :: %s[%s] */
589 msg(6, hte
->h_name
, n
, pos1
,
590 tyname(tyname1
, sizeof(tyname1
), arg1
),
592 tyname(tyname2
, sizeof(tyname2
), arg2
));
597 * Compare the types in the NULL-terminated array ap with the format
601 printflike(hte_t
*hte
, fcall_t
*call
, int n
, const char *fmt
, type_t
**ap
)
605 int fwidth
, prec
, left
, sign
, space
, alt
, zero
;
606 tspec_t sz
, t1
, t2
= NOTSPEC
;
615 tomanyarg(hte
, call
);
623 fwidth
= prec
= left
= sign
= space
= alt
= zero
= 0;
632 } else if (fc
== '+') {
636 } else if (fc
== ' ') {
640 } else if (fc
== '#') {
644 } else if (fc
== '0') {
657 do { fc
= *fp
++; } while (isdigit(fc
)) ;
658 } else if (fc
== '*') {
661 if ((tp
= *ap
++) == NULL
) {
666 if ((t1
= tp
->t_tspec
) != INT
&& (hflag
|| t1
!= UINT
))
667 inconarg(hte
, call
, n
);
675 do { fc
= *fp
++; } while (isdigit(fc
));
676 } else if (fc
== '*') {
678 if ((tp
= *ap
++) == NULL
) {
683 if (tp
->t_tspec
!= INT
)
684 inconarg(hte
, call
, n
);
693 } else if (fc
== 'l') {
695 } else if (fc
== 'q') {
697 } else if (fc
== 'L') {
704 if (sz
!= NOTSPEC
|| left
|| sign
|| space
||
705 alt
|| zero
|| prec
|| fwidth
) {
717 if ((tp
= *ap
++) == NULL
) {
722 if ((t1
= tp
->t_tspec
) == PTR
)
723 t2
= tp
->t_subt
->t_tspec
;
725 if (fc
== 'd' || fc
== 'i') {
726 if (alt
|| sz
== LDOUBLE
) {
732 if (t1
!= LONG
&& (hflag
|| t1
!= ULONG
))
733 inconarg(hte
, call
, n
);
734 } else if (sz
== QUAD
) {
735 if (t1
!= QUAD
&& (hflag
|| t1
!= UQUAD
))
736 inconarg(hte
, call
, n
);
739 * SHORT is always promoted to INT, USHORT
742 if (t1
!= INT
&& (hflag
|| t1
!= UINT
))
743 inconarg(hte
, call
, n
);
745 } else if (fc
== 'o' || fc
== 'u' || fc
== 'x' || fc
== 'X') {
746 if ((alt
&& fc
== 'u') || sz
== LDOUBLE
)
750 if (t1
!= ULONG
&& (hflag
|| t1
!= LONG
))
751 inconarg(hte
, call
, n
);
752 } else if (sz
== QUAD
) {
753 if (t1
!= UQUAD
&& (hflag
|| t1
!= QUAD
))
754 inconarg(hte
, call
, n
);
755 } else if (sz
== SHORT
) {
756 /* USHORT was promoted to INT or UINT */
757 if (t1
!= UINT
&& t1
!= INT
)
758 inconarg(hte
, call
, n
);
760 if (t1
!= UINT
&& (hflag
|| t1
!= INT
))
761 inconarg(hte
, call
, n
);
763 } else if (fc
== 'D' || fc
== 'O' || fc
== 'U') {
764 if ((alt
&& fc
!= 'O') || sz
!= NOTSPEC
|| !tflag
)
772 } else if (fc
== 'f' || fc
== 'e' || fc
== 'E' ||
773 fc
== 'g' || fc
== 'G') {
776 if (sz
!= DOUBLE
&& sz
!= LDOUBLE
)
779 inconarg(hte
, call
, n
);
780 } else if (fc
== 'c') {
781 if (sz
!= NOTSPEC
|| alt
|| zero
)
784 inconarg(hte
, call
, n
);
785 } else if (fc
== 's') {
786 if (sz
!= NOTSPEC
|| alt
|| zero
)
789 (t2
!= CHAR
&& t2
!= UCHAR
&& t2
!= SCHAR
)) {
790 inconarg(hte
, call
, n
);
792 } else if (fc
== 'p') {
793 if (fwidth
|| prec
|| sz
!= NOTSPEC
|| alt
|| zero
)
795 if (t1
!= PTR
|| (hflag
&& t2
!= VOID
))
796 inconarg(hte
, call
, n
);
797 } else if (fc
== 'n') {
798 if (fwidth
|| prec
|| alt
|| zero
|| sz
== LDOUBLE
)
801 inconarg(hte
, call
, n
);
802 } else if (sz
== LONG
) {
803 if (t2
!= LONG
&& t2
!= ULONG
)
804 inconarg(hte
, call
, n
);
805 } else if (sz
== SHORT
) {
806 if (t2
!= SHORT
&& t2
!= USHORT
)
807 inconarg(hte
, call
, n
);
809 if (t2
!= INT
&& t2
!= UINT
)
810 inconarg(hte
, call
, n
);
822 * Compare the types in the NULL-terminated array ap with the format
826 scanflike(hte_t
*hte
, fcall_t
*call
, int n
, const char *fmt
, type_t
**ap
)
831 tspec_t sz
, t1
= NOTSPEC
, t2
= NOTSPEC
;
840 tomanyarg(hte
, call
);
859 do { fc
= *fp
++; } while (isdigit(fc
));
864 } else if (fc
== 'l') {
866 } else if (fc
== 'q') {
868 } else if (fc
== 'L') {
875 if (sz
!= NOTSPEC
|| noasgn
|| fwidth
)
882 if ((tp
= *ap
++) == NULL
) {
887 if ((t1
= tp
->t_tspec
) == PTR
)
888 t2
= tp
->t_subt
->t_tspec
;
891 if (fc
== 'd' || fc
== 'i' || fc
== 'n') {
894 if (sz
!= SHORT
&& sz
!= LONG
&& sz
!= QUAD
)
899 inconarg(hte
, call
, n
);
900 } else if (t2
!= styp(sz
)) {
901 inconarg(hte
, call
, n
);
902 } else if (hflag
&& t2
!= sz
) {
903 inconarg(hte
, call
, n
);
904 } else if (tp
->t_subt
->t_const
) {
905 inconarg(hte
, call
, n
);
908 } else if (fc
== 'o' || fc
== 'u' || fc
== 'x') {
913 } else if (sz
== LONG
) {
915 } else if (sz
== QUAD
) {
921 } else if (fc
== 'D') {
922 if (sz
!= NOTSPEC
|| !tflag
)
926 } else if (fc
== 'O') {
927 if (sz
!= NOTSPEC
|| !tflag
)
931 } else if (fc
== 'X') {
933 * XXX valid in ANSI C, but in NetBSD's libc imple-
934 * mented as "lx". Thats why it should be avoided.
936 if (sz
!= NOTSPEC
|| !tflag
)
940 } else if (fc
== 'E') {
942 * XXX valid in ANSI C, but in NetBSD's libc imple-
943 * mented as "lf". Thats why it should be avoided.
945 if (sz
!= NOTSPEC
|| !tflag
)
949 } else if (fc
== 'F') {
950 /* XXX only for backward compatibility */
951 if (sz
!= NOTSPEC
|| !tflag
)
955 } else if (fc
== 'G') {
957 * XXX valid in ANSI C, but in NetBSD's libc not
960 if (sz
!= NOTSPEC
&& sz
!= LONG
&& sz
!= LDOUBLE
)
963 } else if (fc
== 'e' || fc
== 'f' || fc
== 'g') {
967 } else if (sz
== LONG
) {
969 } else if (sz
!= LDOUBLE
) {
974 } else if (fc
== 's' || fc
== '[' || fc
== 'c') {
978 if ((fc
= *fp
++) == '-') {
990 inconarg(hte
, call
, n
);
991 } else if (t2
!= CHAR
&& t2
!= UCHAR
&&
993 inconarg(hte
, call
, n
);
996 } else if (fc
== 'p') {
1000 if (t1
!= PTR
|| t2
!= PTR
) {
1001 inconarg(hte
, call
, n
);
1002 } else if (tp
->t_subt
->t_subt
->t_tspec
!=VOID
) {
1004 inconarg(hte
, call
, n
);
1017 badfmt(hte_t
*hte
, fcall_t
*call
)
1020 /* %s: malformed format string\t%s */
1021 msg(13, hte
->h_name
, mkpos(&call
->f_pos
));
1025 inconarg(hte_t
*hte
, fcall_t
*call
, int n
)
1028 /* %s, arg %d inconsistent with format\t%s(%d) */
1029 msg(14, hte
->h_name
, n
, mkpos(&call
->f_pos
));
1033 tofewarg(hte_t
*hte
, fcall_t
*call
)
1036 /* %s: too few args for format \t%s */
1037 msg(15, hte
->h_name
, mkpos(&call
->f_pos
));
1041 tomanyarg(hte_t
*hte
, fcall_t
*call
)
1044 /* %s: too many args for format \t%s */
1045 msg(16, hte
->h_name
, mkpos(&call
->f_pos
));
1050 * Print warnings for return values which are used, but not returned,
1051 * or return values which are always or sometimes ignored.
1054 chkrvu(hte_t
*hte
, sym_t
*def
)
1060 /* don't know wheter or not the functions returns a value */
1063 if (hte
->h_calls
== NULL
)
1067 /* function has return value */
1069 for (call
= hte
->h_calls
; call
!= NULL
; call
= call
->f_nxt
) {
1070 used
|= call
->f_rused
|| call
->f_rdisc
;
1071 ignored
|= !call
->f_rused
&& !call
->f_rdisc
;
1074 * XXX as soon as we are able to disable single warnings
1075 * the following dependencies from hflag should be removed.
1076 * but for now I do'nt want to be botherd by this warnings
1077 * which are almost always useless.
1079 if (!used
&& ignored
) {
1081 /* %s returns value which is always ignored */
1082 msg(8, hte
->h_name
);
1083 } else if (used
&& ignored
) {
1085 /* %s returns value which is sometimes ign. */
1086 msg(9, hte
->h_name
);
1089 /* function has no return value */
1090 for (call
= hte
->h_calls
; call
!= NULL
; call
= call
->f_nxt
) {
1092 /* %s value is used( %s ), but none ret. */
1093 msg(10, hte
->h_name
, mkpos(&call
->f_pos
));
1099 * Print warnings for inconsistent argument declarations.
1102 chkadecl(hte_t
*hte
, sym_t
*def
, sym_t
*decl
)
1104 int osdef
, eq
, dowarn
, n
;
1106 type_t
**ap1
, **ap2
, *tp1
, *tp2
;
1112 osdef
= def
->s_osdef
;
1114 } else if (decl
!= NULL
&& TP(decl
->s_type
)->t_proto
) {
1119 if (TP(sym1
->s_type
)->t_tspec
!= FUNC
)
1123 * XXX Prototypes should also be compared with old style function
1127 for (sym
= hte
->h_syms
; sym
!= NULL
; sym
= sym
->s_nxt
) {
1128 if (sym
== sym1
|| !TP(sym
->s_type
)->t_proto
)
1130 ap1
= TP(sym1
->s_type
)->t_args
;
1131 ap2
= TP(sym
->s_type
)->t_args
;
1133 while (*ap1
!= NULL
&& *ap2
!= NULL
) {
1136 eq
= eqtype(xt1
= *ap1
, xt2
= *ap2
, 1, osdef
, 0, &dowarn
);
1137 if (!eq
|| dowarn
) {
1138 char b1
[64], b2
[64];
1139 pos1
= xstrdup(mkpos(&sym1
->s_pos
));
1140 pos2
= mkpos(&sym
->s_pos
);
1141 /* %s, arg %d declared inconsistently ... */
1142 msg(11, hte
->h_name
, n
+ 1,
1143 tyname(b1
, sizeof(b1
), xt1
),
1144 tyname(b2
, sizeof(b2
), xt2
), pos1
, pos2
);
1152 tp1
= TP(sym1
->s_type
);
1153 tp2
= TP(sym
->s_type
);
1154 if (tp1
->t_vararg
== tp2
->t_vararg
)
1156 if (tp2
->t_vararg
&&
1157 sym1
->s_va
&& sym1
->s_nva
== n
&& !sflag
) {
1161 /* %s: variable # of args declared\t%s :: %s */
1162 pos1
= xstrdup(mkpos(&sym1
->s_pos
));
1163 msg(12, hte
->h_name
, pos1
, mkpos(&sym
->s_pos
));
1170 * Check compatibility of two types. Returns 1 if types are compatible,
1173 * ignqual if set, ignore qualifiers of outhermost type; used for
1174 * function arguments
1175 * promote if set, promote left type before comparison; used for
1176 * comparisons of arguments with parameters of old style
1178 * asgn left indirected type must have at least the same qualifiers
1179 * like right indirected type (for assignments and function
1181 * *dowarn set to 1 if an old style declaration was compared with
1182 * an incompatible prototype declaration
1185 eqtype(type_t
*tp1
, type_t
*tp2
, int ignqual
, int promot
, int asgn
, int *dowarn
)
1193 while (tp1
!= NULL
&& tp2
!= NULL
) {
1199 } else if (t
== CHAR
|| t
== SCHAR
) {
1201 } else if (t
== UCHAR
) {
1202 t
= tflag
? UINT
: INT
;
1203 } else if (t
== SHORT
) {
1205 } else if (t
== USHORT
) {
1207 t
= INT_MAX
< USHRT_MAX
|| tflag
? UINT
: INT
;
1211 if (asgn
&& to
== PTR
) {
1212 if (indir
== 1 && (t
== VOID
|| tp2
->t_tspec
== VOID
))
1216 if (t
!= tp2
->t_tspec
) {
1218 * Give pointer to types which differ only in
1219 * signedness a chance if not sflag and not hflag.
1221 if (sflag
|| hflag
|| to
!= PTR
)
1223 if (styp(t
) != styp(tp2
->t_tspec
))
1227 if (tp1
->t_isenum
&& tp2
->t_isenum
) {
1228 if (tp1
->t_istag
&& tp2
->t_istag
) {
1229 return (tp1
->t_tag
== tp2
->t_tag
);
1230 } else if (tp1
->t_istynam
&& tp2
->t_istynam
) {
1231 return (tp1
->t_tynam
== tp2
->t_tynam
);
1232 } else if (tp1
->t_isuniqpos
&& tp2
->t_isuniqpos
) {
1233 return (tp1
->t_uniqpos
.p_line
==
1234 tp2
->t_uniqpos
.p_line
&&
1235 tp1
->t_uniqpos
.p_file
==
1236 tp2
->t_uniqpos
.p_file
&&
1237 tp1
->t_uniqpos
.p_uniq
==
1238 tp2
->t_uniqpos
.p_uniq
);
1245 * XXX Handle combinations of enum and int if eflag is set.
1246 * But note: enum and 0 should be allowed.
1249 if (asgn
&& indir
== 1) {
1250 if (!tp1
->t_const
&& tp2
->t_const
)
1252 if (!tp1
->t_volatile
&& tp2
->t_volatile
)
1254 } else if (!ignqual
&& !tflag
) {
1255 if (tp1
->t_const
!= tp2
->t_const
)
1257 if (tp1
->t_const
!= tp2
->t_const
)
1261 if (t
== STRUCT
|| t
== UNION
) {
1262 if (tp1
->t_istag
&& tp2
->t_istag
) {
1263 return (tp1
->t_tag
== tp2
->t_tag
);
1264 } else if (tp1
->t_istynam
&& tp2
->t_istynam
) {
1265 return (tp1
->t_tynam
== tp2
->t_tynam
);
1266 } else if (tp1
->t_isuniqpos
&& tp2
->t_isuniqpos
) {
1267 return (tp1
->t_uniqpos
.p_line
==
1268 tp2
->t_uniqpos
.p_line
&&
1269 tp1
->t_uniqpos
.p_file
==
1270 tp2
->t_uniqpos
.p_file
&&
1271 tp1
->t_uniqpos
.p_uniq
==
1272 tp2
->t_uniqpos
.p_uniq
);
1278 if (t
== ARRAY
&& tp1
->t_dim
!= tp2
->t_dim
) {
1279 if (tp1
->t_dim
!= 0 && tp2
->t_dim
!= 0)
1284 if (tp1
->t_proto
&& tp2
->t_proto
) {
1285 if (!eqargs(tp1
, tp2
, dowarn
))
1287 } else if (tp1
->t_proto
) {
1288 if (!mnoarg(tp1
, dowarn
))
1290 } else if (tp2
->t_proto
) {
1291 if (!mnoarg(tp2
, dowarn
))
1298 ignqual
= promot
= 0;
1304 return (tp1
== tp2
);
1308 * Compares arguments of two prototypes
1311 eqargs(type_t
*tp1
, type_t
*tp2
, int *dowarn
)
1315 if (tp1
->t_vararg
!= tp2
->t_vararg
)
1321 while (*a1
!= NULL
&& *a2
!= NULL
) {
1323 if (eqtype(*a1
, *a2
, 1, 0, 0, dowarn
) == 0)
1331 return (*a1
== *a2
);
1335 * mnoarg() (matches functions with no argument type information)
1336 * returns 1 if all parameters of a prototype are compatible with
1337 * and old style function declaration.
1338 * This is the case if following conditions are met:
1339 * 1. the prototype must have a fixed number of parameters
1340 * 2. no parameter is of type float
1341 * 3. no parameter is converted to another type if integer promotion
1345 mnoarg(type_t
*tp
, int *dowarn
)
1350 if (tp
->t_vararg
&& dowarn
!= NULL
)
1352 for (arg
= tp
->t_args
; *arg
!= NULL
; arg
++) {
1353 if ((t
= (*arg
)->t_tspec
) == FLOAT
)
1355 if (t
== CHAR
|| t
== SCHAR
|| t
== UCHAR
)
1357 if (t
== SHORT
|| t
== USHORT
)