corrected the treatment of the <<= and >>= operators
authorerikb <none@none>
Wed, 10 Sep 1986 10:23:26 +0000 (10:23 +0000)
committererikb <none@none>
Wed, 10 Sep 1986 10:23:26 +0000 (10:23 +0000)
lang/cem/cemcom/ch7.c
lang/cem/cemcom/ch7bin.c
lang/cem/cemcom/eval.c

index d73052f..0cb13fb 100644 (file)
@@ -324,6 +324,7 @@ ch7asgn(expp, oper, expr)
                EVAL should however take care of evaluating (typeof (f op e))f
        */
        int fund = (*expp)->ex_type->tp_fund;
+       struct type *tp;
 
        /* We expect an lvalue */
        if (!(*expp)->ex_lvalue)        {
@@ -333,6 +334,7 @@ ch7asgn(expp, oper, expr)
        }
        if (oper == '=') {
                ch7cast(&expr, oper, (*expp)->ex_type);
+               tp = expr->ex_type;
        }
        else {  /* turn e into e' where typeof(e') = typeof (f op e) */
                struct expr *extmp = intexpr((arith)0, INT);
@@ -341,13 +343,14 @@ ch7asgn(expp, oper, expr)
                extmp->ex_lvalue = 1;
                extmp->ex_type = (*expp)->ex_type;
                ch7bin(&extmp, oper, expr);
-               /* note that ch7bin creates a tree of the expression
+               /* Note that ch7bin creates a tree of the expression
                        ((typeof (f op e))f op (typeof (f op e))e),
-                  where f ~ extmp and e ~ expr;
-                  we have to use (typeof (f op e))e
+                  where f ~ extmp and e ~ expr.
+                  We want to use (typeof (f op e))e.
                   Ch7bin does not create a tree if both operands
                   were illegal or constants!
                */
+               tp = extmp->ex_type;    /* perform the arithmetic in type tp */
                if (extmp->ex_class == Oper) {
                        expr = extmp->OP_RIGHT;
                        extmp->OP_RIGHT = NILEXPR;
@@ -356,13 +359,17 @@ ch7asgn(expp, oper, expr)
                else
                        expr = extmp;
        }
+
 #ifndef NOBITFIELD
        if (fund == FIELD)
                *expp = new_oper((*expp)->ex_type->tp_up, *expp, oper, expr);
        else
-#endif NOBITFIELD
                *expp = new_oper((*expp)->ex_type, *expp, oper, expr);
-       (*expp)->OP_TYPE = expr->ex_type;       /* for EVAL() */
+#else NOBITFIELD
+       *expp = new_oper((*expp)->ex_type, *expp, oper, expr);
+#endif NOBITFIELD
+
+       (*expp)->OP_TYPE = tp;  /* for EVAL() */
 }
 
 /*     Some interesting (?) questions answered.
index 970e8b7..c34e1c2 100644 (file)
@@ -156,7 +156,8 @@ ch7bin(expp, oper, expr)
        case RIGHTAB:
                opnd2integral(expp, oper);
                opnd2integral(&expr, oper);
-               ch7cast(&expr, oper, int_type); /* leftop should be int */
+               fund = arithbalance(expp, oper, &expr); /* ch. 7.5 */
+               ch7cast(&expr, oper, int_type); /* cvt. rightop to int */
                non_commutative_binop(expp, oper, expr);
                break;
        case '<':
index 2ce3f82..ac14d2d 100644 (file)
@@ -35,7 +35,7 @@
 #include       "atw.h"
 
 #define        CRASH()         crash("EVAL: CRASH at line %u", __LINE__)
-#define        roundup(n)      ((n) < word_size ? word_size : (n))
+#define        toword(n)       ((n) < word_size ? word_size : (n))
 
 char *symbol2str();
 char *long2str();
@@ -374,6 +374,10 @@ EVAL(expr, val, code, true_label, false_label)
                case ANDAB:
                case XORAB:
                case ORAB:
+               {
+                       arith old_offset;
+                       arith tmpvar = tmp_pointer_var(&old_offset);
+
 #ifndef NOBITFIELD
                        if (leftop->ex_type->tp_fund == FIELD)  {
                                eval_field(expr, code);
@@ -381,34 +385,29 @@ EVAL(expr, val, code, true_label, false_label)
                        }
 #endif NOBITFIELD
                        if (leftop->ex_class != Value) {
-                               arith old_offset;
-                               arith tmpvar = tmp_pointer_var(&old_offset);
-
                                EVAL(leftop, LVAL, TRUE, NO_LABEL, NO_LABEL);
                                C_lal(tmpvar);
                                C_sti(pointer_size);
                                C_lal(tmpvar);
                                C_loi(pointer_size);
                                C_loi(leftop->ex_type->tp_size);
-                               conversion(leftop->ex_type, tp);
-                               EVAL(rightop, RVAL, TRUE, NO_LABEL, NO_LABEL);
-                               assop(tp, oper);
-                               conversion(tp, leftop->ex_type);
-                               if (gencode)
-                                       C_dup(roundup(leftop->ex_type->tp_size));
+                       }
+                       else    {
+                               load_val(leftop, RVAL);
+                       }
+                       conversion(leftop->ex_type, tp);
+                       EVAL(rightop, RVAL, TRUE, NO_LABEL, NO_LABEL);
+                       assop(tp, oper);
+                       conversion(tp, leftop->ex_type);
+                       if (gencode)
+                               C_dup(toword(leftop->ex_type->tp_size));
+                       if (leftop->ex_class != Value) {
                                C_lal(tmpvar);
                                C_loi(pointer_size);
                                C_sti(leftop->ex_type->tp_size);
                                free_tmp_var(old_offset);
                        }
-                       else    {
-                               load_val(leftop, RVAL);
-                               conversion(leftop->ex_type, tp);
-                               EVAL(rightop, RVAL, TRUE, NO_LABEL, NO_LABEL);
-                               assop(tp, oper);
-                               conversion(tp, leftop->ex_type);
-                               if (gencode)
-                                       C_dup(roundup(leftop->ex_type->tp_size));
+                       else {
                                store_val(
                                        &(leftop->ex_object.ex_value),
                                        leftop->ex_type
@@ -417,6 +416,7 @@ EVAL(expr, val, code, true_label, false_label)
                        if (gencode)
                                conversion(leftop->ex_type, expr->ex_type);
                        break;
+               }
                case '(':
                {
                        register struct expr *expr;