2 * (c) copyright 1987 by the Vrije Universiteit, Amsterdam, The Netherlands.
3 * See the copyright notice in the ACK home directory, in the file "Copyright".
5 /* $Id: ch3bin.c,v 1.21 1994/06/27 07:58:33 ceriel Exp $ */
6 /* SEMANTIC ANALYSIS (CHAPTER 3.3) -- BINARY OPERATORS */
8 #include "botch_free.h"
13 #include <flt_arith.h>
22 extern char options[];
23 extern char *symbol2str();
25 /* This chapter asks for the repeated application of code to handle
26 an operation that may be executed at compile time or at run time,
27 depending on the constancy of the operands.
31 * Although the relational operators are generally not commutative, we can
32 * switch the arguments if the operator is adapted (e.g. < becomes >)
34 #define non_commutative_binop(expp, oper, expr) mk_binop(expp, oper, expr, 0)
35 #define commutative_binop(expp, oper, expr) mk_binop(expp, oper, expr, 1)
36 #define non_commutative_relop(expp, oper, expr) mk_binop(expp, oper, expr, 1)
38 ch3bin(expp, oper, expr)
39 register struct expr **expp;
42 /* apply binary operator oper between *expp and expr.
43 NB: don't swap operands if op is one of the op= operators!!!
45 register struct type *expp_tp;
48 expp_tp = (*expp)->ex_type;
49 /* expp_tp can never be ARRAY, since any2opnd() converts the type
50 * to pointer (except for SIZEOF and unary &).
52 any2opnd(&expr, oper);
54 case '[': /* 3.3.2.1 */
55 /* indexing follows the commutative laws */
56 switch (expp_tp->tp_fund) {
61 default: /* unindexable */
62 switch (expr->ex_type->tp_fund) {
69 "indexing an object of type %s",
70 symbol2str(expp_tp->tp_fund));
75 ch3bin(expp, '+', expr);
79 case '(': /* 3.3.2.2 */
80 if (expp_tp->tp_fund == POINTER
81 && expp_tp->tp_up->tp_fund == FUNCTION) {
83 expp_tp = (*expp)->ex_type;
85 if (expp_tp->tp_fund != FUNCTION) {
86 expr_error(*expp, "call of non-function (%s)",
87 symbol2str(expp_tp->tp_fund));
88 /* leave the expression; it may still serve */
89 free_expression(expr); /* there go the parameters */
90 *expp = new_oper(error_type,
91 *expp, '(', (struct expr *)0);
94 *expp = new_oper(expp_tp->tp_up, *expp, '(', expr);
95 (*expp)->ex_flags |= EX_SIDEEFFECTS;
98 case PARCOMMA: /* 3.3.2.2 */
99 *expp = new_oper(expr->ex_type, *expp, PARCOMMA, expr);
107 opnd2integral(expp, oper);
108 opnd2integral(&expr, oper);
113 arithbalance(expp, oper, &expr);
114 non_commutative_binop(expp, oper, expr);
120 opnd2integral(expp, oper);
121 opnd2integral(&expr, oper);
124 arithbalance(expp, oper, &expr);
125 commutative_binop(expp, oper, expr);
129 if (expr->ex_type->tp_fund == POINTER) { /* swap operands */
130 struct expr *etmp = expr;
131 expp_tp = expr->ex_type; /* both in registers */
139 if (expp_tp->tp_fund == POINTER) {
140 pointer_arithmetic(expp, oper, &expr);
141 if (expr->ex_type->tp_size != (*expp)->ex_type->tp_size)
142 ch3cast(&expr, CAST, (*expp)->ex_type);
143 pointer_binary(expp, oper, expr);
146 arithbalance(expp, oper, &expr);
148 commutative_binop(expp, oper, expr);
150 non_commutative_binop(expp, oper, expr);
158 if (expp_tp->tp_fund == POINTER) {
159 if (expr->ex_type->tp_fund == POINTER)
160 pntminuspnt(expp, oper, expr);
162 pointer_arithmetic(expp, oper, &expr);
163 pointer_binary(expp, oper, expr);
167 arithbalance(expp, oper, &expr);
168 non_commutative_binop(expp, oper, expr);
176 opnd2integral(expp, oper);
177 opnd2integral(&expr, oper);
178 arithbalance(expp, oper, &expr); /* ch. 3.3.7 */
179 ch3cast(&expr, oper, int_type); /* cvt. rightop to int */
180 non_commutative_binop(expp, oper, expr);
189 relbalance(expp, oper, &expr);
190 non_commutative_relop(expp, oper, expr);
191 (*expp)->ex_type = int_type;
196 opnd2test(expp, oper);
197 opnd2test(&expr, oper);
198 if (is_cp_cst(*expp)) {
199 register struct expr *ex = *expp;
201 /* the following condition is a short-hand for
202 ((oper == AND) && o1) || ((oper == OR) && !o1)
203 where o1 == (*expp)->VL_VALUE;
204 and ((oper == AND) || (oper == OR))
206 if ((oper == AND) == (ex->VL_VALUE != (arith)0)) {
210 ex->ex_flags |= expr->ex_flags;
211 free_expression(expr);
212 *expp = intexpr((arith)(oper != AND), INT);
214 (*expp)->ex_flags |= ex->ex_flags | EX_ILVALUE;
218 if (is_cp_cst(expr)) {
219 /* Note!!!: the following condition is a short-hand for
220 ((oper == AND) && o2) || ((oper == OR) && !o2)
221 where o2 == expr->VL_VALUE
222 and ((oper == AND) || (oper == OR))
224 if ((oper == AND) == (expr->VL_VALUE != (arith)0)) {
225 (*expp)->ex_flags |= expr->ex_flags | EX_ILVALUE;
226 free_expression(expr);
230 expr->VL_VALUE = (arith)1;
231 ch3bin(expp, ',', expr);
235 *expp = new_oper(int_type, *expp, oper, expr);
237 (*expp)->ex_flags |= EX_LOGICAL;
241 if (is_struct_or_union(expp_tp->tp_fund)
242 || is_struct_or_union(expr->ex_type->tp_fund)) {
243 if (!equal_type(expp_tp, expr->ex_type, -1, 0))
244 expr_error(*expp, "illegal balance");
247 relbalance(expp, oper, &expr);
249 if ( (is_cp_cst(*expp) && is_cp_cst(expr))
250 && (*expp)->VL_VALUE == expr->VL_VALUE
252 hwarning("operands of : are constant and equal");
255 *expp = new_oper((*expp)->ex_type, *expp, oper, expr);
259 opnd2logical(expp, oper);
260 if (is_cp_cst(*expp)) {
262 hwarning("condition in ?: expression is constant");
264 if ((*expp)->VL_VALUE) {
265 free_expression(*expp);
266 free_expression(expr->OP_RIGHT);
267 *expp = expr->OP_LEFT;
270 free_expression(*expp);
271 free_expression(expr->OP_LEFT);
272 *expp = expr->OP_RIGHT;
275 (*expp)->ex_flags |= EX_ILVALUE;
278 *expp = new_oper(expr->ex_type, *expp, oper, expr);
283 if (is_cp_cst(*expp)) {
285 hwarning("constant expression ignored");
287 free_expression(*expp);
291 *expp = new_oper(expr->ex_type, *expp, oper, expr);
293 (*expp)->ex_flags |= EX_COMMA;
298 pntminuspnt(expp, oper, expr)
299 register struct expr **expp, *expr;
301 /* Subtracting two pointers is so complicated it merits a
304 struct type *up_type = (*expp)->ex_type->tp_up;
306 if (!equal_type(up_type, expr->ex_type->tp_up, -1, 0)) {
307 expr_error(*expp, "subtracting incompatible pointers");
308 free_expression(expr);
312 /* we hope the optimizer will eliminate the load-time
315 *expp = new_oper((*expp)->ex_type, *expp, oper, expr);
316 ch3cast(expp, CAST, pa_type); /* ptr-ptr: result has pa_type */
318 , intexpr(size_of_type(up_type, symbol2str(up_type->tp_fund))
319 , pa_type->tp_fund));
320 ch3cast(expp, CAST, pa_type); /* result will be an integral expr */
321 /* cast necessary ??? */
322 if (int_size != pointer_size) (*expp)->ex_flags |= EX_PTRDIFF;
326 * The function arg_switched() returns the operator that should be used
327 * when the arguments are switched. This is special for some relational
334 case '<': return '>';
335 case '>': return '<';
336 case LESSEQ: return GREATEREQ;
337 case GREATEREQ: return LESSEQ;
338 default: return oper;
342 mk_binop(expp, oper, expr, commutative)
344 register struct expr *expr;
346 /* Constructs in *expp the operation indicated by the operands.
347 "commutative" indicates whether "oper" is a commutative
350 register struct expr *ex = *expp;
352 if (is_cp_cst(expr) && is_cp_cst(ex))
353 cstbin(expp, oper, expr);
354 else if (is_fp_cst(expr) && is_fp_cst(ex))
355 fltcstbin(expp, oper, expr);
358 && !(ex->ex_flags & EX_VOLATILE)
359 && (expr->ex_depth > ex->ex_depth
360 || ((expr->ex_flags & EX_SIDEEFFECTS)
361 && !(ex->ex_flags & EX_SIDEEFFECTS))
363 ? new_oper(ex->ex_type, expr, arg_switched(oper), ex)
364 : new_oper(ex->ex_type, ex, oper, expr);
368 pointer_arithmetic(expp1, oper, expp2)
369 register struct expr **expp1, **expp2;
372 /* prepares the integral expression expp2 in order to
373 apply it to the pointer expression expp1
375 if ((typ = any2arith(expp2, oper)) == FLOAT
379 "illegal combination of %s and pointer",
381 erroneous2int(expp2);
384 intexpr(size_of_type((*expp1)->ex_type->tp_up, "object"),
389 pointer_binary(expp, oper, expr)
390 register struct expr **expp, *expr;
392 /* constructs the pointer arithmetic expression out of
393 a pointer expression, a binary operator and an integral
396 if (is_ld_cst(expr) && is_ld_cst(*expp))
397 cstbin(expp, oper, expr);
399 *expp = new_oper((*expp)->ex_type, *expp, oper, expr);