tree.c revision 1.108 1 /* $NetBSD: tree.c,v 1.108 2021/01/01 00:00:24 rillig Exp $ */
2
3 /*
4 * Copyright (c) 1994, 1995 Jochen Pohl
5 * All Rights Reserved.
6 *
7 * Redistribution and use in source and binary forms, with or without
8 * modification, are permitted provided that the following conditions
9 * are met:
10 * 1. Redistributions of source code must retain the above copyright
11 * notice, this list of conditions and the following disclaimer.
12 * 2. Redistributions in binary form must reproduce the above copyright
13 * notice, this list of conditions and the following disclaimer in the
14 * documentation and/or other materials provided with the distribution.
15 * 3. All advertising materials mentioning features or use of this software
16 * must display the following acknowledgement:
17 * This product includes software developed by Jochen Pohl for
18 * The NetBSD Project.
19 * 4. The name of the author may not be used to endorse or promote products
20 * derived from this software without specific prior written permission.
21 *
22 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
23 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
24 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
25 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
26 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
27 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
28 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
29 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
30 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
31 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
32 */
33
34 #if HAVE_NBTOOL_CONFIG_H
35 #include "nbtool_config.h"
36 #endif
37
38 #include <sys/cdefs.h>
39 #if defined(__RCSID) && !defined(lint)
40 __RCSID("$NetBSD: tree.c,v 1.108 2021/01/01 00:00:24 rillig Exp $");
41 #endif
42
43 #include <float.h>
44 #include <limits.h>
45 #include <math.h>
46 #include <signal.h>
47 #include <stdlib.h>
48 #include <string.h>
49
50 #include "lint1.h"
51 #include "cgram.h"
52 #include "externs1.h"
53
54 static tnode_t *new_int_const_node(tspec_t, int64_t);
55 static void check_pointer_comparison(op_t, tnode_t *, tnode_t *);
56 static int check_assign_types_compatible(op_t, int, tnode_t *, tnode_t *);
57 static void check_bad_enum_operation(op_t, tnode_t *, tnode_t *);
58 static void check_enum_type_mismatch(op_t, int, tnode_t *, tnode_t *);
59 static void check_enum_int_mismatch(op_t, int, tnode_t *, tnode_t *);
60 static tnode_t *new_tnode(op_t, type_t *, tnode_t *, tnode_t *);
61 static void balance(op_t, tnode_t **, tnode_t **);
62 static void warn_incompatible_types(op_t, tspec_t, tspec_t);
63 static void warn_incompatible_pointers(mod_t *, type_t *, type_t *);
64 static void merge_qualifiers(type_t **, type_t *, type_t *);
65 static int has_constant_member(type_t *);
66 static void check_prototype_conversion(int, tspec_t, tspec_t, type_t *,
67 tnode_t *);
68 static void check_integer_conversion(op_t, int, tspec_t, tspec_t, type_t *,
69 tnode_t *);
70 static void check_pointer_integer_conversion(op_t, tspec_t, type_t *,
71 tnode_t *);
72 static void check_pointer_conversion(op_t, tnode_t *, type_t *);
73 static tnode_t *build_struct_access(op_t, tnode_t *, tnode_t *);
74 static tnode_t *build_prepost_incdec(op_t, tnode_t *);
75 static tnode_t *build_real_imag(op_t, tnode_t *);
76 static tnode_t *build_ampersand(tnode_t *, int);
77 static tnode_t *build_plus_minus(op_t, tnode_t *, tnode_t *);
78 static tnode_t *build_bit_shift(op_t, tnode_t *, tnode_t *);
79 static tnode_t *build_colon(tnode_t *, tnode_t *);
80 static tnode_t *build_assignment(op_t, tnode_t *, tnode_t *);
81 static tnode_t *plength(type_t *);
82 static tnode_t *fold(tnode_t *);
83 static tnode_t *fold_test(tnode_t *);
84 static tnode_t *fold_float(tnode_t *);
85 static tnode_t *check_function_arguments(type_t *, tnode_t *);
86 static tnode_t *check_prototype_argument(int, type_t *, tnode_t *);
87 static void check_null_effect(tnode_t *);
88 static void display_expression(tnode_t *, int);
89 static void check_array_index(tnode_t *, int);
90 static void check_integer_comparison(op_t, tnode_t *, tnode_t *);
91 static void check_precedence_confusion(tnode_t *);
92
93 extern sig_atomic_t fpe;
94
95 #if 0
96 static char *
97 dumpnode(char *buf, size_t len, tnode_t *tn) {
98 const char *n = getopname(tn->tn_op);
99 const char *s;
100 char tbuf[256];
101
102 switch (tn->tn_op) {
103 case NAME:
104 s = tn->tn_sym->s_name;
105 break;
106 case CON:
107 case STRING:
108 s = "*"; /* todo */
109 break;
110 default:
111 s = NULL;
112 break;
113 }
114 char lb[1024];
115 char rb[1024];
116
117 if (s == NULL && tn->tn_left != NULL)
118 dumpnode(lb, sizeof(lb), tn->tn_left);
119 else
120 strcpy(lb, "(null)");
121
122 if (s == NULL && tn->tn_right != NULL)
123 dumpnode(rb, sizeof(rb), tn->tn_right);
124 else
125 strcpy(rb, "(null)");
126
127
128 snprintf(buf, len, "%s: (%s) = %s [%s, %s]", n,
129 tyname(tbuf, sizeof(tbuf), tn->tn_type), s, lb, rb);
130 return buf;
131 }
132 #endif
133
134 /*
135 * Increase degree of reference.
136 * This is most often used to change type "T" in type "pointer to T".
137 */
138 type_t *
139 incref(type_t *tp, tspec_t t)
140 {
141 type_t *tp2;
142
143 tp2 = getblk(sizeof (type_t));
144 tp2->t_tspec = t;
145 tp2->t_subt = tp;
146 return tp2;
147 }
148
149 /*
150 * same for use in expressions
151 */
152 type_t *
153 tincref(type_t *tp, tspec_t t)
154 {
155 type_t *tp2;
156
157 tp2 = tgetblk(sizeof (type_t));
158 tp2->t_tspec = t;
159 tp2->t_subt = tp;
160 return tp2;
161 }
162
163 /*
164 * Create a node for a constant.
165 */
166 tnode_t *
167 getcnode(type_t *tp, val_t *v)
168 {
169 tnode_t *n;
170
171 n = getnode();
172 n->tn_op = CON;
173 n->tn_type = tp;
174 n->tn_val = tgetblk(sizeof (val_t));
175 n->tn_val->v_tspec = tp->t_tspec;
176 n->tn_val->v_ansiu = v->v_ansiu;
177 n->tn_val->v_u = v->v_u;
178 free(v);
179 return n;
180 }
181
182 /*
183 * Create a node for a integer constant.
184 */
185 static tnode_t *
186 new_int_const_node(tspec_t t, int64_t q)
187 {
188 tnode_t *n;
189
190 n = getnode();
191 n->tn_op = CON;
192 n->tn_type = gettyp(t);
193 n->tn_val = tgetblk(sizeof (val_t));
194 n->tn_val->v_tspec = t;
195 n->tn_val->v_quad = q;
196 return n;
197 }
198
199 /*
200 * Create a node for a name (symbol table entry).
201 * ntok is the token which follows the name.
202 */
203 tnode_t *
204 getnnode(sym_t *sym, int ntok)
205 {
206 tnode_t *n;
207
208 if (sym->s_scl == NOSCL) {
209 sym->s_scl = EXTERN;
210 sym->s_def = DECL;
211 if (ntok == T_LPARN) {
212 if (sflag) {
213 /* function implicitly declared to ... */
214 warning(215);
215 }
216 /*
217 * XXX if tflag is set the symbol should be
218 * exported to level 0
219 */
220 sym->s_type = incref(sym->s_type, FUNC);
221 } else {
222 if (!blklev) {
223 /* %s undefined */
224 error(99, sym->s_name);
225 } else {
226 int fixtype;
227 if (strcmp(sym->s_name, "__FUNCTION__") == 0 ||
228 strcmp(sym->s_name, "__PRETTY_FUNCTION__")
229 == 0) {
230 gnuism(316);
231 fixtype = 1;
232 } else if (strcmp(sym->s_name, "__func__") == 0) {
233 if (!Sflag)
234 warning(317);
235 fixtype = 1;
236 } else {
237 error(99, sym->s_name);
238 fixtype = 0;
239 }
240 if (fixtype) {
241 sym->s_type = incref(gettyp(CHAR), PTR);
242 sym->s_type->t_const = 1;
243 }
244 }
245 }
246 }
247
248 if (sym->s_kind != FVFT && sym->s_kind != FMEMBER)
249 LERROR("getnnode(%d)", sym->s_kind);
250
251 n = getnode();
252 n->tn_type = sym->s_type;
253 if (sym->s_scl != ENUMCON) {
254 n->tn_op = NAME;
255 n->tn_sym = sym;
256 if (sym->s_kind == FVFT && sym->s_type->t_tspec != FUNC)
257 n->tn_lvalue = 1;
258 } else {
259 n->tn_op = CON;
260 n->tn_val = tgetblk(sizeof (val_t));
261 *n->tn_val = sym->s_value;
262 }
263
264 return n;
265 }
266
267 /*
268 * Create a node for a string.
269 */
270 tnode_t *
271 getsnode(strg_t *strg)
272 {
273 size_t len;
274 tnode_t *n;
275
276 len = strg->st_len;
277
278 n = getnode();
279
280 n->tn_op = STRING;
281 n->tn_type = tincref(gettyp(strg->st_tspec), ARRAY);
282 n->tn_type->t_dim = len + 1;
283 n->tn_lvalue = 1;
284
285 n->tn_string = tgetblk(sizeof (strg_t));
286 n->tn_string->st_tspec = strg->st_tspec;
287 n->tn_string->st_len = len;
288
289 if (strg->st_tspec == CHAR) {
290 n->tn_string->st_cp = tgetblk(len + 1);
291 (void)memcpy(n->tn_string->st_cp, strg->st_cp, len + 1);
292 free(strg->st_cp);
293 } else {
294 n->tn_string->st_wcp = tgetblk((len + 1) * sizeof (wchar_t));
295 (void)memcpy(n->tn_string->st_wcp, strg->st_wcp,
296 (len + 1) * sizeof (wchar_t));
297 free(strg->st_wcp);
298 }
299 free(strg);
300
301 return n;
302 }
303
304 /*
305 * Returns a symbol which has the same name as the msym argument and is a
306 * member of the struct or union specified by the tn argument.
307 */
308 sym_t *
309 struct_or_union_member(tnode_t *tn, op_t op, sym_t *msym)
310 {
311 str_t *str;
312 type_t *tp;
313 sym_t *sym, *csym;
314 int eq;
315 tspec_t t;
316
317 /*
318 * Remove the member if it was unknown until now (Which means
319 * that no defined struct or union has a member with the same name).
320 */
321 if (msym->s_scl == NOSCL) {
322 /* undefined struct/union member: %s */
323 error(101, msym->s_name);
324 rmsym(msym);
325 msym->s_kind = FMEMBER;
326 msym->s_scl = MOS;
327 msym->s_styp = tgetblk(sizeof (str_t));
328 msym->s_styp->stag = tgetblk(sizeof (sym_t));
329 msym->s_styp->stag->s_name = unnamed;
330 msym->s_value.v_tspec = INT;
331 return msym;
332 }
333
334 /* Set str to the tag of which msym is expected to be a member. */
335 str = NULL;
336 t = (tp = tn->tn_type)->t_tspec;
337 if (op == POINT) {
338 if (t == STRUCT || t == UNION)
339 str = tp->t_str;
340 } else if (op == ARROW && t == PTR) {
341 t = (tp = tp->t_subt)->t_tspec;
342 if (t == STRUCT || t == UNION)
343 str = tp->t_str;
344 }
345
346 /*
347 * If this struct/union has a member with the name of msym, return
348 * return this it.
349 */
350 if (str != NULL) {
351 for (sym = msym; sym != NULL; sym = sym->s_link) {
352 if (sym->s_scl != MOS && sym->s_scl != MOU)
353 continue;
354 if (sym->s_styp != str)
355 continue;
356 if (strcmp(sym->s_name, msym->s_name) != 0)
357 continue;
358 return sym;
359 }
360 }
361
362 /*
363 * Set eq to 0 if there are struct/union members with the same name
364 * and different types and/or offsets.
365 */
366 eq = 1;
367 for (csym = msym; csym != NULL; csym = csym->s_link) {
368 if (csym->s_scl != MOS && csym->s_scl != MOU)
369 continue;
370 if (strcmp(msym->s_name, csym->s_name) != 0)
371 continue;
372 for (sym = csym->s_link ; sym != NULL; sym = sym->s_link) {
373 int w;
374
375 if (sym->s_scl != MOS && sym->s_scl != MOU)
376 continue;
377 if (strcmp(csym->s_name, sym->s_name) != 0)
378 continue;
379 if (csym->s_value.v_quad != sym->s_value.v_quad) {
380 eq = 0;
381 break;
382 }
383 w = 0;
384 eq = eqtype(csym->s_type, sym->s_type, 0, 0, &w) && !w;
385 if (!eq)
386 break;
387 if (csym->s_bitfield != sym->s_bitfield) {
388 eq = 0;
389 break;
390 }
391 if (csym->s_bitfield) {
392 type_t *tp1, *tp2;
393
394 tp1 = csym->s_type;
395 tp2 = sym->s_type;
396 if (tp1->t_flen != tp2->t_flen) {
397 eq = 0;
398 break;
399 }
400 if (tp1->t_foffs != tp2->t_foffs) {
401 eq = 0;
402 break;
403 }
404 }
405 }
406 if (!eq)
407 break;
408 }
409
410 /*
411 * Now handle the case in which the left operand refers really
412 * to a struct/union, but the right operand is not member of it.
413 */
414 if (str != NULL) {
415 /* illegal member use: %s */
416 if (eq && tflag) {
417 warning(102, msym->s_name);
418 } else {
419 error(102, msym->s_name);
420 }
421 return msym;
422 }
423
424 /*
425 * Now the left operand of ARROW does not point to a struct/union
426 * or the left operand of POINT is no struct/union.
427 */
428 if (eq) {
429 if (op == POINT) {
430 /* left operand of "." must be struct/union object */
431 if (tflag) {
432 warning(103);
433 } else {
434 error(103);
435 }
436 } else {
437 char buf[64];
438 /* left operand of "->" must be pointer to ... */
439 if (tflag && tn->tn_type->t_tspec == PTR) {
440 tyname(buf, sizeof(buf), tn->tn_type);
441 warning(104, buf);
442 } else {
443 tyname(buf, sizeof(buf), tn->tn_type);
444 error(104, buf);
445 }
446 }
447 } else {
448 if (tflag) {
449 /* non-unique member requires struct/union %s */
450 error(105, op == POINT ? "object" : "pointer");
451 } else {
452 /* unacceptable operand of '%s' */
453 error(111, modtab[op].m_name);
454 }
455 }
456
457 return msym;
458 }
459
460 /*
461 * Create a tree node. Called for most operands except function calls,
462 * sizeof and casts.
463 *
464 * op operator
465 * ln left operand
466 * rn if not NULL, right operand
467 */
468 tnode_t *
469 build(op_t op, tnode_t *ln, tnode_t *rn)
470 {
471 mod_t *mp;
472 tnode_t *ntn;
473 type_t *rtp;
474
475 mp = &modtab[op];
476
477 /* If there was an error in one of the operands, return. */
478 if (ln == NULL || (mp->m_binary && rn == NULL))
479 return NULL;
480
481 /*
482 * Apply class conversions to the left operand, but only if its
483 * value is needed or it is compared with null.
484 */
485 if (mp->m_vctx || mp->m_tctx)
486 ln = cconv(ln);
487 /*
488 * The right operand is almost always in a test or value context,
489 * except if it is a struct or union member.
490 */
491 if (mp->m_binary && op != ARROW && op != POINT)
492 rn = cconv(rn);
493
494 /*
495 * Print some warnings for comparisons of unsigned values with
496 * constants lower than or equal to null. This must be done
497 * before promote() because otherwise unsigned char and unsigned
498 * short would be promoted to int. Also types are tested to be
499 * CHAR, which would also become int.
500 */
501 if (mp->m_comp)
502 check_integer_comparison(op, ln, rn);
503
504 /*
505 * Promote the left operand if it is in a test or value context
506 */
507 if (mp->m_vctx || mp->m_tctx)
508 ln = promote(op, 0, ln);
509 /*
510 * Promote the right operand, but only if it is no struct or
511 * union member, or if it is not to be assigned to the left operand
512 */
513 if (mp->m_binary && op != ARROW && op != POINT &&
514 op != ASSIGN && op != RETURN) {
515 rn = promote(op, 0, rn);
516 }
517
518 /*
519 * If the result of the operation is different for signed or
520 * unsigned operands and one of the operands is signed only in
521 * ANSI C, print a warning.
522 */
523 if (mp->m_tlansiu && ln->tn_op == CON && ln->tn_val->v_ansiu) {
524 /* ANSI C treats constant as unsigned, op %s */
525 warning(218, mp->m_name);
526 ln->tn_val->v_ansiu = 0;
527 }
528 if (mp->m_transiu && rn->tn_op == CON && rn->tn_val->v_ansiu) {
529 /* ANSI C treats constant as unsigned, op %s */
530 warning(218, mp->m_name);
531 rn->tn_val->v_ansiu = 0;
532 }
533
534 /* Make sure both operands are of the same type */
535 if (mp->m_balance || (tflag && (op == SHL || op == SHR)))
536 balance(op, &ln, &rn);
537
538 /*
539 * Check types for compatibility with the operation and mutual
540 * compatibility. Return if there are serious problems.
541 */
542 if (!typeok(op, 0, ln, rn))
543 return NULL;
544
545 /* And now create the node. */
546 switch (op) {
547 case POINT:
548 case ARROW:
549 ntn = build_struct_access(op, ln, rn);
550 break;
551 case INCAFT:
552 case DECAFT:
553 case INCBEF:
554 case DECBEF:
555 ntn = build_prepost_incdec(op, ln);
556 break;
557 case AMPER:
558 ntn = build_ampersand(ln, 0);
559 break;
560 case STAR:
561 ntn = new_tnode(STAR, ln->tn_type->t_subt, ln, NULL);
562 break;
563 case PLUS:
564 case MINUS:
565 ntn = build_plus_minus(op, ln, rn);
566 break;
567 case SHL:
568 case SHR:
569 ntn = build_bit_shift(op, ln, rn);
570 break;
571 case COLON:
572 ntn = build_colon(ln, rn);
573 break;
574 case ASSIGN:
575 case MULASS:
576 case DIVASS:
577 case MODASS:
578 case ADDASS:
579 case SUBASS:
580 case SHLASS:
581 case SHRASS:
582 case ANDASS:
583 case XORASS:
584 case ORASS:
585 case RETURN:
586 ntn = build_assignment(op, ln, rn);
587 break;
588 case COMMA:
589 case QUEST:
590 ntn = new_tnode(op, rn->tn_type, ln, rn);
591 break;
592 case REAL:
593 case IMAG:
594 ntn = build_real_imag(op, ln);
595 break;
596 default:
597 rtp = mp->m_logical ? gettyp(INT) : ln->tn_type;
598 lint_assert(mp->m_binary || rn == NULL);
599 ntn = new_tnode(op, rtp, ln, rn);
600 break;
601 }
602
603 /* Return if an error occurred. */
604 if (ntn == NULL)
605 return NULL;
606
607 /* Print a warning if precedence confusion is possible */
608 if (mp->m_tpconf)
609 check_precedence_confusion(ntn);
610
611 /*
612 * Print a warning if one of the operands is in a context where
613 * it is compared with null and if this operand is a constant.
614 */
615 if (mp->m_tctx) {
616 if (ln->tn_op == CON ||
617 ((mp->m_binary && op != QUEST) && rn->tn_op == CON)) {
618 if (hflag && !constcond_flag)
619 /* constant in conditional context */
620 warning(161);
621 }
622 }
623
624 /* Fold if the operator requires it */
625 if (mp->m_fold) {
626 if (ln->tn_op == CON && (!mp->m_binary || rn->tn_op == CON)) {
627 if (mp->m_tctx) {
628 ntn = fold_test(ntn);
629 } else if (tspec_is_float(ntn->tn_type->t_tspec)) {
630 ntn = fold_float(ntn);
631 } else {
632 ntn = fold(ntn);
633 }
634 } else if (op == QUEST && ln->tn_op == CON) {
635 ntn = ln->tn_val->v_quad ? rn->tn_left : rn->tn_right;
636 }
637 }
638
639 return ntn;
640 }
641
642 /*
643 * Perform class conversions.
644 *
645 * Arrays of type T are converted into pointers to type T.
646 * Functions are converted to pointers to functions.
647 * Lvalues are converted to rvalues.
648 */
649 tnode_t *
650 cconv(tnode_t *tn)
651 {
652 type_t *tp;
653
654 /*
655 * Array-lvalue (array of type T) is converted into rvalue
656 * (pointer to type T)
657 */
658 if (tn->tn_type->t_tspec == ARRAY) {
659 if (!tn->tn_lvalue) {
660 /* %soperand of '%s' must be lvalue */
661 /* XXX print correct operator */
662 (void)gnuism(114, "", modtab[AMPER].m_name);
663 }
664 tn = new_tnode(AMPER, tincref(tn->tn_type->t_subt, PTR),
665 tn, NULL);
666 }
667
668 /*
669 * Expression of type function (function with return value of type T)
670 * in rvalue-expression (pointer to function with return value
671 * of type T)
672 */
673 if (tn->tn_type->t_tspec == FUNC)
674 tn = build_ampersand(tn, 1);
675
676 /* lvalue to rvalue */
677 if (tn->tn_lvalue) {
678 tp = tduptyp(tn->tn_type);
679 tp->t_const = tp->t_volatile = 0;
680 tn = new_tnode(LOAD, tp, tn, NULL);
681 }
682
683 return tn;
684 }
685
686 /*
687 * Perform most type checks. First the types are checked using
688 * the information from modtab[]. After that it is done by hand for
689 * more complicated operators and type combinations.
690 *
691 * If the types are ok, typeok() returns 1, otherwise 0.
692 */
693 int
694 typeok(op_t op, int arg, tnode_t *ln, tnode_t *rn)
695 {
696 mod_t *mp;
697 tspec_t lt, rt = NOTSPEC, lst = NOTSPEC, rst = NOTSPEC, olt = NOTSPEC,
698 ort = NOTSPEC;
699 type_t *ltp, *rtp = NULL, *lstp = NULL, *rstp = NULL;
700 char lbuf[128], rbuf[128];
701 tnode_t *tn;
702
703 mp = &modtab[op];
704
705 lint_assert((ltp = ln->tn_type) != NULL);
706
707 if ((lt = ltp->t_tspec) == PTR)
708 lst = (lstp = ltp->t_subt)->t_tspec;
709 if (mp->m_binary) {
710 lint_assert((rtp = rn->tn_type) != NULL);
711 if ((rt = rtp->t_tspec) == PTR)
712 rst = (rstp = rtp->t_subt)->t_tspec;
713 }
714
715 if (mp->m_requires_integer) {
716 if (!tspec_is_int(lt) || (mp->m_binary && !tspec_is_int(rt))) {
717 warn_incompatible_types(op, lt, rt);
718 return 0;
719 }
720 } else if (mp->m_requires_integer_or_complex) {
721 if ((!tspec_is_int(lt) && !tspec_is_complex(lt)) ||
722 (mp->m_binary &&
723 (!tspec_is_int(rt) && !tspec_is_complex(rt)))) {
724 warn_incompatible_types(op, lt, rt);
725 return 0;
726 }
727 } else if (mp->m_requires_scalar) {
728 if (!tspec_is_scalar(lt) ||
729 (mp->m_binary && !tspec_is_scalar(rt))) {
730 warn_incompatible_types(op, lt, rt);
731 return 0;
732 }
733 } else if (mp->m_requires_arith) {
734 if (!tspec_is_arith(lt) ||
735 (mp->m_binary && !tspec_is_arith(rt))) {
736 warn_incompatible_types(op, lt, rt);
737 return 0;
738 }
739 }
740
741 if (op == SHL || op == SHR || op == SHLASS || op == SHRASS) {
742 /*
743 * For these operations we need the types before promotion
744 * and balancing.
745 */
746 for (tn=ln; tn->tn_op==CVT && !tn->tn_cast; tn=tn->tn_left)
747 continue;
748 olt = tn->tn_type->t_tspec;
749 for (tn=rn; tn->tn_op==CVT && !tn->tn_cast; tn=tn->tn_left)
750 continue;
751 ort = tn->tn_type->t_tspec;
752 }
753
754 switch (op) {
755 case POINT:
756 /*
757 * Most errors required by ANSI C are reported in
758 * struct_or_union_member().
759 * Here we only must check for totally wrong things.
760 */
761 if (lt == FUNC || lt == VOID || ltp->t_isfield ||
762 ((lt != STRUCT && lt != UNION) && !ln->tn_lvalue)) {
763 /* Without tflag we got already an error */
764 if (tflag)
765 /* unacceptable operand of '%s' */
766 error(111, mp->m_name);
767 return 0;
768 }
769 /* Now we have an object we can create a pointer to */
770 break;
771 case ARROW:
772 if (lt != PTR && !(tflag && tspec_is_int(lt))) {
773 /* Without tflag we got already an error */
774 if (tflag)
775 /* unacceptable operand of '%s' */
776 error(111, mp->m_name);
777 return 0;
778 }
779 break;
780 case INCAFT:
781 case DECAFT:
782 case INCBEF:
783 case DECBEF:
784 /* operands have scalar types (checked above) */
785 if (!ln->tn_lvalue) {
786 if (ln->tn_op == CVT && ln->tn_cast &&
787 ln->tn_left->tn_op == LOAD) {
788 /* a cast to non-ptr does not yield an lvalue */
789 if (ln->tn_type->t_tspec == PTR)
790 break;
791 error(163);
792 }
793 /* %soperand of '%s' must be lvalue */
794 error(114, "", mp->m_name);
795 return 0;
796 } else if (ltp->t_const) {
797 /* %soperand of '%s' must be modifiable lvalue */
798 if (!tflag)
799 warning(115, "", mp->m_name);
800 }
801 break;
802 case AMPER:
803 if (lt == ARRAY || lt == FUNC) {
804 /* ok, a warning comes later (in build_ampersand()) */
805 } else if (!ln->tn_lvalue) {
806 if (ln->tn_op == CVT && ln->tn_cast &&
807 ln->tn_left->tn_op == LOAD) {
808 /* a cast to non-ptr does not yield an lvalue */
809 if (ln->tn_type->t_tspec == PTR)
810 break;
811 error(163);
812 }
813 /* %soperand of '%s' must be lvalue */
814 error(114, "", mp->m_name);
815 return 0;
816 } else if (tspec_is_scalar(lt)) {
817 if (ltp->t_isfield) {
818 /* cannot take address of bit-field */
819 error(112);
820 return 0;
821 }
822 } else if (lt != STRUCT && lt != UNION) {
823 /* unacceptable operand of '%s' */
824 error(111, mp->m_name);
825 return 0;
826 }
827 if (ln->tn_op == NAME && ln->tn_sym->s_reg) {
828 /* cannot take address of register %s */
829 error(113, ln->tn_sym->s_name);
830 return 0;
831 }
832 break;
833 case STAR:
834 /* until now there were no type checks for this operator */
835 if (lt != PTR) {
836 /* cannot dereference non-pointer type */
837 error(96);
838 return 0;
839 }
840 break;
841 case PLUS:
842 /* operands have scalar types (checked above) */
843 if ((lt == PTR && !tspec_is_int(rt)) ||
844 (rt == PTR && !tspec_is_int(lt))) {
845 warn_incompatible_types(op, lt, rt);
846 return 0;
847 }
848 break;
849 case MINUS:
850 /* operands have scalar types (checked above) */
851 if (lt == PTR && (!tspec_is_int(rt) && rt != PTR)) {
852 warn_incompatible_types(op, lt, rt);
853 return 0;
854 } else if (rt == PTR && lt != PTR) {
855 warn_incompatible_types(op, lt, rt);
856 return 0;
857 }
858 if (lt == PTR && rt == PTR) {
859 if (!eqtype(lstp, rstp, 1, 0, NULL)) {
860 /* illegal pointer subtraction */
861 error(116);
862 }
863 }
864 break;
865 case SHR:
866 /* operands have integer types (checked above) */
867 if (pflag && !tspec_is_uint(lt)) {
868 /*
869 * The left operand is signed. This means that
870 * the operation is (possibly) nonportable.
871 */
872 if (ln->tn_op != CON) {
873 /* bitop. on signed value poss. nonportable */
874 warning(117);
875 } else if (ln->tn_val->v_quad < 0) {
876 /* bitop. on signed value nonportable */
877 warning(120);
878 }
879 } else if (!tflag && !sflag &&
880 !tspec_is_uint(olt) && tspec_is_uint(ort)) {
881 /*
882 * The left operand would become unsigned in
883 * traditional C.
884 */
885 if (hflag &&
886 (ln->tn_op != CON || ln->tn_val->v_quad < 0)) {
887 /* semantics of '%s' change in ANSI C; ... */
888 warning(118, mp->m_name);
889 }
890 } else if (!tflag && !sflag &&
891 !tspec_is_uint(olt) && !tspec_is_uint(ort) &&
892 psize(lt) < psize(rt)) {
893 /*
894 * In traditional C the left operand would be extended,
895 * possibly with 1, and then shifted.
896 */
897 if (hflag &&
898 (ln->tn_op != CON || ln->tn_val->v_quad < 0)) {
899 /* semantics of '%s' change in ANSI C; ... */
900 warning(118, mp->m_name);
901 }
902 }
903 goto shift;
904 case SHL:
905 /*
906 * ANSI C does not perform balancing for shift operations,
907 * but traditional C does. If the width of the right operand
908 * is greater than the width of the left operand, than in
909 * traditional C the left operand would be extended to the
910 * width of the right operand. For SHL this may result in
911 * different results.
912 */
913 if (psize(lt) < psize(rt)) {
914 /*
915 * XXX If both operands are constant, make sure
916 * that there is really a difference between
917 * ANSI C and traditional C.
918 */
919 if (hflag)
920 /* semantics of '%s' change in ANSI C; ... */
921 warning(118, mp->m_name);
922 }
923 shift:
924 if (rn->tn_op == CON) {
925 if (!tspec_is_uint(rt) && rn->tn_val->v_quad < 0) {
926 /* negative shift */
927 warning(121);
928 } else if ((uint64_t)rn->tn_val->v_quad == (uint64_t)size(lt)) {
929 /* shift equal to size of object */
930 warning(267);
931 } else if ((uint64_t)rn->tn_val->v_quad > (uint64_t)size(lt)) {
932 /* shift greater than size of object */
933 warning(122);
934 }
935 }
936 break;
937 case EQ:
938 case NE:
939 /*
940 * Accept some things which are allowed with EQ and NE,
941 * but not with ordered comparisons.
942 */
943 if (lt == PTR && ((rt == PTR && rst == VOID) ||
944 tspec_is_int(rt))) {
945 if (rn->tn_op == CON && rn->tn_val->v_quad == 0)
946 break;
947 }
948 if (rt == PTR && ((lt == PTR && lst == VOID) ||
949 tspec_is_int(lt))) {
950 if (ln->tn_op == CON && ln->tn_val->v_quad == 0)
951 break;
952 }
953 /* FALLTHROUGH */
954 case LT:
955 case GT:
956 case LE:
957 case GE:
958 if ((lt == PTR || rt == PTR) && lt != rt) {
959 if (tspec_is_int(lt) || tspec_is_int(rt)) {
960 const char *lx = lt == PTR ?
961 "pointer" : "integer";
962 const char *rx = rt == PTR ?
963 "pointer" : "integer";
964 tyname(lbuf, sizeof(lbuf), ltp);
965 tyname(rbuf, sizeof(rbuf), rtp);
966 /* illegal combination of %s (%s) and ... */
967 warning(123, lx, lbuf, rx, rbuf, mp->m_name);
968 } else {
969 warn_incompatible_types(op, lt, rt);
970 return 0;
971 }
972 } else if (lt == PTR && rt == PTR) {
973 check_pointer_comparison(op, ln, rn);
974 }
975 break;
976 case QUEST:
977 if (!tspec_is_scalar(lt)) {
978 /* first operand must have scalar type, op ? : */
979 error(170);
980 return 0;
981 }
982 while (rn->tn_op == CVT)
983 rn = rn->tn_left;
984 lint_assert(rn->tn_op == COLON);
985 break;
986 case COLON:
987 if (tspec_is_arith(lt) && tspec_is_arith(rt))
988 break;
989
990 if (lt == STRUCT && rt == STRUCT && ltp->t_str == rtp->t_str)
991 break;
992 if (lt == UNION && rt == UNION && ltp->t_str == rtp->t_str)
993 break;
994
995 /* combination of any pointer and 0, 0L or (void *)0 is ok */
996 if (lt == PTR && ((rt == PTR && rst == VOID) ||
997 tspec_is_int(rt))) {
998 if (rn->tn_op == CON && rn->tn_val->v_quad == 0)
999 break;
1000 }
1001 if (rt == PTR && ((lt == PTR && lst == VOID) ||
1002 tspec_is_int(lt))) {
1003 if (ln->tn_op == CON && ln->tn_val->v_quad == 0)
1004 break;
1005 }
1006
1007 if ((lt == PTR && tspec_is_int(rt)) ||
1008 (tspec_is_int(lt) && rt == PTR)) {
1009 const char *lx = lt == PTR ? "pointer" : "integer";
1010 const char *rx = rt == PTR ? "pointer" : "integer";
1011 tyname(lbuf, sizeof(lbuf), ltp);
1012 tyname(rbuf, sizeof(rbuf), rtp);
1013 /* illegal combination of %s (%s) and %s (%s), op %s */
1014 warning(123, lx, lbuf, rx, rbuf, mp->m_name);
1015 break;
1016 }
1017
1018 if (lt == VOID || rt == VOID) {
1019 if (lt != VOID || rt != VOID)
1020 /* incompatible types in conditional */
1021 warning(126);
1022 break;
1023 }
1024
1025 if (lt == PTR && rt == PTR && ((lst == VOID && rst == FUNC) ||
1026 (lst == FUNC && rst == VOID))) {
1027 /* (void *)0 handled above */
1028 if (sflag)
1029 /* ANSI C forbids conv. of %s to %s, op %s */
1030 warning(305, "function pointer", "'void *'",
1031 mp->m_name);
1032 break;
1033 }
1034
1035 if (rt == PTR && lt == PTR) {
1036 if (eqptrtype(lstp, rstp, 1))
1037 break;
1038 if (!eqtype(lstp, rstp, 1, 0, NULL))
1039 warn_incompatible_pointers(mp, ltp, rtp);
1040 break;
1041 }
1042
1043 /* incompatible types in conditional */
1044 error(126);
1045 return 0;
1046
1047 case ASSIGN:
1048 case INIT:
1049 case FARG:
1050 case RETURN:
1051 if (!check_assign_types_compatible(op, arg, ln, rn))
1052 return 0;
1053 goto assign;
1054 case MULASS:
1055 case DIVASS:
1056 case MODASS:
1057 goto assign;
1058 case ADDASS:
1059 case SUBASS:
1060 /* operands have scalar types (checked above) */
1061 if ((lt == PTR && !tspec_is_int(rt)) || rt == PTR) {
1062 warn_incompatible_types(op, lt, rt);
1063 return 0;
1064 }
1065 goto assign;
1066 case SHLASS:
1067 goto assign;
1068 case SHRASS:
1069 if (pflag && !tspec_is_uint(lt) &&
1070 !(tflag && tspec_is_uint(rt))) {
1071 /* bitop. on signed value possibly nonportable */
1072 warning(117);
1073 }
1074 goto assign;
1075 case ANDASS:
1076 case XORASS:
1077 case ORASS:
1078 goto assign;
1079 assign:
1080 if (!ln->tn_lvalue) {
1081 if (ln->tn_op == CVT && ln->tn_cast &&
1082 ln->tn_left->tn_op == LOAD) {
1083 /* a cast to non-ptr does not yield an lvalue */
1084 if (ln->tn_type->t_tspec == PTR)
1085 break;
1086 error(163);
1087 }
1088 /* %soperand of '%s' must be lvalue */
1089 error(114, "left ", mp->m_name);
1090 return 0;
1091 } else if (ltp->t_const || ((lt == STRUCT || lt == UNION) &&
1092 has_constant_member(ltp))) {
1093 /* %soperand of %s must be modifiable lvalue */
1094 if (!tflag)
1095 warning(115, "left ", mp->m_name);
1096 }
1097 break;
1098 case COMMA:
1099 if (!modtab[ln->tn_op].m_sideeff)
1100 check_null_effect(ln);
1101 break;
1102 /* LINTED206: (enumeration values not handled in switch) */
1103 case CON:
1104 case CASE:
1105 case PUSH:
1106 case LOAD:
1107 case ICALL:
1108 case CVT:
1109 case CALL:
1110 case FSEL:
1111 case STRING:
1112 case NAME:
1113 case LOGOR:
1114 case LOGAND:
1115 case OR:
1116 case XOR:
1117 case AND:
1118 case MOD:
1119 case DIV:
1120 case MULT:
1121 case UMINUS:
1122 case UPLUS:
1123 case DEC:
1124 case INC:
1125 case COMPL:
1126 case NOT:
1127 case NOOP:
1128 case REAL:
1129 case IMAG:
1130 break;
1131 }
1132
1133 if (mp->m_bad_on_enum &&
1134 (ltp->t_isenum || (mp->m_binary && rtp->t_isenum))) {
1135 check_bad_enum_operation(op, ln, rn);
1136 } else if (mp->m_valid_on_enum &&
1137 (ltp->t_isenum && rtp && rtp->t_isenum)) {
1138 check_enum_type_mismatch(op, arg, ln, rn);
1139 } else if (mp->m_valid_on_enum &&
1140 (ltp->t_isenum || (rtp && rtp->t_isenum))) {
1141 check_enum_int_mismatch(op, arg, ln, rn);
1142 }
1143
1144 return 1;
1145 }
1146
1147 static void
1148 check_pointer_comparison(op_t op, tnode_t *ln, tnode_t *rn)
1149 {
1150 type_t *ltp, *rtp;
1151 tspec_t lt, rt;
1152 const char *lts, *rts;
1153
1154 lt = (ltp = ln->tn_type)->t_subt->t_tspec;
1155 rt = (rtp = rn->tn_type)->t_subt->t_tspec;
1156
1157 if (lt == VOID || rt == VOID) {
1158 if (sflag && (lt == FUNC || rt == FUNC)) {
1159 /* (void *)0 already handled in typeok() */
1160 *(lt == FUNC ? <s : &rts) = "function pointer";
1161 *(lt == VOID ? <s : &rts) = "'void *'";
1162 /* ANSI C forbids comparison of %s with %s */
1163 warning(274, lts, rts);
1164 }
1165 return;
1166 }
1167
1168 if (!eqtype(ltp->t_subt, rtp->t_subt, 1, 0, NULL)) {
1169 warn_incompatible_pointers(&modtab[op], ltp, rtp);
1170 return;
1171 }
1172
1173 if (lt == FUNC && rt == FUNC) {
1174 if (sflag && op != EQ && op != NE)
1175 /* ANSI C forbids ordered comparisons of ... */
1176 warning(125);
1177 }
1178 }
1179
1180 /*
1181 * Checks type compatibility for ASSIGN, INIT, FARG and RETURN
1182 * and prints warnings/errors if necessary.
1183 * If the types are (almost) compatible, 1 is returned, otherwise 0.
1184 */
1185 static int
1186 check_assign_types_compatible(op_t op, int arg, tnode_t *ln, tnode_t *rn)
1187 {
1188 tspec_t lt, rt, lst = NOTSPEC, rst = NOTSPEC;
1189 type_t *ltp, *rtp, *lstp = NULL, *rstp = NULL;
1190 mod_t *mp;
1191 const char *lts, *rts;
1192 char lbuf[128], rbuf[128];
1193
1194 if ((lt = (ltp = ln->tn_type)->t_tspec) == PTR)
1195 lst = (lstp = ltp->t_subt)->t_tspec;
1196 if ((rt = (rtp = rn->tn_type)->t_tspec) == PTR)
1197 rst = (rstp = rtp->t_subt)->t_tspec;
1198 mp = &modtab[op];
1199
1200 if (tspec_is_arith(lt) && tspec_is_arith(rt))
1201 return 1;
1202
1203 if ((lt == STRUCT || lt == UNION) && (rt == STRUCT || rt == UNION))
1204 /* both are struct or union */
1205 return ltp->t_str == rtp->t_str;
1206
1207 /* 0, 0L and (void *)0 may be assigned to any pointer */
1208 if (lt == PTR && ((rt == PTR && rst == VOID) || tspec_is_int(rt))) {
1209 if (rn->tn_op == CON && rn->tn_val->v_quad == 0)
1210 return 1;
1211 }
1212
1213 if (lt == PTR && rt == PTR && (lst == VOID || rst == VOID)) {
1214 /* two pointers, at least one pointer to void */
1215 if (sflag && (lst == FUNC || rst == FUNC)) {
1216 /* comb. of ptr to func and ptr to void */
1217 *(lst == FUNC ? <s : &rts) = "function pointer";
1218 *(lst == VOID ? <s : &rts) = "'void *'";
1219 switch (op) {
1220 case INIT:
1221 case RETURN:
1222 /* ANSI C forbids conversion of %s to %s */
1223 warning(303, rts, lts);
1224 break;
1225 case FARG:
1226 /* ANSI C forbids conv. of %s to %s, arg #%d */
1227 warning(304, rts, lts, arg);
1228 break;
1229 default:
1230 /* ANSI C forbids conv. of %s to %s, op %s */
1231 warning(305, rts, lts, mp->m_name);
1232 break;
1233 }
1234 }
1235 }
1236
1237 if (lt == PTR && rt == PTR && (lst == VOID || rst == VOID ||
1238 eqtype(lstp, rstp, 1, 0, NULL))) {
1239 /* compatible pointer types (qualifiers ignored) */
1240 if (!tflag &&
1241 ((!lstp->t_const && rstp->t_const) ||
1242 (!lstp->t_volatile && rstp->t_volatile))) {
1243 /* left side has not all qualifiers of right */
1244 tyname(lbuf, sizeof(lbuf), lstp);
1245 tyname(rbuf, sizeof(rbuf), rstp);
1246 switch (op) {
1247 case INIT:
1248 case RETURN:
1249 /* incompatible pointer types (%s != %s) */
1250 warning(182, lbuf, rbuf);
1251 break;
1252 case FARG:
1253 /* argument has incompatible pointer type... */
1254 warning(153, arg, lbuf, rbuf);
1255 break;
1256 default:
1257 /* operands have incompatible pointer type... */
1258 warning(128, mp->m_name, lbuf, rbuf);
1259 break;
1260 }
1261 }
1262 return 1;
1263 }
1264
1265 if ((lt == PTR && tspec_is_int(rt)) ||
1266 (tspec_is_int(lt) && rt == PTR)) {
1267 const char *lx = lt == PTR ? "pointer" : "integer";
1268 const char *rx = rt == PTR ? "pointer" : "integer";
1269 tyname(lbuf, sizeof(lbuf), ltp);
1270 tyname(rbuf, sizeof(rbuf), rtp);
1271
1272 switch (op) {
1273 case INIT:
1274 case RETURN:
1275 /* illegal combination of %s (%s) and %s (%s) */
1276 warning(183, lx, lbuf, rx, rbuf);
1277 break;
1278 case FARG:
1279 /* illegal comb. of %s (%s) and %s (%s), arg #%d */
1280 warning(154, lx, lbuf, rx, rbuf, arg);
1281 break;
1282 default:
1283 /* illegal combination of %s (%s) and %s (%s), op %s */
1284 warning(123, lx, lbuf, rx, rbuf, mp->m_name);
1285 break;
1286 }
1287 return 1;
1288 }
1289
1290 if (lt == PTR && rt == PTR) {
1291 switch (op) {
1292 case INIT:
1293 case RETURN:
1294 warn_incompatible_pointers(NULL, ltp, rtp);
1295 break;
1296 case FARG:
1297 /* arg. has incomp. pointer type, arg #%d (%s != %s) */
1298 warning(153, arg, tyname(lbuf, sizeof(lbuf), ltp),
1299 tyname(rbuf, sizeof(rbuf), rtp));
1300 break;
1301 default:
1302 warn_incompatible_pointers(mp, ltp, rtp);
1303 break;
1304 }
1305 return 1;
1306 }
1307
1308 switch (op) {
1309 case INIT:
1310 /* initialisation type mismatch (%s) and (%s) */
1311 error(185, tyname(lbuf, sizeof(lbuf), ltp),
1312 tyname(rbuf, sizeof(rbuf), rtp));
1313 break;
1314 case RETURN:
1315 /* return value type mismatch (%s) and (%s) */
1316 error(211, tyname(lbuf, sizeof(lbuf), ltp),
1317 tyname(rbuf, sizeof(rbuf), rtp));
1318 break;
1319 case FARG:
1320 /* argument is incompatible with prototype, arg #%d */
1321 warning(155, arg);
1322 break;
1323 default:
1324 warn_incompatible_types(op, lt, rt);
1325 break;
1326 }
1327
1328 return 0;
1329 }
1330
1331 /*
1332 * Prints a warning if an operator, which should be senseless for an
1333 * enum type, is applied to an enum type.
1334 */
1335 static void
1336 check_bad_enum_operation(op_t op, tnode_t *ln, tnode_t *rn)
1337 {
1338 mod_t *mp;
1339
1340 if (!eflag)
1341 return;
1342
1343 mp = &modtab[op];
1344
1345 if (!(ln->tn_type->t_isenum ||
1346 (mp->m_binary && rn->tn_type->t_isenum))) {
1347 return;
1348 }
1349
1350 /*
1351 * Enum as offset to a pointer is an exception (otherwise enums
1352 * could not be used as array indizes).
1353 */
1354 if (op == PLUS &&
1355 ((ln->tn_type->t_isenum && rn->tn_type->t_tspec == PTR) ||
1356 (rn->tn_type->t_isenum && ln->tn_type->t_tspec == PTR))) {
1357 return;
1358 }
1359
1360 /* dubious operation on enum, op %s */
1361 warning(241, mp->m_name);
1362
1363 }
1364
1365 /*
1366 * Prints a warning if an operator is applied to two different enum types.
1367 */
1368 static void
1369 check_enum_type_mismatch(op_t op, int arg, tnode_t *ln, tnode_t *rn)
1370 {
1371 mod_t *mp;
1372
1373 mp = &modtab[op];
1374
1375 if (ln->tn_type->t_enum != rn->tn_type->t_enum) {
1376 switch (op) {
1377 case INIT:
1378 /* enum type mismatch in initialisation */
1379 warning(210);
1380 break;
1381 case FARG:
1382 /* enum type mismatch, arg #%d */
1383 warning(156, arg);
1384 break;
1385 case RETURN:
1386 /* return value type mismatch (%s) and (%s) */
1387 warning(211);
1388 break;
1389 default:
1390 /* enum type mismatch, op %s */
1391 warning(130, mp->m_name);
1392 break;
1393 }
1394 } else if (Pflag && mp->m_comp && op != EQ && op != NE) {
1395 if (eflag)
1396 /* dubious comparison of enums, op %s */
1397 warning(243, mp->m_name);
1398 }
1399 }
1400
1401 /*
1402 * Prints a warning if an operator has both enum and other integer
1403 * types.
1404 */
1405 static void
1406 check_enum_int_mismatch(op_t op, int arg, tnode_t *ln, tnode_t *rn)
1407 {
1408 char lbuf[64], rbuf[64];
1409
1410 if (!eflag)
1411 return;
1412
1413 switch (op) {
1414 case INIT:
1415 /*
1416 * Initializations with 0 should be allowed. Otherwise,
1417 * we should complain about all uninitialized enums,
1418 * consequently.
1419 */
1420 if (!rn->tn_type->t_isenum && rn->tn_op == CON &&
1421 tspec_is_int(rn->tn_type->t_tspec) &&
1422 rn->tn_val->v_quad == 0) {
1423 return;
1424 }
1425 /* initialisation of '%s' with '%s' */
1426 warning(277, tyname(lbuf, sizeof(lbuf), ln->tn_type),
1427 tyname(rbuf, sizeof(rbuf), rn->tn_type));
1428 break;
1429 case FARG:
1430 /* combination of '%s' and '%s', arg #%d */
1431 warning(278, tyname(lbuf, sizeof(lbuf), ln->tn_type),
1432 tyname(rbuf, sizeof(rbuf), rn->tn_type), arg);
1433 break;
1434 case RETURN:
1435 /* combination of '%s' and '%s' in return */
1436 warning(279, tyname(lbuf, sizeof(lbuf), ln->tn_type),
1437 tyname(rbuf, sizeof(rbuf), rn->tn_type));
1438 break;
1439 default:
1440 /* combination of '%s' and '%s', op %s */
1441 warning(242, tyname(lbuf, sizeof(lbuf), ln->tn_type),
1442 tyname(rbuf, sizeof(rbuf), rn->tn_type),
1443 modtab[op].m_name);
1444 break;
1445 }
1446 }
1447
1448 /*
1449 * Build and initialize a new node.
1450 */
1451 static tnode_t *
1452 new_tnode(op_t op, type_t *type, tnode_t *ln, tnode_t *rn)
1453 {
1454 tnode_t *ntn;
1455 tspec_t t;
1456 #ifdef notyet
1457 size_t l;
1458 uint64_t rnum;
1459 #endif
1460
1461 ntn = getnode();
1462
1463 ntn->tn_op = op;
1464 ntn->tn_type = type;
1465 ntn->tn_left = ln;
1466 ntn->tn_right = rn;
1467
1468 switch (op) {
1469 #ifdef notyet
1470 case SHR:
1471 if (rn->tn_op != CON)
1472 break;
1473 rnum = rn->tn_val->v_quad;
1474 l = tsize(ln->tn_type) / CHAR_BIT;
1475 t = ln->tn_type->t_tspec;
1476 switch (l) {
1477 case 8:
1478 if (rnum >= 56)
1479 t = UCHAR;
1480 else if (rnum >= 48)
1481 t = USHORT;
1482 else if (rnum >= 32)
1483 t = UINT;
1484 break;
1485 case 4:
1486 if (rnum >= 24)
1487 t = UCHAR;
1488 else if (rnum >= 16)
1489 t = USHORT;
1490 break;
1491 case 2:
1492 if (rnum >= 8)
1493 t = UCHAR;
1494 break;
1495 default:
1496 break;
1497 }
1498 if (t != ln->tn_type->t_tspec)
1499 ntn->tn_type->t_tspec = t;
1500 break;
1501 #endif
1502 case STAR:
1503 case FSEL:
1504 lint_assert(ln->tn_type->t_tspec == PTR);
1505 t = ln->tn_type->t_subt->t_tspec;
1506 if (t != FUNC && t != VOID)
1507 ntn->tn_lvalue = 1;
1508 break;
1509 default:
1510 break;
1511 }
1512
1513 return ntn;
1514 }
1515
1516 /*
1517 * Performs usual conversion of operands to (unsigned) int.
1518 *
1519 * If tflag is set or the operand is a function argument with no
1520 * type information (no prototype or variable # of args), convert
1521 * float to double.
1522 */
1523 tnode_t *
1524 promote(op_t op, int farg, tnode_t *tn)
1525 {
1526 tspec_t t;
1527 type_t *ntp;
1528 u_int len;
1529
1530 t = tn->tn_type->t_tspec;
1531
1532 if (!tspec_is_arith(t))
1533 return tn;
1534
1535 if (!tflag) {
1536 /*
1537 * ANSI C requires that the result is always of type INT
1538 * if INT can represent all possible values of the previous
1539 * type.
1540 */
1541 if (tn->tn_type->t_isfield) {
1542 len = tn->tn_type->t_flen;
1543 if (size(INT) > len) {
1544 t = INT;
1545 } else {
1546 lint_assert(len == size(INT));
1547 if (tspec_is_uint(t)) {
1548 t = UINT;
1549 } else {
1550 t = INT;
1551 }
1552 }
1553 } else if (t == CHAR || t == UCHAR || t == SCHAR) {
1554 t = (size(CHAR) < size(INT) || t != UCHAR) ?
1555 INT : UINT;
1556 } else if (t == SHORT || t == USHORT) {
1557 t = (size(SHORT) < size(INT) || t == SHORT) ?
1558 INT : UINT;
1559 } else if (t == ENUM) {
1560 t = INT;
1561 } else if (farg && t == FLOAT) {
1562 t = DOUBLE;
1563 }
1564 } else {
1565 /*
1566 * In traditional C, keep unsigned and promote FLOAT
1567 * to DOUBLE.
1568 */
1569 if (t == UCHAR || t == USHORT) {
1570 t = UINT;
1571 } else if (t == CHAR || t == SCHAR || t == SHORT) {
1572 t = INT;
1573 } else if (t == FLOAT) {
1574 t = DOUBLE;
1575 } else if (t == ENUM) {
1576 t = INT;
1577 }
1578 }
1579
1580 if (t != tn->tn_type->t_tspec) {
1581 ntp = tduptyp(tn->tn_type);
1582 ntp->t_tspec = t;
1583 /*
1584 * Keep t_isenum so we are later able to check compatibility
1585 * of enum types.
1586 */
1587 tn = convert(op, 0, ntp, tn);
1588 }
1589
1590 return tn;
1591 }
1592
1593 /*
1594 * Insert conversions which are necessary to give both operands the same
1595 * type. This is done in different ways for traditional C and ANIS C.
1596 */
1597 static void
1598 balance(op_t op, tnode_t **lnp, tnode_t **rnp)
1599 {
1600 tspec_t lt, rt, t;
1601 int i, u;
1602 type_t *ntp;
1603 static tspec_t tl[] = {
1604 LDOUBLE, DOUBLE, FLOAT, UQUAD, QUAD, ULONG, LONG, UINT, INT,
1605 };
1606
1607 lt = (*lnp)->tn_type->t_tspec;
1608 rt = (*rnp)->tn_type->t_tspec;
1609
1610 if (!tspec_is_arith(lt) || !tspec_is_arith(rt))
1611 return;
1612
1613 if (!tflag) {
1614 if (lt == rt) {
1615 t = lt;
1616 } else if (lt == LCOMPLEX || rt == LCOMPLEX) {
1617 t = LCOMPLEX;
1618 } else if (lt == DCOMPLEX || rt == DCOMPLEX) {
1619 t = DCOMPLEX;
1620 } else if (lt == COMPLEX || rt == COMPLEX) {
1621 t = COMPLEX;
1622 } else if (lt == FCOMPLEX || rt == FCOMPLEX) {
1623 t = FCOMPLEX;
1624 } else if (lt == LDOUBLE || rt == LDOUBLE) {
1625 t = LDOUBLE;
1626 } else if (lt == DOUBLE || rt == DOUBLE) {
1627 t = DOUBLE;
1628 } else if (lt == FLOAT || rt == FLOAT) {
1629 t = FLOAT;
1630 } else {
1631 /*
1632 * If type A has more bits than type B it should
1633 * be able to hold all possible values of type B.
1634 */
1635 if (size(lt) > size(rt)) {
1636 t = lt;
1637 } else if (size(lt) < size(rt)) {
1638 t = rt;
1639 } else {
1640 for (i = 3; tl[i] != INT; i++) {
1641 if (tl[i] == lt || tl[i] == rt)
1642 break;
1643 }
1644 if ((tspec_is_uint(lt) || tspec_is_uint(rt)) &&
1645 !tspec_is_uint(tl[i])) {
1646 i--;
1647 }
1648 t = tl[i];
1649 }
1650 }
1651 } else {
1652 /* Keep unsigned in traditional C */
1653 u = tspec_is_uint(lt) || tspec_is_uint(rt);
1654 for (i = 0; tl[i] != INT; i++) {
1655 if (lt == tl[i] || rt == tl[i])
1656 break;
1657 }
1658 t = tl[i];
1659 if (u && tspec_is_int(t) && !tspec_is_uint(t))
1660 t = utyp(t);
1661 }
1662
1663 if (t != lt) {
1664 ntp = tduptyp((*lnp)->tn_type);
1665 ntp->t_tspec = t;
1666 *lnp = convert(op, 0, ntp, *lnp);
1667 }
1668 if (t != rt) {
1669 ntp = tduptyp((*rnp)->tn_type);
1670 ntp->t_tspec = t;
1671 *rnp = convert(op, 0, ntp, *rnp);
1672 }
1673 }
1674
1675 /*
1676 * Insert a conversion operator, which converts the type of the node
1677 * to another given type.
1678 * If op is FARG, arg is the number of the argument (used for warnings).
1679 */
1680 tnode_t *
1681 convert(op_t op, int arg, type_t *tp, tnode_t *tn)
1682 {
1683 tnode_t *ntn;
1684 tspec_t nt, ot, ost = NOTSPEC;
1685
1686 nt = tp->t_tspec;
1687 if ((ot = tn->tn_type->t_tspec) == PTR)
1688 ost = tn->tn_type->t_subt->t_tspec;
1689
1690 if (!tflag && !sflag && op == FARG)
1691 check_prototype_conversion(arg, nt, ot, tp, tn);
1692 if (tspec_is_int(nt) && tspec_is_int(ot)) {
1693 check_integer_conversion(op, arg, nt, ot, tp, tn);
1694 } else if (nt == PTR && ((ot == PTR && ost == VOID) ||
1695 tspec_is_int(ot)) && tn->tn_op == CON && tn->tn_val->v_quad == 0) {
1696 /* 0, 0L and (void *)0 may be assigned to any pointer. */
1697 } else if (tspec_is_int(nt) && ot == PTR) {
1698 check_pointer_integer_conversion(op, nt, tp, tn);
1699 } else if (nt == PTR && ot == PTR) {
1700 check_pointer_conversion(op, tn, tp);
1701 }
1702
1703 ntn = getnode();
1704 ntn->tn_op = CVT;
1705 ntn->tn_type = tp;
1706 ntn->tn_cast = op == CVT;
1707 ntn->tn_right = NULL;
1708 if (tn->tn_op != CON || nt == VOID) {
1709 ntn->tn_left = tn;
1710 } else {
1711 ntn->tn_op = CON;
1712 ntn->tn_val = tgetblk(sizeof (val_t));
1713 cvtcon(op, arg, ntn->tn_type, ntn->tn_val, tn->tn_val);
1714 }
1715
1716 return ntn;
1717 }
1718
1719 /*
1720 * Print a warning if a prototype causes a type conversion that is
1721 * different from what would happen to the same argument in the
1722 * absence of a prototype.
1723 *
1724 * Errors/Warnings about illegal type combinations are already printed
1725 * in check_assign_types_compatible().
1726 */
1727 static void
1728 check_prototype_conversion(int arg, tspec_t nt, tspec_t ot, type_t *tp,
1729 tnode_t *tn)
1730 {
1731 tnode_t *ptn;
1732 char buf[64];
1733
1734 if (!tspec_is_arith(nt) || !tspec_is_arith(ot))
1735 return;
1736
1737 /*
1738 * If the type of the formal parameter is char/short, a warning
1739 * would be useless, because functions declared the old style
1740 * can't expect char/short arguments.
1741 */
1742 if (nt == CHAR || nt == UCHAR || nt == SHORT || nt == USHORT)
1743 return;
1744
1745 /* get default promotion */
1746 ptn = promote(NOOP, 1, tn);
1747 ot = ptn->tn_type->t_tspec;
1748
1749 /* return if types are the same with and without prototype */
1750 if (nt == ot || (nt == ENUM && ot == INT))
1751 return;
1752
1753 if (tspec_is_float(nt) != tspec_is_float(ot) ||
1754 psize(nt) != psize(ot)) {
1755 /* representation and/or width change */
1756 if (!tspec_is_int(ot) || psize(ot) > psize(INT)) {
1757 /* conversion to '%s' due to prototype, arg #%d */
1758 warning(259, tyname(buf, sizeof(buf), tp), arg);
1759 }
1760 } else if (hflag) {
1761 /*
1762 * they differ in sign or base type (char, short, int,
1763 * long, long long, float, double, long double)
1764 *
1765 * if they differ only in sign and the argument is a constant
1766 * and the msb of the argument is not set, print no warning
1767 */
1768 if (ptn->tn_op == CON && tspec_is_int(nt) &&
1769 styp(nt) == styp(ot) &&
1770 msb(ptn->tn_val->v_quad, ot, -1) == 0) {
1771 /* ok */
1772 } else {
1773 /* conversion to '%s' due to prototype, arg #%d */
1774 warning(259, tyname(buf, sizeof(buf), tp), arg);
1775 }
1776 }
1777 }
1778
1779 /*
1780 * Print warnings for conversions of integer types which may cause problems.
1781 */
1782 /* ARGSUSED */
1783 static void
1784 check_integer_conversion(op_t op, int arg, tspec_t nt, tspec_t ot, type_t *tp,
1785 tnode_t *tn)
1786 {
1787 char lbuf[64], rbuf[64], opbuf[16];
1788 if (tn->tn_op == CON)
1789 return;
1790
1791 if (op == CVT)
1792 return;
1793
1794 if (Pflag && psize(nt) > psize(ot) &&
1795 tspec_is_uint(nt) != tspec_is_uint(ot)) {
1796 /* conversion to %s may sign-extend incorrectly (, arg #%d) */
1797 if (aflag && pflag) {
1798 if (op == FARG) {
1799 warning(297, tyname(lbuf, sizeof(lbuf), tp),
1800 arg);
1801 } else {
1802 warning(131, tyname(lbuf, sizeof(lbuf), tp));
1803 }
1804 }
1805 }
1806
1807 if (Pflag && psize(nt) > psize(ot)) {
1808 switch (tn->tn_op) {
1809 case PLUS:
1810 case MINUS:
1811 case MULT:
1812 case SHL:
1813 warning(324,
1814 tyname(rbuf, sizeof(rbuf), gettyp(ot)),
1815 tyname(lbuf, sizeof(lbuf), tp),
1816 print_tnode(opbuf, sizeof(opbuf), tn));
1817 break;
1818 default:
1819 break;
1820 }
1821 }
1822
1823 if (psize(nt) < psize(ot) &&
1824 (ot == LONG || ot == ULONG || ot == QUAD || ot == UQUAD ||
1825 aflag > 1)) {
1826 /* conversion from '%s' may lose accuracy */
1827 if (aflag) {
1828 if (op == FARG) {
1829 warning(298,
1830 tyname(rbuf, sizeof(rbuf), tn->tn_type),
1831 tyname(lbuf, sizeof(lbuf), tp),
1832 arg);
1833 } else {
1834 warning(132,
1835 tyname(rbuf, sizeof(rbuf), tn->tn_type),
1836 tyname(lbuf, sizeof(lbuf), tp));
1837 }
1838 }
1839 }
1840 }
1841
1842 /*
1843 * Print warnings for dubious conversions of pointer to integer.
1844 */
1845 static void
1846 check_pointer_integer_conversion(op_t op, tspec_t nt, type_t *tp, tnode_t *tn)
1847 {
1848 char buf[64];
1849
1850 if (tn->tn_op == CON)
1851 return;
1852
1853 if (op != CVT) {
1854 /* We got already an error. */
1855 return;
1856 }
1857
1858 if (psize(nt) < psize(PTR)) {
1859 if (pflag && size(nt) >= size(PTR)) {
1860 /* conv. of pointer to '%s' may lose bits */
1861 warning(134, tyname(buf, sizeof(buf), tp));
1862 } else {
1863 /* conv. of pointer to '%s' loses bits */
1864 warning(133, tyname(buf, sizeof(buf), tp));
1865 }
1866 }
1867 }
1868
1869 /*
1870 * Print warnings for questionable pointer conversions.
1871 */
1872 static void
1873 check_pointer_conversion(op_t op, tnode_t *tn, type_t *tp)
1874 {
1875 tspec_t nt, ot;
1876 const char *nts, *ots;
1877
1878 /*
1879 * We got already an error (pointers of different types
1880 * without a cast) or we will not get a warning.
1881 */
1882 if (op != CVT)
1883 return;
1884
1885 nt = tp->t_subt->t_tspec;
1886 ot = tn->tn_type->t_subt->t_tspec;
1887
1888 if (nt == VOID || ot == VOID) {
1889 if (sflag && (nt == FUNC || ot == FUNC)) {
1890 /* (void *)0 already handled in convert() */
1891 *(nt == FUNC ? &nts : &ots) = "function pointer";
1892 *(nt == VOID ? &nts : &ots) = "'void *'";
1893 /* ANSI C forbids conversion of %s to %s */
1894 warning(303, ots, nts);
1895 }
1896 return;
1897 } else if (nt == FUNC && ot == FUNC) {
1898 return;
1899 } else if (nt == FUNC || ot == FUNC) {
1900 /* questionable conversion of function pointer */
1901 warning(229);
1902 return;
1903 }
1904
1905 if (getbound(tp->t_subt) > getbound(tn->tn_type->t_subt)) {
1906 if (hflag)
1907 /* possible pointer alignment problem */
1908 warning(135);
1909 }
1910 if (((nt == STRUCT || nt == UNION) &&
1911 tp->t_subt->t_str != tn->tn_type->t_subt->t_str) ||
1912 psize(nt) != psize(ot)) {
1913 if (cflag) {
1914 /* pointer casts may be troublesome */
1915 warning(247);
1916 }
1917 }
1918 }
1919
1920 /*
1921 * Converts a typed constant in a constant of another type.
1922 *
1923 * op operator which requires conversion
1924 * arg if op is FARG, # of argument
1925 * tp type in which to convert the constant
1926 * nv new constant
1927 * v old constant
1928 */
1929 void
1930 cvtcon(op_t op, int arg, type_t *tp, val_t *nv, val_t *v)
1931 {
1932 char lbuf[64], rbuf[64];
1933 tspec_t ot, nt;
1934 ldbl_t max = 0.0, min = 0.0;
1935 int sz, rchk;
1936 int64_t xmask, xmsk1;
1937 int osz, nsz;
1938
1939 ot = v->v_tspec;
1940 nt = nv->v_tspec = tp->t_tspec;
1941 rchk = 0;
1942
1943 if (ot == FLOAT || ot == DOUBLE || ot == LDOUBLE) {
1944 switch (nt) {
1945 case BOOL:
1946 max = 1; min = 0; break;
1947 case CHAR:
1948 max = TARG_CHAR_MAX; min = TARG_CHAR_MIN; break;
1949 case UCHAR:
1950 max = TARG_UCHAR_MAX; min = 0; break;
1951 case SCHAR:
1952 max = TARG_SCHAR_MAX; min = TARG_SCHAR_MIN; break;
1953 case SHORT:
1954 max = TARG_SHRT_MAX; min = TARG_SHRT_MIN; break;
1955 case USHORT:
1956 max = TARG_USHRT_MAX; min = 0; break;
1957 case ENUM:
1958 case INT:
1959 max = TARG_INT_MAX; min = TARG_INT_MIN; break;
1960 case UINT:
1961 max = (u_int)TARG_UINT_MAX;min = 0; break;
1962 case LONG:
1963 max = TARG_LONG_MAX; min = TARG_LONG_MIN; break;
1964 case ULONG:
1965 max = (u_long)TARG_ULONG_MAX; min = 0; break;
1966 case QUAD:
1967 max = QUAD_MAX; min = QUAD_MIN; break;
1968 case UQUAD:
1969 max = (uint64_t)UQUAD_MAX; min = 0; break;
1970 case FLOAT:
1971 case FCOMPLEX:
1972 max = FLT_MAX; min = -FLT_MAX; break;
1973 case DOUBLE:
1974 case DCOMPLEX:
1975 max = DBL_MAX; min = -DBL_MAX; break;
1976 case PTR:
1977 /* Got already an error because of float --> ptr */
1978 case LDOUBLE:
1979 case LCOMPLEX:
1980 max = LDBL_MAX; min = -LDBL_MAX; break;
1981 default:
1982 lint_assert(0);
1983 }
1984 if (v->v_ldbl > max || v->v_ldbl < min) {
1985 lint_assert(nt != LDOUBLE);
1986 if (op == FARG) {
1987 /* conv. of '%s' to '%s' is out of range, ... */
1988 warning(295,
1989 tyname(lbuf, sizeof(lbuf), gettyp(ot)),
1990 tyname(rbuf, sizeof(rbuf), tp),
1991 arg);
1992 } else {
1993 /* conversion of '%s' to '%s' is out of range */
1994 warning(119,
1995 tyname(lbuf, sizeof(lbuf), gettyp(ot)),
1996 tyname(rbuf, sizeof(rbuf), tp));
1997 }
1998 v->v_ldbl = v->v_ldbl > 0 ? max : min;
1999 }
2000 if (nt == FLOAT) {
2001 nv->v_ldbl = (float)v->v_ldbl;
2002 } else if (nt == DOUBLE) {
2003 nv->v_ldbl = (double)v->v_ldbl;
2004 } else if (nt == LDOUBLE) {
2005 nv->v_ldbl = v->v_ldbl;
2006 } else {
2007 nv->v_quad = (nt == PTR || tspec_is_uint(nt)) ?
2008 (int64_t)v->v_ldbl : (int64_t)v->v_ldbl;
2009 }
2010 } else {
2011 if (nt == FLOAT) {
2012 nv->v_ldbl = (ot == PTR || tspec_is_uint(ot)) ?
2013 (float)(uint64_t)v->v_quad : (float)v->v_quad;
2014 } else if (nt == DOUBLE) {
2015 nv->v_ldbl = (ot == PTR || tspec_is_uint(ot)) ?
2016 (double)(uint64_t)v->v_quad : (double)v->v_quad;
2017 } else if (nt == LDOUBLE) {
2018 nv->v_ldbl = (ot == PTR || tspec_is_uint(ot)) ?
2019 (ldbl_t)(uint64_t)v->v_quad : (ldbl_t)v->v_quad;
2020 } else {
2021 rchk = 1; /* Check for lost precision. */
2022 nv->v_quad = v->v_quad;
2023 }
2024 }
2025
2026 if (v->v_ansiu && tspec_is_float(nt)) {
2027 /* ANSI C treats constant as unsigned */
2028 warning(157);
2029 v->v_ansiu = 0;
2030 } else if (v->v_ansiu && (tspec_is_int(nt) && !tspec_is_uint(nt) &&
2031 psize(nt) > psize(ot))) {
2032 /* ANSI C treats constant as unsigned */
2033 warning(157);
2034 v->v_ansiu = 0;
2035 }
2036
2037 switch (nt) {
2038 case FLOAT:
2039 case FCOMPLEX:
2040 case DOUBLE:
2041 case DCOMPLEX:
2042 case LDOUBLE:
2043 case LCOMPLEX:
2044 break;
2045 default:
2046 sz = tp->t_isfield ? tp->t_flen : size(nt);
2047 nv->v_quad = xsign(nv->v_quad, nt, sz);
2048 break;
2049 }
2050
2051 if (rchk && op != CVT) {
2052 osz = size(ot);
2053 nsz = tp->t_isfield ? tp->t_flen : size(nt);
2054 xmask = qlmasks[nsz] ^ qlmasks[osz];
2055 xmsk1 = qlmasks[nsz] ^ qlmasks[osz - 1];
2056 /*
2057 * For bitwise operations we are not interested in the
2058 * value, but in the bits itself.
2059 */
2060 if (op == ORASS || op == OR || op == XOR) {
2061 /*
2062 * Print a warning if bits which were set are
2063 * lost due to the conversion.
2064 * This can happen with operator ORASS only.
2065 */
2066 if (nsz < osz && (v->v_quad & xmask) != 0) {
2067 /* constant truncated by conv., op %s */
2068 warning(306, modtab[op].m_name);
2069 }
2070 } else if (op == ANDASS || op == AND) {
2071 /*
2072 * Print a warning if additional bits are not all 1
2073 * and the most significant bit of the old value is 1,
2074 * or if at least one (but not all) removed bit was 0.
2075 */
2076 if (nsz > osz &&
2077 (nv->v_quad & qbmasks[osz - 1]) != 0 &&
2078 (nv->v_quad & xmask) != xmask) {
2079 /*
2080 * extra bits set to 0 in conversion
2081 * of '%s' to '%s', op %s
2082 */
2083 warning(309,
2084 tyname(lbuf, sizeof(lbuf), gettyp(ot)),
2085 tyname(rbuf, sizeof(rbuf), tp),
2086 modtab[op].m_name);
2087 } else if (nsz < osz &&
2088 (v->v_quad & xmask) != xmask &&
2089 (v->v_quad & xmask) != 0) {
2090 /* constant truncated by conv., op %s */
2091 warning(306, modtab[op].m_name);
2092 }
2093 } else if ((nt != PTR && tspec_is_uint(nt)) &&
2094 (ot != PTR && !tspec_is_uint(ot)) && v->v_quad < 0) {
2095 if (op == ASSIGN) {
2096 /* assignment of negative constant to ... */
2097 warning(164);
2098 } else if (op == INIT) {
2099 /* initialisation of unsigned with neg... */
2100 warning(221);
2101 } else if (op == FARG) {
2102 /* conversion of negative constant to ... */
2103 warning(296, arg);
2104 } else if (modtab[op].m_comp) {
2105 /* handled by check_integer_comparison() */
2106 } else {
2107 /* conversion of negative constant to ... */
2108 warning(222);
2109 }
2110 } else if (nv->v_quad != v->v_quad && nsz <= osz &&
2111 (v->v_quad & xmask) != 0 &&
2112 (tspec_is_uint(ot) ||
2113 (v->v_quad & xmsk1) != xmsk1)) {
2114 /*
2115 * Loss of significant bit(s). All truncated bits
2116 * of unsigned types or all truncated bits plus the
2117 * msb of the target for signed types are considered
2118 * to be significant bits. Loss of significant bits
2119 * means that at least on of the bits was set in an
2120 * unsigned type or that at least one, but not all of
2121 * the bits was set in an signed type.
2122 * Loss of significant bits means that it is not
2123 * possible, also not with necessary casts, to convert
2124 * back to the original type. A example for a
2125 * necessary cast is:
2126 * char c; int i; c = 128;
2127 * i = c; ** yields -128 **
2128 * i = (unsigned char)c; ** yields 128 **
2129 */
2130 if (op == ASSIGN && tp->t_isfield) {
2131 /* precision lost in bit-field assignment */
2132 warning(166);
2133 } else if (op == ASSIGN) {
2134 /* constant truncated by assignment */
2135 warning(165);
2136 } else if (op == INIT && tp->t_isfield) {
2137 /* bit-field initializer does not fit */
2138 warning(180);
2139 } else if (op == INIT) {
2140 /* initializer does not fit */
2141 warning(178);
2142 } else if (op == CASE) {
2143 /* case label affected by conversion */
2144 warning(196);
2145 } else if (op == FARG) {
2146 /* conv. of '%s' to '%s' is out of range, ... */
2147 warning(295,
2148 tyname(lbuf, sizeof(lbuf), gettyp(ot)),
2149 tyname(rbuf, sizeof(rbuf), tp),
2150 arg);
2151 } else {
2152 /* conversion of '%s' to '%s' is out of range */
2153 warning(119,
2154 tyname(lbuf, sizeof(lbuf), gettyp(ot)),
2155 tyname(rbuf, sizeof(rbuf), tp));
2156 }
2157 } else if (nv->v_quad != v->v_quad) {
2158 if (op == ASSIGN && tp->t_isfield) {
2159 /* precision lost in bit-field assignment */
2160 warning(166);
2161 } else if (op == INIT && tp->t_isfield) {
2162 /* bit-field initializer out of range */
2163 warning(11);
2164 } else if (op == CASE) {
2165 /* case label affected by conversion */
2166 warning(196);
2167 } else if (op == FARG) {
2168 /* conv. of '%s' to '%s' is out of range, ... */
2169 warning(295,
2170 tyname(lbuf, sizeof(lbuf), gettyp(ot)),
2171 tyname(rbuf, sizeof(rbuf), tp),
2172 arg);
2173 } else {
2174 /* conversion of '%s' to '%s' is out of range */
2175 warning(119,
2176 tyname(lbuf, sizeof(lbuf), gettyp(ot)),
2177 tyname(rbuf, sizeof(rbuf), tp));
2178 }
2179 }
2180 }
2181 }
2182
2183 /*
2184 * Called if incompatible types were detected.
2185 * Prints a appropriate warning.
2186 */
2187 static void
2188 warn_incompatible_types(op_t op, tspec_t lt, tspec_t rt)
2189 {
2190 mod_t *mp;
2191 int e = 0;
2192
2193 mp = &modtab[op];
2194
2195 if (lt == VOID || (mp->m_binary && rt == VOID)) {
2196 /* void type illegal in expression */
2197 e = 109;
2198 } else if (op == ASSIGN) {
2199 if ((lt == STRUCT || lt == UNION) &&
2200 (rt == STRUCT || rt == UNION)) {
2201 /* assignment of different structures */
2202 e = 240;
2203 } else {
2204 /* assignment type mismatch */
2205 e = 171;
2206 }
2207 } else if (mp->m_binary) {
2208 /* operands of %s have incompatible types */
2209 e = 107;
2210 } else {
2211 /* operand of %s has incompatible type */
2212 e = 108;
2213 }
2214 switch (e) {
2215 case 0:
2216 return;
2217 case 109:
2218 error(e);
2219 return;
2220 case 108:
2221 case 107:
2222 error(e, mp->m_name, basic_type_name(lt), basic_type_name(rt));
2223 return;
2224 default:
2225 error(e, basic_type_name(lt), basic_type_name(rt));
2226 return;
2227 }
2228 }
2229
2230 /*
2231 * Called if incompatible pointer types are detected.
2232 * Print an appropriate warning.
2233 */
2234 static void
2235 warn_incompatible_pointers(mod_t *mp, type_t *ltp, type_t *rtp)
2236 {
2237 tspec_t lt, rt;
2238
2239 lint_assert(ltp->t_tspec == PTR);
2240 lint_assert(rtp->t_tspec == PTR);
2241
2242 lt = ltp->t_subt->t_tspec;
2243 rt = rtp->t_subt->t_tspec;
2244
2245 if ((lt == STRUCT || lt == UNION) && (rt == STRUCT || rt == UNION)) {
2246 if (mp == NULL) {
2247 /* illegal structure pointer combination */
2248 warning(244);
2249 } else {
2250 /* illegal structure pointer combination, op %s */
2251 warning(245, mp->m_name);
2252 }
2253 } else {
2254 if (mp == NULL) {
2255 /* illegal pointer combination */
2256 warning(184);
2257 } else {
2258 /* illegal pointer combination, op %s */
2259 warning(124, mp->m_name);
2260 }
2261 }
2262 }
2263
2264 /*
2265 * Make sure type (*tpp)->t_subt has at least the qualifiers
2266 * of tp1->t_subt and tp2->t_subt.
2267 */
2268 static void
2269 merge_qualifiers(type_t **tpp, type_t *tp1, type_t *tp2)
2270 {
2271
2272 lint_assert((*tpp)->t_tspec == PTR);
2273 lint_assert(tp1->t_tspec == PTR);
2274 lint_assert(tp2->t_tspec == PTR);
2275
2276 if ((*tpp)->t_subt->t_const ==
2277 (tp1->t_subt->t_const | tp2->t_subt->t_const) &&
2278 (*tpp)->t_subt->t_volatile ==
2279 (tp1->t_subt->t_volatile | tp2->t_subt->t_volatile)) {
2280 return;
2281 }
2282
2283 *tpp = tduptyp(*tpp);
2284 (*tpp)->t_subt = tduptyp((*tpp)->t_subt);
2285 (*tpp)->t_subt->t_const =
2286 tp1->t_subt->t_const | tp2->t_subt->t_const;
2287 (*tpp)->t_subt->t_volatile =
2288 tp1->t_subt->t_volatile | tp2->t_subt->t_volatile;
2289 }
2290
2291 /*
2292 * Returns 1 if the given structure or union has a constant member
2293 * (maybe recursively).
2294 */
2295 static int
2296 has_constant_member(type_t *tp)
2297 {
2298 sym_t *m;
2299 tspec_t t;
2300
2301 lint_assert((t = tp->t_tspec) == STRUCT || t == UNION);
2302
2303 for (m = tp->t_str->memb; m != NULL; m = m->s_next) {
2304 tp = m->s_type;
2305 if (tp->t_const)
2306 return 1;
2307 if ((t = tp->t_tspec) == STRUCT || t == UNION) {
2308 if (has_constant_member(m->s_type))
2309 return 1;
2310 }
2311 }
2312 return 0;
2313 }
2314
2315 /*
2316 * Create a new node for one of the operators POINT and ARROW.
2317 */
2318 static tnode_t *
2319 build_struct_access(op_t op, tnode_t *ln, tnode_t *rn)
2320 {
2321 tnode_t *ntn, *ctn;
2322 int nolval;
2323
2324 lint_assert(rn->tn_op == NAME);
2325 lint_assert(rn->tn_sym->s_value.v_tspec == INT);
2326 lint_assert(rn->tn_sym->s_scl == MOS || rn->tn_sym->s_scl == MOU);
2327
2328 /*
2329 * Remember if the left operand is an lvalue (structure members
2330 * are lvalues if and only if the structure itself is an lvalue).
2331 */
2332 nolval = op == POINT && !ln->tn_lvalue;
2333
2334 if (op == POINT) {
2335 ln = build_ampersand(ln, 1);
2336 } else if (ln->tn_type->t_tspec != PTR) {
2337 lint_assert(tflag);
2338 lint_assert(tspec_is_int(ln->tn_type->t_tspec));
2339 ln = convert(NOOP, 0, tincref(gettyp(VOID), PTR), ln);
2340 }
2341
2342 #if PTRDIFF_IS_LONG
2343 ctn = new_int_const_node(LONG, rn->tn_sym->s_value.v_quad / CHAR_BIT);
2344 #else
2345 ctn = new_int_const_node(INT, rn->tn_sym->s_value.v_quad / CHAR_BIT);
2346 #endif
2347
2348 ntn = new_tnode(PLUS, tincref(rn->tn_type, PTR), ln, ctn);
2349 if (ln->tn_op == CON)
2350 ntn = fold(ntn);
2351
2352 if (rn->tn_type->t_isfield) {
2353 ntn = new_tnode(FSEL, ntn->tn_type->t_subt, ntn, NULL);
2354 } else {
2355 ntn = new_tnode(STAR, ntn->tn_type->t_subt, ntn, NULL);
2356 }
2357
2358 if (nolval)
2359 ntn->tn_lvalue = 0;
2360
2361 return ntn;
2362 }
2363
2364 /*
2365 * Create a node for INCAFT, INCBEF, DECAFT and DECBEF.
2366 */
2367 static tnode_t *
2368 build_prepost_incdec(op_t op, tnode_t *ln)
2369 {
2370 tnode_t *cn, *ntn;
2371
2372 lint_assert(ln != NULL);
2373
2374 if (ln->tn_type->t_tspec == PTR) {
2375 cn = plength(ln->tn_type);
2376 } else {
2377 cn = new_int_const_node(INT, (int64_t)1);
2378 }
2379 ntn = new_tnode(op, ln->tn_type, ln, cn);
2380
2381 return ntn;
2382 }
2383
2384 /*
2385 * Create a node for REAL, IMAG
2386 */
2387 static tnode_t *
2388 build_real_imag(op_t op, tnode_t *ln)
2389 {
2390 tnode_t *cn, *ntn;
2391 char buf[64];
2392
2393 lint_assert(ln != NULL);
2394
2395 switch (ln->tn_type->t_tspec) {
2396 case LCOMPLEX:
2397 cn = new_int_const_node(LDOUBLE, (int64_t)1);
2398 break;
2399 case DCOMPLEX:
2400 cn = new_int_const_node(DOUBLE, (int64_t)1);
2401 break;
2402 case FCOMPLEX:
2403 cn = new_int_const_node(FLOAT, (int64_t)1);
2404 break;
2405 default:
2406 error(276, op == REAL ? "real" : "imag",
2407 tyname(buf, sizeof(buf), ln->tn_type));
2408 return NULL;
2409 }
2410 ntn = new_tnode(op, cn->tn_type, ln, cn);
2411 ntn->tn_lvalue = 1;
2412
2413 return ntn;
2414 }
2415 /*
2416 * Create a tree node for the & operator
2417 */
2418 static tnode_t *
2419 build_ampersand(tnode_t *tn, int noign)
2420 {
2421 tnode_t *ntn;
2422 tspec_t t;
2423
2424 if (!noign && ((t = tn->tn_type->t_tspec) == ARRAY || t == FUNC)) {
2425 /* & before array or function: ignored */
2426 if (tflag)
2427 warning(127);
2428 return tn;
2429 }
2430
2431 /* eliminate &* */
2432 if (tn->tn_op == STAR &&
2433 tn->tn_left->tn_type->t_tspec == PTR &&
2434 tn->tn_left->tn_type->t_subt == tn->tn_type) {
2435 return tn->tn_left;
2436 }
2437
2438 ntn = new_tnode(AMPER, tincref(tn->tn_type, PTR), tn, NULL);
2439
2440 return ntn;
2441 }
2442
2443 /*
2444 * Create a node for operators PLUS and MINUS.
2445 */
2446 static tnode_t *
2447 build_plus_minus(op_t op, tnode_t *ln, tnode_t *rn)
2448 {
2449 tnode_t *ntn, *ctn;
2450 type_t *tp;
2451
2452 /* If pointer and integer, then pointer to the lhs. */
2453 if (rn->tn_type->t_tspec == PTR &&
2454 tspec_is_int(ln->tn_type->t_tspec)) {
2455 ntn = ln;
2456 ln = rn;
2457 rn = ntn;
2458 }
2459
2460 if (ln->tn_type->t_tspec == PTR && rn->tn_type->t_tspec != PTR) {
2461
2462 lint_assert(tspec_is_int(rn->tn_type->t_tspec));
2463
2464 ctn = plength(ln->tn_type);
2465 if (rn->tn_type->t_tspec != ctn->tn_type->t_tspec)
2466 rn = convert(NOOP, 0, ctn->tn_type, rn);
2467 rn = new_tnode(MULT, rn->tn_type, rn, ctn);
2468 if (rn->tn_left->tn_op == CON)
2469 rn = fold(rn);
2470 ntn = new_tnode(op, ln->tn_type, ln, rn);
2471
2472 } else if (rn->tn_type->t_tspec == PTR) {
2473
2474 lint_assert(ln->tn_type->t_tspec == PTR);
2475 lint_assert(op == MINUS);
2476 #if PTRDIFF_IS_LONG
2477 tp = gettyp(LONG);
2478 #else
2479 tp = gettyp(INT);
2480 #endif
2481 ntn = new_tnode(op, tp, ln, rn);
2482 if (ln->tn_op == CON && rn->tn_op == CON)
2483 ntn = fold(ntn);
2484 ctn = plength(ln->tn_type);
2485 balance(NOOP, &ntn, &ctn);
2486 ntn = new_tnode(DIV, tp, ntn, ctn);
2487
2488 } else {
2489
2490 ntn = new_tnode(op, ln->tn_type, ln, rn);
2491
2492 }
2493 return ntn;
2494 }
2495
2496 /*
2497 * Create a node for operators SHL and SHR.
2498 */
2499 static tnode_t *
2500 build_bit_shift(op_t op, tnode_t *ln, tnode_t *rn)
2501 {
2502 tspec_t t;
2503 tnode_t *ntn;
2504
2505 if ((t = rn->tn_type->t_tspec) != INT && t != UINT)
2506 rn = convert(CVT, 0, gettyp(INT), rn);
2507 ntn = new_tnode(op, ln->tn_type, ln, rn);
2508 return ntn;
2509 }
2510
2511 /*
2512 * Create a node for COLON.
2513 */
2514 static tnode_t *
2515 build_colon(tnode_t *ln, tnode_t *rn)
2516 {
2517 tspec_t lt, rt, pdt;
2518 type_t *rtp;
2519 tnode_t *ntn;
2520
2521 lt = ln->tn_type->t_tspec;
2522 rt = rn->tn_type->t_tspec;
2523 #if PTRDIFF_IS_LONG
2524 pdt = LONG;
2525 #else
2526 pdt = INT;
2527 #endif
2528
2529 /*
2530 * Arithmetic types are balanced, all other type combinations
2531 * still need to be handled.
2532 */
2533 if (tspec_is_arith(lt) && tspec_is_arith(rt)) {
2534 rtp = ln->tn_type;
2535 } else if (lt == VOID || rt == VOID) {
2536 rtp = gettyp(VOID);
2537 } else if (lt == STRUCT || lt == UNION) {
2538 /* Both types must be identical. */
2539 lint_assert(rt == STRUCT || rt == UNION);
2540 lint_assert(ln->tn_type->t_str == rn->tn_type->t_str);
2541 if (incompl(ln->tn_type)) {
2542 /* unknown operand size, op %s */
2543 error(138, modtab[COLON].m_name);
2544 return NULL;
2545 }
2546 rtp = ln->tn_type;
2547 } else if (lt == PTR && tspec_is_int(rt)) {
2548 if (rt != pdt) {
2549 rn = convert(NOOP, 0, gettyp(pdt), rn);
2550 rt = pdt;
2551 }
2552 rtp = ln->tn_type;
2553 } else if (rt == PTR && tspec_is_int(lt)) {
2554 if (lt != pdt) {
2555 ln = convert(NOOP, 0, gettyp(pdt), ln);
2556 lt = pdt;
2557 }
2558 rtp = rn->tn_type;
2559 } else if (lt == PTR && ln->tn_type->t_subt->t_tspec == VOID) {
2560 lint_assert(rt == PTR);
2561 rtp = rn->tn_type;
2562 merge_qualifiers(&rtp, ln->tn_type, rn->tn_type);
2563 } else if (rt == PTR && rn->tn_type->t_subt->t_tspec == VOID) {
2564 lint_assert(lt == PTR);
2565 rtp = ln->tn_type;
2566 merge_qualifiers(&rtp, ln->tn_type, rn->tn_type);
2567 } else {
2568 lint_assert(lt == PTR);
2569 lint_assert(rt == PTR);
2570 /*
2571 * XXX For now we simply take the left type. This is
2572 * probably wrong, if one type contains a function prototype
2573 * and the other one, at the same place, only an old style
2574 * declaration.
2575 */
2576 rtp = ln->tn_type;
2577 merge_qualifiers(&rtp, ln->tn_type, rn->tn_type);
2578 }
2579
2580 ntn = new_tnode(COLON, rtp, ln, rn);
2581
2582 return ntn;
2583 }
2584
2585 /*
2586 * Create a node for an assignment operator (both = and op= ).
2587 */
2588 static tnode_t *
2589 build_assignment(op_t op, tnode_t *ln, tnode_t *rn)
2590 {
2591 tspec_t lt, rt;
2592 tnode_t *ntn, *ctn;
2593
2594 lint_assert(ln != NULL);
2595 lint_assert(rn != NULL);
2596
2597 lt = ln->tn_type->t_tspec;
2598 rt = rn->tn_type->t_tspec;
2599
2600 if ((op == ADDASS || op == SUBASS) && lt == PTR) {
2601 lint_assert(tspec_is_int(rt));
2602 ctn = plength(ln->tn_type);
2603 if (rn->tn_type->t_tspec != ctn->tn_type->t_tspec)
2604 rn = convert(NOOP, 0, ctn->tn_type, rn);
2605 rn = new_tnode(MULT, rn->tn_type, rn, ctn);
2606 if (rn->tn_left->tn_op == CON)
2607 rn = fold(rn);
2608 }
2609
2610 if ((op == ASSIGN || op == RETURN) && (lt == STRUCT || rt == STRUCT)) {
2611 lint_assert(lt == rt);
2612 lint_assert(ln->tn_type->t_str == rn->tn_type->t_str);
2613 if (incompl(ln->tn_type)) {
2614 if (op == RETURN) {
2615 /* cannot return incomplete type */
2616 error(212);
2617 } else {
2618 /* unknown operand size, op %s */
2619 error(138, modtab[op].m_name);
2620 }
2621 return NULL;
2622 }
2623 }
2624
2625 if (op == SHLASS) {
2626 if (psize(lt) < psize(rt)) {
2627 if (hflag)
2628 /* semantics of '%s' change in ANSI C; ... */
2629 warning(118, "<<=");
2630 }
2631 } else if (op != SHRASS) {
2632 if (op == ASSIGN || lt != PTR) {
2633 if (lt != rt ||
2634 (ln->tn_type->t_isfield && rn->tn_op == CON)) {
2635 rn = convert(op, 0, ln->tn_type, rn);
2636 rt = lt;
2637 }
2638 }
2639 }
2640
2641 ntn = new_tnode(op, ln->tn_type, ln, rn);
2642
2643 return ntn;
2644 }
2645
2646 /*
2647 * Get length of type tp->t_subt.
2648 */
2649 static tnode_t *
2650 plength(type_t *tp)
2651 {
2652 int elem, elsz;
2653 tspec_t st;
2654
2655 lint_assert(tp->t_tspec == PTR);
2656 tp = tp->t_subt;
2657
2658 elem = 1;
2659 elsz = 0;
2660
2661 while (tp->t_tspec == ARRAY) {
2662 elem *= tp->t_dim;
2663 tp = tp->t_subt;
2664 }
2665
2666 switch (tp->t_tspec) {
2667 case FUNC:
2668 /* pointer to function is not allowed here */
2669 error(110);
2670 break;
2671 case VOID:
2672 /* cannot do pointer arithmetic on operand of ... */
2673 (void)gnuism(136);
2674 break;
2675 case STRUCT:
2676 case UNION:
2677 if ((elsz = tp->t_str->size) == 0)
2678 /* cannot do pointer arithmetic on operand of ... */
2679 error(136);
2680 break;
2681 case ENUM:
2682 if (incompl(tp)) {
2683 /* cannot do pointer arithmetic on operand of ... */
2684 warning(136);
2685 }
2686 /* FALLTHROUGH */
2687 default:
2688 if ((elsz = size(tp->t_tspec)) == 0) {
2689 /* cannot do pointer arithmetic on operand of ... */
2690 error(136);
2691 } else {
2692 lint_assert(elsz != -1);
2693 }
2694 break;
2695 }
2696
2697 if (elem == 0 && elsz != 0) {
2698 /* cannot do pointer arithmetic on operand of ... */
2699 error(136);
2700 }
2701
2702 if (elsz == 0)
2703 elsz = CHAR_BIT;
2704
2705 #if PTRDIFF_IS_LONG
2706 st = LONG;
2707 #else
2708 st = INT;
2709 #endif
2710
2711 return new_int_const_node(st, (int64_t)(elem * elsz / CHAR_BIT));
2712 }
2713
2714 /*
2715 * XXX
2716 * Note: There appear to be a number of bugs in detecting overflow in
2717 * this function. An audit and a set of proper regression tests are needed.
2718 * --Perry Metzger, Nov. 16, 2001
2719 */
2720 /*
2721 * Do only as much as necessary to compute constant expressions.
2722 * Called only if the operator allows folding and (both) operands
2723 * are constants.
2724 */
2725 static tnode_t *
2726 fold(tnode_t *tn)
2727 {
2728 val_t *v;
2729 tspec_t t;
2730 int utyp, ovfl;
2731 int64_t sl, sr = 0, q = 0, mask;
2732 uint64_t ul, ur = 0;
2733 tnode_t *cn;
2734
2735 v = xcalloc(1, sizeof (val_t));
2736 v->v_tspec = t = tn->tn_type->t_tspec;
2737
2738 utyp = t == PTR || tspec_is_uint(t);
2739 ul = sl = tn->tn_left->tn_val->v_quad;
2740 if (modtab[tn->tn_op].m_binary)
2741 ur = sr = tn->tn_right->tn_val->v_quad;
2742
2743 mask = qlmasks[size(t)];
2744 ovfl = 0;
2745
2746 switch (tn->tn_op) {
2747 case UPLUS:
2748 q = sl;
2749 break;
2750 case UMINUS:
2751 q = -sl;
2752 if (sl != 0 && msb(q, t, -1) == msb(sl, t, -1))
2753 ovfl = 1;
2754 break;
2755 case COMPL:
2756 q = ~sl;
2757 break;
2758 case MULT:
2759 if (utyp) {
2760 q = ul * ur;
2761 if (q != (q & mask))
2762 ovfl = 1;
2763 else if ((ul != 0) && ((q / ul) != ur))
2764 ovfl = 1;
2765 } else {
2766 q = sl * sr;
2767 if (msb(q, t, -1) != (msb(sl, t, -1) ^ msb(sr, t, -1)))
2768 ovfl = 1;
2769 }
2770 break;
2771 case DIV:
2772 if (sr == 0) {
2773 /* division by 0 */
2774 error(139);
2775 q = utyp ? UQUAD_MAX : QUAD_MAX;
2776 } else {
2777 q = utyp ? (int64_t)(ul / ur) : sl / sr;
2778 }
2779 break;
2780 case MOD:
2781 if (sr == 0) {
2782 /* modulus by 0 */
2783 error(140);
2784 q = 0;
2785 } else {
2786 q = utyp ? (int64_t)(ul % ur) : sl % sr;
2787 }
2788 break;
2789 case PLUS:
2790 q = utyp ? (int64_t)(ul + ur) : sl + sr;
2791 if (msb(sl, t, -1) != 0 && msb(sr, t, -1) != 0) {
2792 if (msb(q, t, -1) == 0)
2793 ovfl = 1;
2794 } else if (msb(sl, t, -1) == 0 && msb(sr, t, -1) == 0) {
2795 if (msb(q, t, -1) != 0)
2796 ovfl = 1;
2797 }
2798 break;
2799 case MINUS:
2800 q = utyp ? (int64_t)(ul - ur) : sl - sr;
2801 if (msb(sl, t, -1) != 0 && msb(sr, t, -1) == 0) {
2802 if (msb(q, t, -1) == 0)
2803 ovfl = 1;
2804 } else if (msb(sl, t, -1) == 0 && msb(sr, t, -1) != 0) {
2805 if (msb(q, t, -1) != 0)
2806 ovfl = 1;
2807 }
2808 break;
2809 case SHL:
2810 q = utyp ? (int64_t)(ul << sr) : sl << sr;
2811 break;
2812 case SHR:
2813 /*
2814 * The sign must be explicitly extended because
2815 * shifts of signed values are implementation dependent.
2816 */
2817 q = ul >> sr;
2818 q = xsign(q, t, size(t) - (int)sr);
2819 break;
2820 case LT:
2821 q = utyp ? ul < ur : sl < sr;
2822 break;
2823 case LE:
2824 q = utyp ? ul <= ur : sl <= sr;
2825 break;
2826 case GE:
2827 q = utyp ? ul >= ur : sl >= sr;
2828 break;
2829 case GT:
2830 q = utyp ? ul > ur : sl > sr;
2831 break;
2832 case EQ:
2833 q = utyp ? ul == ur : sl == sr;
2834 break;
2835 case NE:
2836 q = utyp ? ul != ur : sl != sr;
2837 break;
2838 case AND:
2839 q = utyp ? (int64_t)(ul & ur) : sl & sr;
2840 break;
2841 case XOR:
2842 q = utyp ? (int64_t)(ul ^ ur) : sl ^ sr;
2843 break;
2844 case OR:
2845 q = utyp ? (int64_t)(ul | ur) : sl | sr;
2846 break;
2847 default:
2848 lint_assert(0);
2849 }
2850
2851 /* XXX does not work for quads. */
2852 if (ovfl || ((uint64_t)(q | mask) != ~(uint64_t)0 &&
2853 (q & ~mask) != 0)) {
2854 if (hflag)
2855 /* integer overflow detected, op %s */
2856 warning(141, modtab[tn->tn_op].m_name);
2857 }
2858
2859 v->v_quad = xsign(q, t, -1);
2860
2861 cn = getcnode(tn->tn_type, v);
2862
2863 return cn;
2864 }
2865
2866 /*
2867 * Same for operators whose operands are compared with 0 (test context).
2868 */
2869 static tnode_t *
2870 fold_test(tnode_t *tn)
2871 {
2872 int l, r = 0;
2873 val_t *v;
2874
2875 v = xcalloc(1, sizeof (val_t));
2876 v->v_tspec = tn->tn_type->t_tspec;
2877 lint_assert(tn->tn_type->t_tspec == INT);
2878
2879 if (tspec_is_float(tn->tn_left->tn_type->t_tspec)) {
2880 l = tn->tn_left->tn_val->v_ldbl != 0.0;
2881 } else {
2882 l = tn->tn_left->tn_val->v_quad != 0;
2883 }
2884
2885 if (modtab[tn->tn_op].m_binary) {
2886 if (tspec_is_float(tn->tn_right->tn_type->t_tspec)) {
2887 r = tn->tn_right->tn_val->v_ldbl != 0.0;
2888 } else {
2889 r = tn->tn_right->tn_val->v_quad != 0;
2890 }
2891 }
2892
2893 switch (tn->tn_op) {
2894 case NOT:
2895 if (hflag && !constcond_flag)
2896 /* constant argument to NOT */
2897 warning(239);
2898 v->v_quad = !l;
2899 break;
2900 case LOGAND:
2901 v->v_quad = l && r;
2902 break;
2903 case LOGOR:
2904 v->v_quad = l || r;
2905 break;
2906 default:
2907 lint_assert(0);
2908 }
2909
2910 return getcnode(tn->tn_type, v);
2911 }
2912
2913 /*
2914 * Same for operands with floating point type.
2915 */
2916 static tnode_t *
2917 fold_float(tnode_t *tn)
2918 {
2919 val_t *v;
2920 tspec_t t;
2921 ldbl_t l, r = 0;
2922
2923 fpe = 0;
2924 v = xcalloc(1, sizeof (val_t));
2925 v->v_tspec = t = tn->tn_type->t_tspec;
2926
2927 lint_assert(tspec_is_float(t));
2928 lint_assert(t == tn->tn_left->tn_type->t_tspec);
2929 lint_assert(!modtab[tn->tn_op].m_binary ||
2930 t == tn->tn_right->tn_type->t_tspec);
2931
2932 l = tn->tn_left->tn_val->v_ldbl;
2933 if (modtab[tn->tn_op].m_binary)
2934 r = tn->tn_right->tn_val->v_ldbl;
2935
2936 switch (tn->tn_op) {
2937 case UPLUS:
2938 v->v_ldbl = l;
2939 break;
2940 case UMINUS:
2941 v->v_ldbl = -l;
2942 break;
2943 case MULT:
2944 v->v_ldbl = l * r;
2945 break;
2946 case DIV:
2947 if (r == 0.0) {
2948 /* division by 0 */
2949 error(139);
2950 if (t == FLOAT) {
2951 v->v_ldbl = l < 0 ? -FLT_MAX : FLT_MAX;
2952 } else if (t == DOUBLE) {
2953 v->v_ldbl = l < 0 ? -DBL_MAX : DBL_MAX;
2954 } else {
2955 v->v_ldbl = l < 0 ? -LDBL_MAX : LDBL_MAX;
2956 }
2957 } else {
2958 v->v_ldbl = l / r;
2959 }
2960 break;
2961 case PLUS:
2962 v->v_ldbl = l + r;
2963 break;
2964 case MINUS:
2965 v->v_ldbl = l - r;
2966 break;
2967 case LT:
2968 v->v_quad = l < r;
2969 break;
2970 case LE:
2971 v->v_quad = l <= r;
2972 break;
2973 case GE:
2974 v->v_quad = l >= r;
2975 break;
2976 case GT:
2977 v->v_quad = l > r;
2978 break;
2979 case EQ:
2980 v->v_quad = l == r;
2981 break;
2982 case NE:
2983 v->v_quad = l != r;
2984 break;
2985 default:
2986 lint_assert(0);
2987 }
2988
2989 lint_assert(fpe || !isnan((double)v->v_ldbl));
2990 if (fpe || !finite((double)v->v_ldbl) ||
2991 (t == FLOAT &&
2992 (v->v_ldbl > FLT_MAX || v->v_ldbl < -FLT_MAX)) ||
2993 (t == DOUBLE &&
2994 (v->v_ldbl > DBL_MAX || v->v_ldbl < -DBL_MAX))) {
2995 /* floating point overflow detected, op %s */
2996 warning(142, modtab[tn->tn_op].m_name);
2997 if (t == FLOAT) {
2998 v->v_ldbl = v->v_ldbl < 0 ? -FLT_MAX : FLT_MAX;
2999 } else if (t == DOUBLE) {
3000 v->v_ldbl = v->v_ldbl < 0 ? -DBL_MAX : DBL_MAX;
3001 } else {
3002 v->v_ldbl = v->v_ldbl < 0 ? -LDBL_MAX: LDBL_MAX;
3003 }
3004 fpe = 0;
3005 }
3006
3007 return getcnode(tn->tn_type, v);
3008 }
3009
3010
3011 /*
3012 * Create a constant node for sizeof.
3013 */
3014 tnode_t *
3015 build_sizeof(type_t *tp)
3016 {
3017 tspec_t st;
3018 #if SIZEOF_IS_ULONG
3019 st = ULONG;
3020 #else
3021 st = UINT;
3022 #endif
3023 return new_int_const_node(st, tsize(tp) / CHAR_BIT);
3024 }
3025
3026 /*
3027 * Create a constant node for offsetof.
3028 */
3029 tnode_t *
3030 build_offsetof(type_t *tp, sym_t *sym)
3031 {
3032 tspec_t st;
3033 #if SIZEOF_IS_ULONG
3034 st = ULONG;
3035 #else
3036 st = UINT;
3037 #endif
3038 tspec_t t = tp->t_tspec;
3039 if (t != STRUCT && t != UNION)
3040 error(111, "offsetof");
3041
3042 // XXX: wrong size, no checking for sym fixme
3043 return new_int_const_node(st, tsize(tp) / CHAR_BIT);
3044 }
3045
3046 int64_t
3047 tsize(type_t *tp)
3048 {
3049 int elem, elsz, flex;
3050
3051 elem = 1;
3052 flex = 0;
3053 while (tp->t_tspec == ARRAY) {
3054 flex = 1; /* allow c99 flex arrays [] [0] */
3055 elem *= tp->t_dim;
3056 tp = tp->t_subt;
3057 }
3058 if (elem == 0) {
3059 if (!flex) {
3060 /* cannot take size/alignment of incomplete type */
3061 error(143);
3062 elem = 1;
3063 }
3064 }
3065 switch (tp->t_tspec) {
3066 case FUNC:
3067 /* cannot take size/alignment of function */
3068 error(144);
3069 elsz = 1;
3070 break;
3071 case STRUCT:
3072 case UNION:
3073 if (incompl(tp)) {
3074 /* cannot take size/alignment of incomplete type */
3075 error(143);
3076 elsz = 1;
3077 } else {
3078 elsz = tp->t_str->size;
3079 }
3080 break;
3081 case ENUM:
3082 if (incompl(tp)) {
3083 /* cannot take size/alignment of incomplete type */
3084 warning(143);
3085 }
3086 /* FALLTHROUGH */
3087 default:
3088 if (tp->t_isfield) {
3089 /* cannot take size/alignment of bit-field */
3090 error(145);
3091 }
3092 if (tp->t_tspec == VOID) {
3093 /* cannot take size/alignment of void */
3094 error(146);
3095 elsz = 1;
3096 } else {
3097 elsz = size(tp->t_tspec);
3098 lint_assert(elsz > 0);
3099 }
3100 break;
3101 }
3102
3103 /* XXX: type conversion is too late */
3104 return (int64_t)(elem * elsz);
3105 }
3106
3107 /*
3108 */
3109 tnode_t *
3110 build_alignof(type_t *tp)
3111 {
3112 tspec_t st;
3113
3114 switch (tp->t_tspec) {
3115 case ARRAY:
3116 break;
3117
3118 case FUNC:
3119 /* cannot take size/alignment of function */
3120 error(144);
3121 return 0;
3122
3123 case STRUCT:
3124 case UNION:
3125 if (incompl(tp)) {
3126 /* cannot take size/alignment of incomplete type */
3127 error(143);
3128 return 0;
3129 }
3130 break;
3131 case ENUM:
3132 break;
3133 default:
3134 if (tp->t_isfield) {
3135 /* cannot take size/alignment of bit-field */
3136 error(145);
3137 return 0;
3138 }
3139 if (tp->t_tspec == VOID) {
3140 /* cannot take size/alignment of void */
3141 error(146);
3142 return 0;
3143 }
3144 break;
3145 }
3146
3147 #if SIZEOF_IS_ULONG
3148 st = ULONG;
3149 #else
3150 st = UINT;
3151 #endif
3152
3153 return new_int_const_node(st, (int64_t)getbound(tp) / CHAR_BIT);
3154 }
3155
3156 /*
3157 * Type casts.
3158 */
3159 tnode_t *
3160 cast(tnode_t *tn, type_t *tp)
3161 {
3162 tspec_t nt, ot;
3163
3164 if (tn == NULL)
3165 return NULL;
3166
3167 tn = cconv(tn);
3168
3169 nt = tp->t_tspec;
3170 ot = tn->tn_type->t_tspec;
3171
3172 if (nt == VOID) {
3173 /*
3174 * XXX ANSI C requires scalar types or void (Plauger & Brodie).
3175 * But this seams really questionable.
3176 */
3177 } else if (nt == UNION) {
3178 char buf[256], buf1[256];
3179 sym_t *m;
3180 str_t *str = tp->t_str;
3181 if (!Sflag) {
3182 error(328);
3183 return NULL;
3184 }
3185 for (m = str->memb; m != NULL; m = m->s_next) {
3186 if (sametype(m->s_type, tn->tn_type)) {
3187 tn = getnode();
3188 tn->tn_op = CVT;
3189 tn->tn_type = tp;
3190 tn->tn_cast = 1;
3191 tn->tn_right = NULL;
3192 return tn;
3193 }
3194 }
3195 error(329, tyname(buf, sizeof(buf), tn->tn_type),
3196 tyname(buf1, sizeof(buf1), tp));
3197 return NULL;
3198 } else if (nt == STRUCT || nt == ARRAY || nt == FUNC) {
3199 /* invalid cast expression */
3200 if (!Sflag || nt == ARRAY || nt == FUNC) {
3201 error(147);
3202 return NULL;
3203 }
3204 } else if (ot == STRUCT || ot == UNION) {
3205 /* invalid cast expression */
3206 error(147);
3207 return NULL;
3208 } else if (ot == VOID) {
3209 /* improper cast of void expression */
3210 error(148);
3211 return NULL;
3212 } else if (tspec_is_int(nt) && tspec_is_scalar(ot)) {
3213 /* ok */
3214 } else if (tspec_is_float(nt) && tspec_is_arith(ot)) {
3215 /* ok */
3216 } else if (nt == PTR && tspec_is_int(ot)) {
3217 /* ok */
3218 } else if (nt == PTR && ot == PTR) {
3219 if (!tp->t_subt->t_const && tn->tn_type->t_subt->t_const) {
3220 if (hflag)
3221 /* cast discards 'const' from ... */
3222 warning(275);
3223 }
3224 } else {
3225 /* invalid cast expression */
3226 error(147);
3227 return NULL;
3228 }
3229
3230 tn = convert(CVT, 0, tp, tn);
3231 tn->tn_cast = 1;
3232
3233 return tn;
3234 }
3235
3236 /*
3237 * Create the node for a function argument.
3238 * All necessary conversions and type checks are done in funccall(), because
3239 * in funcarg() we have no information about expected argument types.
3240 */
3241 tnode_t *
3242 funcarg(tnode_t *args, tnode_t *arg)
3243 {
3244 tnode_t *ntn;
3245
3246 /*
3247 * If there was a serious error in the expression for the argument,
3248 * create a dummy argument so the positions of the remaining arguments
3249 * will not change.
3250 */
3251 if (arg == NULL)
3252 arg = new_int_const_node(INT, (int64_t)0);
3253
3254 ntn = new_tnode(PUSH, arg->tn_type, arg, args);
3255
3256 return ntn;
3257 }
3258
3259 /*
3260 * Create the node for a function call. Also check types of
3261 * function arguments and insert conversions, if necessary.
3262 */
3263 tnode_t *
3264 funccall(tnode_t *func, tnode_t *args)
3265 {
3266 tnode_t *ntn;
3267 op_t fcop;
3268
3269 if (func == NULL)
3270 return NULL;
3271
3272 if (func->tn_op == NAME && func->tn_type->t_tspec == FUNC) {
3273 fcop = CALL;
3274 } else {
3275 fcop = ICALL;
3276 }
3277
3278 /*
3279 * after cconv() func will always be a pointer to a function
3280 * if it is a valid function designator.
3281 */
3282 func = cconv(func);
3283
3284 if (func->tn_type->t_tspec != PTR ||
3285 func->tn_type->t_subt->t_tspec != FUNC) {
3286 char buf[256];
3287 /* illegal function (type %s) */
3288 error(149, tyname(buf, sizeof(buf), func->tn_type));
3289 return NULL;
3290 }
3291
3292 args = check_function_arguments(func->tn_type->t_subt, args);
3293
3294 ntn = new_tnode(fcop, func->tn_type->t_subt->t_subt, func, args);
3295
3296 return ntn;
3297 }
3298
3299 /*
3300 * Check types of all function arguments and insert conversions,
3301 * if necessary.
3302 */
3303 static tnode_t *
3304 check_function_arguments(type_t *ftp, tnode_t *args)
3305 {
3306 tnode_t *arg;
3307 sym_t *asym;
3308 tspec_t at;
3309 int narg, npar, n, i;
3310
3311 /* get # of args in the prototype */
3312 npar = 0;
3313 for (asym = ftp->t_args; asym != NULL; asym = asym->s_next)
3314 npar++;
3315
3316 /* get # of args in function call */
3317 narg = 0;
3318 for (arg = args; arg != NULL; arg = arg->tn_right)
3319 narg++;
3320
3321 asym = ftp->t_args;
3322 if (ftp->t_proto && npar != narg && !(ftp->t_vararg && npar < narg)) {
3323 /* argument mismatch: %d arg%s passed, %d expected */
3324 error(150, narg, narg > 1 ? "s" : "", npar);
3325 asym = NULL;
3326 }
3327
3328 for (n = 1; n <= narg; n++) {
3329
3330 /*
3331 * The rightmost argument is at the top of the argument
3332 * subtree.
3333 */
3334 for (i = narg, arg = args; i > n; i--, arg = arg->tn_right)
3335 continue;
3336
3337 /* some things which are always not allowed */
3338 if ((at = arg->tn_left->tn_type->t_tspec) == VOID) {
3339 /* void expressions may not be arguments, arg #%d */
3340 error(151, n);
3341 return NULL;
3342 } else if ((at == STRUCT || at == UNION) &&
3343 incompl(arg->tn_left->tn_type)) {
3344 /* argument cannot have unknown size, arg #%d */
3345 error(152, n);
3346 return NULL;
3347 } else if (tspec_is_int(at) &&
3348 arg->tn_left->tn_type->t_isenum &&
3349 incompl(arg->tn_left->tn_type)) {
3350 /* argument cannot have unknown size, arg #%d */
3351 warning(152, n);
3352 }
3353
3354 /* class conversions (arg in value context) */
3355 arg->tn_left = cconv(arg->tn_left);
3356
3357 if (asym != NULL) {
3358 arg->tn_left = check_prototype_argument(
3359 n, asym->s_type, arg->tn_left);
3360 } else {
3361 arg->tn_left = promote(NOOP, 1, arg->tn_left);
3362 }
3363 arg->tn_type = arg->tn_left->tn_type;
3364
3365 if (asym != NULL)
3366 asym = asym->s_next;
3367 }
3368
3369 return args;
3370 }
3371
3372 /*
3373 * Compare the type of an argument with the corresponding type of a
3374 * prototype parameter. If it is a valid combination, but both types
3375 * are not the same, insert a conversion to convert the argument into
3376 * the type of the parameter.
3377 */
3378 static tnode_t *
3379 check_prototype_argument(
3380 int n, /* pos of arg */
3381 type_t *tp, /* expected type (from prototype) */
3382 tnode_t *tn) /* argument */
3383 {
3384 tnode_t *ln;
3385 int dowarn;
3386
3387 ln = xcalloc(1, sizeof (tnode_t));
3388 ln->tn_type = tduptyp(tp);
3389 ln->tn_type->t_const = 0;
3390 ln->tn_lvalue = 1;
3391 if (typeok(FARG, n, ln, tn)) {
3392 if (!eqtype(tp, tn->tn_type, 1, 0, (dowarn = 0, &dowarn)) || dowarn)
3393 tn = convert(FARG, n, tp, tn);
3394 }
3395 free(ln);
3396 return tn;
3397 }
3398
3399 /*
3400 * Return the value of an integral constant expression.
3401 * If the expression is not constant or its type is not an integer
3402 * type, an error message is printed.
3403 */
3404 val_t *
3405 constant(tnode_t *tn, int required)
3406 {
3407 val_t *v;
3408
3409 if (tn != NULL)
3410 tn = cconv(tn);
3411 if (tn != NULL)
3412 tn = promote(NOOP, 0, tn);
3413
3414 v = xcalloc(1, sizeof (val_t));
3415
3416 if (tn == NULL) {
3417 lint_assert(nerr != 0);
3418 v->v_tspec = INT;
3419 v->v_quad = 1;
3420 return v;
3421 }
3422
3423 v->v_tspec = tn->tn_type->t_tspec;
3424
3425 if (tn->tn_op == CON) {
3426 lint_assert(tn->tn_type->t_tspec == tn->tn_val->v_tspec);
3427 if (tspec_is_int(tn->tn_val->v_tspec)) {
3428 v->v_ansiu = tn->tn_val->v_ansiu;
3429 v->v_quad = tn->tn_val->v_quad;
3430 return v;
3431 }
3432 v->v_quad = tn->tn_val->v_ldbl;
3433 } else {
3434 v->v_quad = 1;
3435 }
3436
3437 /* integral constant expression expected */
3438 if (required)
3439 error(55);
3440 else
3441 c99ism(318);
3442
3443 if (!tspec_is_int(v->v_tspec))
3444 v->v_tspec = INT;
3445
3446 return v;
3447 }
3448
3449 /*
3450 * Perform some tests on expressions which can't be done in build() and
3451 * functions called by build(). These tests must be done here because
3452 * we need some information about the context in which the operations
3453 * are performed.
3454 * After all tests are performed, expr() frees the memory which is used
3455 * for the expression.
3456 */
3457 void
3458 expr(tnode_t *tn, int vctx, int tctx, int dofreeblk)
3459 {
3460
3461 lint_assert(tn != NULL || nerr != 0);
3462
3463 if (tn == NULL) {
3464 tfreeblk();
3465 return;
3466 }
3467
3468 /* expr() is also called in global initialisations */
3469 if (dcs->d_ctx != EXTERN)
3470 check_statement_reachable();
3471
3472 check_expr_misc(tn, vctx, tctx, !tctx, 0, 0, 0);
3473 if (tn->tn_op == ASSIGN) {
3474 if (hflag && tctx)
3475 /* assignment in conditional context */
3476 warning(159);
3477 } else if (tn->tn_op == CON) {
3478 if (hflag && tctx && !constcond_flag)
3479 /* constant in conditional context */
3480 warning(161);
3481 }
3482 if (!modtab[tn->tn_op].m_sideeff) {
3483 /*
3484 * for left operands of COMMA this warning is already
3485 * printed
3486 */
3487 if (tn->tn_op != COMMA && !vctx && !tctx)
3488 check_null_effect(tn);
3489 }
3490 if (dflag)
3491 display_expression(tn, 0);
3492
3493 /* free the tree memory */
3494 if (dofreeblk)
3495 tfreeblk();
3496 }
3497
3498 static void
3499 check_null_effect(tnode_t *tn)
3500 {
3501
3502 if (!hflag)
3503 return;
3504
3505 while (!modtab[tn->tn_op].m_sideeff) {
3506 if (tn->tn_op == CVT && tn->tn_type->t_tspec == VOID) {
3507 tn = tn->tn_left;
3508 } else if (tn->tn_op == LOGAND || tn->tn_op == LOGOR) {
3509 /*
3510 * && and || have a side effect if the right operand
3511 * has a side effect.
3512 */
3513 tn = tn->tn_right;
3514 } else if (tn->tn_op == QUEST) {
3515 /*
3516 * ? has a side effect if at least one of its right
3517 * operands has a side effect
3518 */
3519 tn = tn->tn_right;
3520 } else if (tn->tn_op == COLON || tn->tn_op == COMMA) {
3521 /*
3522 * : has a side effect if at least one of its operands
3523 * has a side effect
3524 */
3525 if (modtab[tn->tn_left->tn_op].m_sideeff) {
3526 tn = tn->tn_left;
3527 } else if (modtab[tn->tn_right->tn_op].m_sideeff) {
3528 tn = tn->tn_right;
3529 } else {
3530 break;
3531 }
3532 } else {
3533 break;
3534 }
3535 }
3536 if (!modtab[tn->tn_op].m_sideeff)
3537 /* expression has null effect */
3538 warning(129);
3539 }
3540
3541 /*
3542 * Dump an expression to stdout
3543 * only used for debugging
3544 */
3545 static void
3546 display_expression(tnode_t *tn, int offs)
3547 {
3548 uint64_t uq;
3549
3550 if (tn == NULL) {
3551 (void)printf("%*s%s\n", offs, "", "NULL");
3552 return;
3553 }
3554 (void)printf("%*sop %s ", offs, "", modtab[tn->tn_op].m_name);
3555
3556 if (tn->tn_op == NAME) {
3557 (void)printf("%s: %s ",
3558 tn->tn_sym->s_name,
3559 storage_class_name(tn->tn_sym->s_scl));
3560 } else if (tn->tn_op == CON && tspec_is_float(tn->tn_type->t_tspec)) {
3561 (void)printf("%#g ", (double)tn->tn_val->v_ldbl);
3562 } else if (tn->tn_op == CON && tspec_is_int(tn->tn_type->t_tspec)) {
3563 uq = tn->tn_val->v_quad;
3564 (void)printf("0x %08lx %08lx ",
3565 (long)(uq >> 32) & 0xffffffffl,
3566 (long)uq & 0xffffffffl);
3567 } else if (tn->tn_op == CON) {
3568 lint_assert(tn->tn_type->t_tspec == PTR);
3569 (void)printf("0x%0*lx ", (int)(sizeof (void *) * CHAR_BIT / 4),
3570 (u_long)tn->tn_val->v_quad);
3571 } else if (tn->tn_op == STRING) {
3572 if (tn->tn_string->st_tspec == CHAR) {
3573 (void)printf("\"%s\"", tn->tn_string->st_cp);
3574 } else {
3575 char *s;
3576 size_t n;
3577 n = MB_CUR_MAX * (tn->tn_string->st_len + 1);
3578 s = xmalloc(n);
3579 (void)wcstombs(s, tn->tn_string->st_wcp, n);
3580 (void)printf("L\"%s\"", s);
3581 free(s);
3582 }
3583 (void)printf(" ");
3584 } else if (tn->tn_op == FSEL) {
3585 (void)printf("o=%d, l=%d ", tn->tn_type->t_foffs,
3586 tn->tn_type->t_flen);
3587 }
3588 (void)printf("%s\n", ttos(tn->tn_type));
3589 if (tn->tn_op == NAME || tn->tn_op == CON || tn->tn_op == STRING)
3590 return;
3591 display_expression(tn->tn_left, offs + 2);
3592 if (modtab[tn->tn_op].m_binary ||
3593 (tn->tn_op == PUSH && tn->tn_right != NULL)) {
3594 display_expression(tn->tn_right, offs + 2);
3595 }
3596 }
3597
3598 /*
3599 * Called by expr() to recursively perform some tests.
3600 */
3601 /* ARGSUSED */
3602 void
3603 check_expr_misc(tnode_t *tn, int vctx, int tctx, int eqwarn, int fcall, int rvdisc,
3604 int szof)
3605 {
3606 tnode_t *ln, *rn;
3607 mod_t *mp;
3608 int nrvdisc, cvctx, ctctx;
3609 op_t op;
3610 scl_t sc;
3611 dinfo_t *di;
3612
3613 if (tn == NULL)
3614 return;
3615
3616 ln = tn->tn_left;
3617 rn = tn->tn_right;
3618 mp = &modtab[op = tn->tn_op];
3619
3620 switch (op) {
3621 case AMPER:
3622 if (ln->tn_op == NAME && (reached || rchflg)) {
3623 if (!szof)
3624 mark_as_set(ln->tn_sym);
3625 mark_as_used(ln->tn_sym, fcall, szof);
3626 }
3627 if (ln->tn_op == STAR && ln->tn_left->tn_op == PLUS)
3628 /* check the range of array indices */
3629 check_array_index(ln->tn_left, 1);
3630 break;
3631 case LOAD:
3632 if (ln->tn_op == STAR && ln->tn_left->tn_op == PLUS)
3633 /* check the range of array indices */
3634 check_array_index(ln->tn_left, 0);
3635 /* FALLTHROUGH */
3636 case PUSH:
3637 case INCBEF:
3638 case DECBEF:
3639 case INCAFT:
3640 case DECAFT:
3641 case ADDASS:
3642 case SUBASS:
3643 case MULASS:
3644 case DIVASS:
3645 case MODASS:
3646 case ANDASS:
3647 case ORASS:
3648 case XORASS:
3649 case SHLASS:
3650 case SHRASS:
3651 case REAL:
3652 case IMAG:
3653 if (ln->tn_op == NAME && (reached || rchflg)) {
3654 sc = ln->tn_sym->s_scl;
3655 /*
3656 * Look if there was a asm statement in one of the
3657 * compound statements we are in. If not, we don't
3658 * print a warning.
3659 */
3660 for (di = dcs; di != NULL; di = di->d_next) {
3661 if (di->d_asm)
3662 break;
3663 }
3664 if (sc != EXTERN && sc != STATIC &&
3665 !ln->tn_sym->s_set && !szof && di == NULL) {
3666 /* %s may be used before set */
3667 warning(158, ln->tn_sym->s_name);
3668 mark_as_set(ln->tn_sym);
3669 }
3670 mark_as_used(ln->tn_sym, 0, 0);
3671 }
3672 break;
3673 case ASSIGN:
3674 if (ln->tn_op == NAME && !szof && (reached || rchflg)) {
3675 mark_as_set(ln->tn_sym);
3676 if (ln->tn_sym->s_scl == EXTERN)
3677 outusg(ln->tn_sym);
3678 }
3679 if (ln->tn_op == STAR && ln->tn_left->tn_op == PLUS)
3680 /* check the range of array indices */
3681 check_array_index(ln->tn_left, 0);
3682 break;
3683 case CALL:
3684 if (ln->tn_op != AMPER || ln->tn_left->tn_op != NAME)
3685 LERROR("check_expr_misc(op=%s != %s || %s != %s)",
3686 getopname(ln->tn_op), getopname(AMPER),
3687 getopname(ln->tn_left->tn_op), getopname(NAME));
3688 if (!szof)
3689 outcall(tn, vctx || tctx, rvdisc);
3690 break;
3691 case EQ:
3692 /* equality operator "==" found where "=" was exp. */
3693 if (hflag && eqwarn)
3694 warning(160);
3695 break;
3696 case CON:
3697 case NAME:
3698 case STRING:
3699 return;
3700 /* LINTED206: (enumeration values not handled in switch) */
3701 case OR:
3702 case XOR:
3703 case NE:
3704 case GE:
3705 case GT:
3706 case LE:
3707 case LT:
3708 case SHR:
3709 case SHL:
3710 case MINUS:
3711 case PLUS:
3712 case MOD:
3713 case DIV:
3714 case MULT:
3715 case STAR:
3716 case UMINUS:
3717 case UPLUS:
3718 case DEC:
3719 case INC:
3720 case COMPL:
3721 case NOT:
3722 case POINT:
3723 case ARROW:
3724 case NOOP:
3725 case AND:
3726 case FARG:
3727 case CASE:
3728 case INIT:
3729 case RETURN:
3730 case ICALL:
3731 case CVT:
3732 case COMMA:
3733 case FSEL:
3734 case COLON:
3735 case QUEST:
3736 case LOGOR:
3737 case LOGAND:
3738 break;
3739 }
3740
3741 cvctx = mp->m_vctx;
3742 ctctx = mp->m_tctx;
3743 /*
3744 * values of operands of ':' are not used if the type of at least
3745 * one of the operands (for gcc compatibility) is void
3746 * XXX test/value context of QUEST should probably be used as
3747 * context for both operands of COLON
3748 */
3749 if (op == COLON && tn->tn_type->t_tspec == VOID)
3750 cvctx = ctctx = 0;
3751 nrvdisc = op == CVT && tn->tn_type->t_tspec == VOID;
3752 check_expr_misc(ln, cvctx, ctctx, mp->m_eqwarn, op == CALL, nrvdisc, szof);
3753
3754 switch (op) {
3755 case PUSH:
3756 if (rn != NULL)
3757 check_expr_misc(rn, 0, 0, mp->m_eqwarn, 0, 0, szof);
3758 break;
3759 case LOGAND:
3760 case LOGOR:
3761 check_expr_misc(rn, 0, 1, mp->m_eqwarn, 0, 0, szof);
3762 break;
3763 case COLON:
3764 check_expr_misc(rn, cvctx, ctctx, mp->m_eqwarn, 0, 0, szof);
3765 break;
3766 case COMMA:
3767 check_expr_misc(rn, vctx, tctx, mp->m_eqwarn, 0, 0, szof);
3768 break;
3769 default:
3770 if (mp->m_binary)
3771 check_expr_misc(rn, 1, 0, mp->m_eqwarn, 0, 0, szof);
3772 break;
3773 }
3774
3775 }
3776
3777 /*
3778 * Checks the range of array indices, if possible.
3779 * amper is set if only the address of the element is used. This
3780 * means that the index is allowed to refer to the first element
3781 * after the array.
3782 */
3783 static void
3784 check_array_index(tnode_t *tn, int amper)
3785 {
3786 int dim;
3787 tnode_t *ln, *rn;
3788 int elsz;
3789 int64_t con;
3790
3791 ln = tn->tn_left;
3792 rn = tn->tn_right;
3793
3794 /* We can only check constant indices. */
3795 if (rn->tn_op != CON)
3796 return;
3797
3798 /* Return if the left node does not stem from an array. */
3799 if (ln->tn_op != AMPER)
3800 return;
3801 if (ln->tn_left->tn_op != STRING && ln->tn_left->tn_op != NAME)
3802 return;
3803 if (ln->tn_left->tn_type->t_tspec != ARRAY)
3804 return;
3805
3806 /*
3807 * For incomplete array types, we can print a warning only if
3808 * the index is negative.
3809 */
3810 if (incompl(ln->tn_left->tn_type) && rn->tn_val->v_quad >= 0)
3811 return;
3812
3813 /* Get the size of one array element */
3814 if ((elsz = length(ln->tn_type->t_subt, NULL)) == 0)
3815 return;
3816 elsz /= CHAR_BIT;
3817
3818 /* Change the unit of the index from bytes to element size. */
3819 if (tspec_is_uint(rn->tn_type->t_tspec)) {
3820 con = (uint64_t)rn->tn_val->v_quad / elsz;
3821 } else {
3822 con = rn->tn_val->v_quad / elsz;
3823 }
3824
3825 dim = ln->tn_left->tn_type->t_dim + (amper ? 1 : 0);
3826
3827 if (!tspec_is_uint(rn->tn_type->t_tspec) && con < 0) {
3828 /* array subscript cannot be negative: %ld */
3829 warning(167, (long)con);
3830 } else if (dim > 0 && (uint64_t)con >= (uint64_t)dim) {
3831 /* array subscript cannot be > %d: %ld */
3832 warning(168, dim - 1, (long)con);
3833 }
3834 }
3835
3836 /*
3837 * Check for ordered comparisons of unsigned values with 0.
3838 */
3839 static void
3840 check_integer_comparison(op_t op, tnode_t *ln, tnode_t *rn)
3841 {
3842 char buf[64];
3843 tspec_t lt, rt;
3844 mod_t *mp;
3845
3846 lt = ln->tn_type->t_tspec;
3847 rt = rn->tn_type->t_tspec;
3848 mp = &modtab[op];
3849
3850 if (ln->tn_op != CON && rn->tn_op != CON)
3851 return;
3852
3853 if (!tspec_is_int(lt) || !tspec_is_int(rt))
3854 return;
3855
3856 if ((hflag || pflag) && lt == CHAR && rn->tn_op == CON &&
3857 (rn->tn_val->v_quad < 0 ||
3858 rn->tn_val->v_quad > (int)~(~0U << (CHAR_BIT - 1)))) {
3859 /* nonportable character comparison, op %s */
3860 warning(230, mp->m_name);
3861 return;
3862 }
3863 if ((hflag || pflag) && rt == CHAR && ln->tn_op == CON &&
3864 (ln->tn_val->v_quad < 0 ||
3865 ln->tn_val->v_quad > (int)~(~0U << (CHAR_BIT - 1)))) {
3866 /* nonportable character comparison, op %s */
3867 warning(230, mp->m_name);
3868 return;
3869 }
3870 if (tspec_is_uint(lt) && !tspec_is_uint(rt) &&
3871 rn->tn_op == CON && rn->tn_val->v_quad <= 0) {
3872 if (rn->tn_val->v_quad < 0) {
3873 /* comparison of %s with %s, op %s */
3874 warning(162, tyname(buf, sizeof(buf), ln->tn_type),
3875 "negative constant", mp->m_name);
3876 } else if (op == LT || op == GE || (hflag && op == LE)) {
3877 /* comparison of %s with %s, op %s */
3878 warning(162, tyname(buf, sizeof(buf), ln->tn_type),
3879 "0", mp->m_name);
3880 }
3881 return;
3882 }
3883 if (tspec_is_uint(rt) && !tspec_is_uint(lt) &&
3884 ln->tn_op == CON && ln->tn_val->v_quad <= 0) {
3885 if (ln->tn_val->v_quad < 0) {
3886 /* comparison of %s with %s, op %s */
3887 warning(162, "negative constant",
3888 tyname(buf, sizeof(buf), rn->tn_type), mp->m_name);
3889 } else if (op == GT || op == LE || (hflag && op == GE)) {
3890 /* comparison of %s with %s, op %s */
3891 warning(162, "0", tyname(buf, sizeof(buf), rn->tn_type),
3892 mp->m_name);
3893 }
3894 return;
3895 }
3896 }
3897
3898 /*
3899 * Takes an expression an returns 0 if this expression can be used
3900 * for static initialisation, otherwise -1.
3901 *
3902 * Constant initialisation expressions must be constant or an address
3903 * of a static object with an optional offset. In the first case,
3904 * the result is returned in *offsp. In the second case, the static
3905 * object is returned in *symp and the offset in *offsp.
3906 *
3907 * The expression can consist of PLUS, MINUS, AMPER, NAME, STRING and
3908 * CON. Type conversions are allowed if they do not change binary
3909 * representation (including width).
3910 */
3911 int
3912 conaddr(tnode_t *tn, sym_t **symp, ptrdiff_t *offsp)
3913 {
3914 sym_t *sym;
3915 ptrdiff_t offs1, offs2;
3916 tspec_t t, ot;
3917
3918 switch (tn->tn_op) {
3919 case MINUS:
3920 if (tn->tn_right->tn_op == CVT)
3921 return conaddr(tn->tn_right, symp, offsp);
3922 else if (tn->tn_right->tn_op != CON)
3923 return -1;
3924 /* FALLTHROUGH */
3925 case PLUS:
3926 offs1 = offs2 = 0;
3927 if (tn->tn_left->tn_op == CON) {
3928 offs1 = (ptrdiff_t)tn->tn_left->tn_val->v_quad;
3929 if (conaddr(tn->tn_right, &sym, &offs2) == -1)
3930 return -1;
3931 } else if (tn->tn_right->tn_op == CON) {
3932 offs2 = (ptrdiff_t)tn->tn_right->tn_val->v_quad;
3933 if (tn->tn_op == MINUS)
3934 offs2 = -offs2;
3935 if (conaddr(tn->tn_left, &sym, &offs1) == -1)
3936 return -1;
3937 } else {
3938 return -1;
3939 }
3940 *symp = sym;
3941 *offsp = offs1 + offs2;
3942 break;
3943 case AMPER:
3944 if (tn->tn_left->tn_op == NAME) {
3945 *symp = tn->tn_left->tn_sym;
3946 *offsp = 0;
3947 } else if (tn->tn_left->tn_op == STRING) {
3948 /*
3949 * If this would be the front end of a compiler we
3950 * would return a label instead of 0.
3951 */
3952 *offsp = 0;
3953 }
3954 break;
3955 case CVT:
3956 t = tn->tn_type->t_tspec;
3957 ot = tn->tn_left->tn_type->t_tspec;
3958 if ((!tspec_is_int(t) && t != PTR) ||
3959 (!tspec_is_int(ot) && ot != PTR)) {
3960 return -1;
3961 }
3962 #ifdef notdef
3963 /*
3964 * consider:
3965 * struct foo {
3966 * unsigned char a;
3967 * } f = {
3968 * (u_char)(u_long)(&(((struct foo *)0)->a))
3969 * };
3970 * since psize(u_long) != psize(u_char) this fails.
3971 */
3972 else if (psize(t) != psize(ot))
3973 return -1;
3974 #endif
3975 if (conaddr(tn->tn_left, symp, offsp) == -1)
3976 return -1;
3977 break;
3978 default:
3979 return -1;
3980 }
3981 return 0;
3982 }
3983
3984 /*
3985 * Concatenate two string constants.
3986 */
3987 strg_t *
3988 cat_strings(strg_t *strg1, strg_t *strg2)
3989 {
3990 size_t len1, len2, len;
3991
3992 if (strg1->st_tspec != strg2->st_tspec) {
3993 /* cannot concatenate wide and regular string literals */
3994 error(292);
3995 return strg1;
3996 }
3997
3998 len1 = strg1->st_len;
3999 len2 = strg2->st_len + 1; /* + NUL */
4000 len = len1 + len2;
4001
4002 #define COPY(F) \
4003 do { \
4004 strg1->F = xrealloc(strg1->F, len * sizeof(*strg1->F)); \
4005 (void)memcpy(strg1->F + len1, strg2->F, len2 * sizeof(*strg1->F)); \
4006 free(strg2->F); \
4007 } while (/*CONSTCOND*/0)
4008
4009 if (strg1->st_tspec == CHAR)
4010 COPY(st_cp);
4011 else
4012 COPY(st_wcp);
4013
4014 strg1->st_len = len - 1; /* - NUL */;
4015 free(strg2);
4016
4017 return strg1;
4018 }
4019
4020 /*
4021 * Print a warning if the given node has operands which should be
4022 * parenthesized.
4023 *
4024 * XXX Does not work if an operand is a constant expression. Constant
4025 * expressions are already folded.
4026 */
4027 static void
4028 check_precedence_confusion(tnode_t *tn)
4029 {
4030 tnode_t *ln, *rn;
4031 op_t lop, rop = NOOP;
4032 int lparn, rparn = 0;
4033 mod_t *mp;
4034 int dowarn;
4035
4036 if (!hflag)
4037 return;
4038
4039 mp = &modtab[tn->tn_op];
4040
4041 lparn = 0;
4042 for (ln = tn->tn_left; ln->tn_op == CVT; ln = ln->tn_left)
4043 lparn |= ln->tn_parenthesized;
4044 lparn |= ln->tn_parenthesized;
4045 lop = ln->tn_op;
4046
4047 if (mp->m_binary) {
4048 rparn = 0;
4049 for (rn = tn->tn_right; tn->tn_op == CVT; rn = rn->tn_left)
4050 rparn |= rn->tn_parenthesized;
4051 rparn |= rn->tn_parenthesized;
4052 rop = rn->tn_op;
4053 }
4054
4055 dowarn = 0;
4056
4057 switch (tn->tn_op) {
4058 case SHL:
4059 case SHR:
4060 if (!lparn && (lop == PLUS || lop == MINUS)) {
4061 dowarn = 1;
4062 } else if (!rparn && (rop == PLUS || rop == MINUS)) {
4063 dowarn = 1;
4064 }
4065 break;
4066 case LOGOR:
4067 if (!lparn && lop == LOGAND) {
4068 dowarn = 1;
4069 } else if (!rparn && rop == LOGAND) {
4070 dowarn = 1;
4071 }
4072 break;
4073 case AND:
4074 case XOR:
4075 case OR:
4076 if (!lparn && lop != tn->tn_op) {
4077 if (lop == PLUS || lop == MINUS) {
4078 dowarn = 1;
4079 } else if (lop == AND || lop == XOR) {
4080 dowarn = 1;
4081 }
4082 }
4083 if (!dowarn && !rparn && rop != tn->tn_op) {
4084 if (rop == PLUS || rop == MINUS) {
4085 dowarn = 1;
4086 } else if (rop == AND || rop == XOR) {
4087 dowarn = 1;
4088 }
4089 }
4090 break;
4091 /* LINTED206: (enumeration values not handled in switch) */
4092 case DECAFT:
4093 case XORASS:
4094 case SHLASS:
4095 case NOOP:
4096 case ARROW:
4097 case ORASS:
4098 case POINT:
4099 case NAME:
4100 case NOT:
4101 case COMPL:
4102 case CON:
4103 case INC:
4104 case STRING:
4105 case DEC:
4106 case INCBEF:
4107 case DECBEF:
4108 case INCAFT:
4109 case FSEL:
4110 case CALL:
4111 case COMMA:
4112 case CVT:
4113 case ICALL:
4114 case LOAD:
4115 case PUSH:
4116 case RETURN:
4117 case INIT:
4118 case CASE:
4119 case FARG:
4120 case SUBASS:
4121 case ADDASS:
4122 case MODASS:
4123 case DIVASS:
4124 case MULASS:
4125 case ASSIGN:
4126 case COLON:
4127 case QUEST:
4128 case LOGAND:
4129 case NE:
4130 case EQ:
4131 case GE:
4132 case GT:
4133 case LE:
4134 case LT:
4135 case MINUS:
4136 case PLUS:
4137 case MOD:
4138 case DIV:
4139 case MULT:
4140 case AMPER:
4141 case STAR:
4142 case UMINUS:
4143 case SHRASS:
4144 case UPLUS:
4145 case ANDASS:
4146 case REAL:
4147 case IMAG:
4148 break;
4149 }
4150
4151 if (dowarn) {
4152 /* precedence confusion possible: parenthesize! */
4153 warning(169);
4154 }
4155
4156 }
4157