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