-void exprhs (unsigned flags, int k, ExprDesc* lval)
+void exprhs (unsigned Flags, int k, ExprDesc* Expr)
/* Put the result of an expression into the primary register */
{
int f;
- f = lval->Flags;
+ f = Expr->Flags;
if (k) {
/* Dereferenced lvalue */
- flags |= TypeOf (lval->Type);
- if (lval->Test & E_FORCETEST) {
- flags |= CF_TEST;
- lval->Test &= ~E_FORCETEST;
+ Flags |= TypeOf (Expr->Type);
+ if (Expr->Test & E_FORCETEST) {
+ Flags |= CF_TEST;
+ Expr->Test &= ~E_FORCETEST;
}
- if (f & E_MGLOBAL) {
- /* Reference to a global variable */
- flags |= GlobalModeFlags (f);
- g_getstatic (flags, lval->Name, lval->ConstVal);
+ if (f & E_MGLOBAL) {
+ /* Reference to a global variable */
+ Flags |= GlobalModeFlags (f);
+ g_getstatic (Flags, Expr->Name, Expr->ConstVal);
} else if (f & E_MLOCAL) {
/* Reference to a local variable */
- g_getlocal (flags, lval->ConstVal);
+ g_getlocal (Flags, Expr->ConstVal);
} else if (f & E_MCONST) {
/* Reference to an absolute address */
- g_getstatic (flags | CF_ABSOLUTE, lval->ConstVal, 0);
+ g_getstatic (Flags | CF_ABSOLUTE, Expr->ConstVal, 0);
} else if (f == E_MEOFFS) {
- /* Reference to address in primary with offset in lval */
- g_getind (flags, lval->ConstVal);
+ /* Reference to address in primary with offset in Expr */
+ g_getind (Flags, Expr->ConstVal);
} else if (f != E_MREG) {
- /* Reference with address in primary */
- g_getind (flags, 0);
+ /* Reference with address in primary */
+ g_getind (Flags, 0);
}
} else {
- /* An rvalue */
- if (f == E_MEOFFS) {
- /* reference not storable */
- flags |= TypeOf (lval->Type);
- g_inc (flags | CF_CONST, lval->ConstVal);
- } else if ((f & E_MEXPR) == 0) {
- /* Constant of some sort, load it into the primary */
- LoadConstant (flags, lval);
- }
+ /* An rvalue */
+ if (f == E_MEOFFS) {
+ /* reference not storable */
+ Flags |= TypeOf (Expr->Type);
+ g_inc (Flags | CF_CONST, Expr->ConstVal);
+ } else if ((f & E_MEXPR) == 0) {
+ /* Constant of some sort, load it into the primary */
+ LoadConstant (Flags, Expr);
+ }
}
/* Are we testing this value? */
- if (lval->Test & E_FORCETEST) {
+ if (Expr->Test & E_FORCETEST) {
/* Yes, force a test */
- flags |= TypeOf (lval->Type);
- g_test (flags);
- lval->Test &= ~E_FORCETEST;
+ Flags |= TypeOf (Expr->Type);
+ g_test (Flags);
+ Expr->Test &= ~E_FORCETEST;
}
}
-static int hieQuest (ExprDesc *lval)
-/* Parse "lvalue ? exp : exp" */
+static int hieQuest (ExprDesc* lval)
+/* Parse the ternary operator */
{
- int k1, k2, k3;
- int labf;
- int labt;
- ExprDesc lval2; /* Expression 2 */
- ExprDesc lval3; /* Expression 3 */
- type* rtype; /* Type of result */
+ int k1, k2, k3;
+ int labf;
+ int labt;
+ ExprDesc Expr2; /* Expression 2 */
+ ExprDesc Expr3; /* Expression 3 */
+ int Expr2IsNULL; /* Expression 2 is a NULL pointer */
+ int Expr3IsNULL; /* Expression 3 is a NULL pointer */
+ type* ResultType; /* Type of result */
k1 = Preprocessing? hieOrPP (lval) : hieOr (lval);
labf = GetLocalLabel ();
g_falsejump (CF_NONE, labf);
- /* Parse second expression */
- k2 = expr (hie1, &lval2);
- if (!IsTypeVoid (lval2.Type)) {
+ /* Parse second expression. Remember for later if it is a NULL pointer
+ * expression, then load it into the primary.
+ */
+ k2 = expr (hie1, &Expr2);
+ Expr2IsNULL = IsNullPtr (&Expr2);
+ if (!IsTypeVoid (Expr2.Type)) {
/* Load it into the primary */
- exprhs (CF_NONE, k2, &lval2);
- lval2.Flags = E_MEXPR;
+ exprhs (CF_NONE, k2, &Expr2);
+ Expr2.Flags = E_MEXPR;
k2 = 0;
}
labt = GetLocalLabel ();
ConsumeColon ();
g_jump (labt);
- /* Parse the third expression */
+ /* Jump here if the first expression was false */
g_defcodelabel (labf);
- k3 = expr (hie1, &lval3);
- if (!IsTypeVoid (lval3.Type)) {
+
+ /* Parse second expression. Remember for later if it is a NULL pointer
+ * expression, then load it into the primary.
+ */
+ k3 = expr (hie1, &Expr3);
+ Expr3IsNULL = IsNullPtr (&Expr3);
+ if (!IsTypeVoid (Expr3.Type)) {
/* Load it into the primary */
- exprhs (CF_NONE, k3, &lval3);
- lval3.Flags = E_MEXPR;
+ exprhs (CF_NONE, k3, &Expr3);
+ Expr3.Flags = E_MEXPR;
k3 = 0;
}
* type void.
* - all other cases are flagged by an error.
*/
- if (IsClassInt (lval2.Type) && IsClassInt (lval3.Type)) {
+ if (IsClassInt (Expr2.Type) && IsClassInt (Expr3.Type)) {
/* Get common type */
- rtype = promoteint (lval2.Type, lval3.Type);
+ ResultType = promoteint (Expr2.Type, Expr3.Type);
/* Convert the third expression to this type if needed */
- TypeConversion (&lval3, k3, rtype);
+ TypeConversion (&Expr3, k3, ResultType);
/* Setup a new label so that the expr3 code will jump around
* the type cast code for expr2.
g_defcodelabel (labt);
/* Create the typecast code for expr2 */
- TypeConversion (&lval2, k2, rtype);
+ TypeConversion (&Expr2, k2, ResultType);
/* Jump here around the typecase code. */
g_defcodelabel (labf);
labt = 0; /* Mark other label as invalid */
- } else if (IsClassPtr (lval2.Type) && IsClassPtr (lval3.Type)) {
+ } else if (IsClassPtr (Expr2.Type) && IsClassPtr (Expr3.Type)) {
/* Must point to same type */
- if (TypeCmp (Indirect (lval2.Type), Indirect (lval3.Type)) < TC_EQUAL) {
+ if (TypeCmp (Indirect (Expr2.Type), Indirect (Expr3.Type)) < TC_EQUAL) {
Error ("Incompatible pointer types");
}
/* Result has the common type */
- rtype = lval2.Type;
- } else if (IsClassPtr (lval2.Type) && IsNullPtr (&lval3)) {
+ ResultType = Expr2.Type;
+ } else if (IsClassPtr (Expr2.Type) && Expr3IsNULL) {
/* Result type is pointer, no cast needed */
- rtype = lval2.Type;
- } else if (IsNullPtr (&lval2) && IsClassPtr (lval3.Type)) {
+ ResultType = Expr2.Type;
+ } else if (Expr2IsNULL && IsClassPtr (Expr3.Type)) {
/* Result type is pointer, no cast needed */
- rtype = lval3.Type;
- } else if (IsTypeVoid (lval2.Type) && IsTypeVoid (lval3.Type)) {
+ ResultType = Expr3.Type;
+ } else if (IsTypeVoid (Expr2.Type) && IsTypeVoid (Expr3.Type)) {
/* Result type is void */
- rtype = lval3.Type;
+ ResultType = Expr3.Type;
} else {
Error ("Incompatible types");
- rtype = lval2.Type; /* Doesn't matter here */
+ ResultType = Expr2.Type; /* Doesn't matter here */
}
/* If we don't have the label defined until now, do it */
/* Setup the target expression */
lval->Flags = E_MEXPR;
- lval->Type = rtype;
+ lval->Type = ResultType;
k1 = 0;
}
return k1;
} else {
/* Not constant, load into the primary */
exprhs (CF_NONE, k, &lval2);
- lval2.Flags = E_MEXPR;
- k = 0;
if (MustScale) {
/* lhs is a pointer, scale rhs */
g_scale (TypeOf (lval2.Type), CheckedSizeOf (lval->Type+1));
rflags |= TypeOf (lval2.Type);
/* Convert the type of the lhs to that of the rhs */
- TypeConversion (&lval2, k, lval->Type);
+ g_typecast (lflags, rflags);
/* Output apropriate code */
if (lval->Flags & E_MGLOBAL) {