1
0
mirror of https://github.com/cc65/cc65.git synced 2025-01-10 19:29:45 +00:00

Fixed a code generation bug

git-svn-id: svn://svn.cc65.org/cc65/trunk@1215 b7a2c559-68d2-44c3-8de9-860c34a00d81
This commit is contained in:
cuz 2002-04-06 14:51:27 +00:00
parent ad1951c068
commit c6fe12ef6b
7 changed files with 198 additions and 136 deletions

View File

@ -224,7 +224,7 @@ const char* MakeHexArg (unsigned Num)
*/ */
{ {
static char Buf[16]; static char Buf[16];
xsprintf (Buf, sizeof (Buf), "$%02X", (char) Num); xsprintf (Buf, sizeof (Buf), "$%02X", (unsigned char) Num);
return Buf; return Buf;
} }
@ -376,6 +376,46 @@ int CE_KnownImm (const CodeEntry* E)
int CE_UseLoadFlags (const CodeEntry* E)
/* Return true if the instruction uses any flags that are set by a load of
* a register (N and Z).
*/
{
/* A branch will use the flags */
if (E->Info & OF_FBRA) {
return 1;
}
/* Call of a boolean transformer routine will also use the flags */
if (E->OPC == OP65_JSR) {
/* Get the condition that is evaluated and check it */
switch (FindBoolCmpCond (E->Arg)) {
case CMP_EQ:
case CMP_NE:
case CMP_GT:
case CMP_GE:
case CMP_LT:
case CMP_LE:
case CMP_UGT:
case CMP_ULE:
case CMP_INV:
/* Will use the N or Z flags */
return 1;
case CMP_UGE: /* Uses only carry */
case CMP_ULT: /* Dito */
default: /* No bool transformer subroutine */
return 0;
}
}
/* Anything else */
return 0;
}
void CE_FreeRegInfo (CodeEntry* E) void CE_FreeRegInfo (CodeEntry* E)
/* Free an existing register info struct */ /* Free an existing register info struct */
{ {

View File

@ -196,6 +196,11 @@ INLINE int CE_IsCall (const CodeEntry* E, const char* Name)
# define CE_IsCall(E, Name) ((E)->OPC == OP65_JSR && strcmp ((E)->Arg, (Name)) == 0) # define CE_IsCall(E, Name) ((E)->OPC == OP65_JSR && strcmp ((E)->Arg, (Name)) == 0)
#endif #endif
int CE_UseLoadFlags (const CodeEntry* E);
/* Return true if the instruction uses any flags that are set by a load of
* a register (N and Z).
*/
void CE_FreeRegInfo (CodeEntry* E); void CE_FreeRegInfo (CodeEntry* E);
/* Free an existing register info struct */ /* Free an existing register info struct */

View File

@ -56,6 +56,11 @@
/* Table with the compare suffixes */
static const char CmpSuffixTab [][4] = {
"eq", "ne", "gt", "ge", "lt", "le", "ugt", "uge", "ult", "ule"
};
/* Table listing the function names and code info values for known internally /* Table listing the function names and code info values for known internally
* used functions. This table should get auto-generated in the future. * used functions. This table should get auto-generated in the future.
*/ */
@ -584,3 +589,59 @@ unsigned GetKnownReg (unsigned Use, const RegContents* RC)
static cmp_t FindCmpCond (const char* Code, unsigned CodeLen)
/* Search for a compare condition by the given code using the given length */
{
unsigned I;
/* Linear search */
for (I = 0; I < sizeof (CmpSuffixTab) / sizeof (CmpSuffixTab [0]); ++I) {
if (strncmp (Code, CmpSuffixTab [I], CodeLen) == 0) {
/* Found */
return I;
}
}
/* Not found */
return CMP_INV;
}
cmp_t FindBoolCmpCond (const char* Name)
/* Check if the given string is the name of one of the boolean transformer
* subroutine, and if so, return the condition that is evaluated by this
* routine. Return CMP_INV if the condition is not recognised.
*/
{
/* Check for the correct subroutine name */
if (strncmp (Name, "bool", 4) == 0) {
/* Name is ok, search for the code in the table */
return FindCmpCond (Name+4, strlen(Name)-4);
} else {
/* Not found */
return CMP_INV;
}
}
cmp_t FindTosCmpCond (const char* Name)
/* Check if this is a call to one of the TOS compare functions (tosgtax).
* Return the condition code or CMP_INV on failure.
*/
{
unsigned Len = strlen (Name);
/* Check for the correct subroutine name */
if (strncmp (Name, "tos", 3) == 0 && strcmp (Name+Len-2, "ax") == 0) {
/* Name is ok, search for the code in the table */
return FindCmpCond (Name+3, Len-3-2);
} else {
/* Not found */
return CMP_INV;
}
}

View File

@ -103,6 +103,23 @@ struct ZPInfo {
/* Defines for the conditions in a compare */
typedef enum {
CMP_INV = -1,
CMP_EQ,
CMP_NE,
CMP_GT,
CMP_GE,
CMP_LT,
CMP_LE,
CMP_UGT,
CMP_UGE,
CMP_ULT,
CMP_ULE
} cmp_t;
/*****************************************************************************/ /*****************************************************************************/
/* Code */ /* Code */
/*****************************************************************************/ /*****************************************************************************/
@ -143,6 +160,17 @@ unsigned GetKnownReg (unsigned Use, const struct RegContents* RC);
* register in question does not have a known value, return REG_NONE. * register in question does not have a known value, return REG_NONE.
*/ */
cmp_t FindBoolCmpCond (const char* Name);
/* Check if the given string is the name of one of the boolean transformer
* subroutine, and if so, return the condition that is evaluated by this
* routine. Return CMP_INV if the condition is not recognised.
*/
cmp_t FindTosCmpCond (const char* Name);
/* Check if this is a call to one of the TOS compare functions (tosgtax).
* Return the condition code or CMP_INV on failure.
*/
/* End of codeinfo.h */ /* End of codeinfo.h */

View File

@ -49,26 +49,6 @@
/* Defines for the conditions in a compare */
typedef enum {
CMP_INV = -1,
CMP_EQ,
CMP_NE,
CMP_GT,
CMP_GE,
CMP_LT,
CMP_LE,
CMP_UGT,
CMP_UGE,
CMP_ULT,
CMP_ULE
} cmp_t;
/* Table with the compare suffixes */
static const char CmpSuffixTab [][4] = {
"eq", "ne", "gt", "ge", "lt", "le", "ugt", "uge", "ult", "ule"
};
/* Table used to invert a condition, indexed by condition */ /* Table used to invert a condition, indexed by condition */
static const unsigned char CmpInvertTab [] = { static const unsigned char CmpInvertTab [] = {
CMP_NE, CMP_EQ, CMP_NE, CMP_EQ,
@ -89,59 +69,6 @@ static const char CmpSignedTab [] = {
static cmp_t FindCmpCond (const char* Code, unsigned CodeLen)
/* Search for a compare condition by the given code using the given length */
{
unsigned I;
/* Linear search */
for (I = 0; I < sizeof (CmpSuffixTab) / sizeof (CmpSuffixTab [0]); ++I) {
if (strncmp (Code, CmpSuffixTab [I], CodeLen) == 0) {
/* Found */
return I;
}
}
/* Not found */
return CMP_INV;
}
static cmp_t FindBoolCmpCond (const char* Name)
/* Map a condition suffix to a code. Return the code or CMP_INV on failure */
{
/* Check for the correct subroutine name */
if (strncmp (Name, "bool", 4) == 0) {
/* Name is ok, search for the code in the table */
return FindCmpCond (Name+4, strlen(Name)-4);
} else {
/* Not found */
return CMP_INV;
}
}
static cmp_t FindTosCmpCond (const char* Name)
/* Check if this is a call to one of the TOS compare functions (tosgtax).
* Return the condition code or CMP_INV on failure.
*/
{
unsigned Len = strlen (Name);
/* Check for the correct subroutine name */
if (strncmp (Name, "tos", 3) == 0 && strcmp (Name+Len-2, "ax") == 0) {
/* Name is ok, search for the code in the table */
return FindCmpCond (Name+3, Len-3-2);
} else {
/* Not found */
return CMP_INV;
}
}
static void ReplaceCmp (CodeSeg* S, unsigned I, cmp_t Cond) static void ReplaceCmp (CodeSeg* S, unsigned I, cmp_t Cond)
/* Helper function for the replacement of routines that return a boolean /* Helper function for the replacement of routines that return a boolean
* followed by a conditional jump. Instead of the boolean value, the condition * followed by a conditional jump. Instead of the boolean value, the condition

View File

@ -655,7 +655,7 @@ unsigned OptCondBranches (CodeSeg* S)
/*****************************************************************************/ /*****************************************************************************/
/* Remove unused loads and stores */ /* Remove unused loads and stores */
/*****************************************************************************/ /*****************************************************************************/
@ -675,24 +675,24 @@ unsigned OptUnusedLoads (CodeSeg* S)
CodeEntry* E = CS_GetEntry (S, I); CodeEntry* E = CS_GetEntry (S, I);
/* Check if it's a register load or transfer insn */ /* Check if it's a register load or transfer insn */
if ((E->Info & (OF_LOAD | OF_XFR | OF_REG_INCDEC)) != 0 && if ((E->Info & (OF_LOAD | OF_XFR | OF_REG_INCDEC)) != 0 &&
(N = CS_GetNextEntry (S, I)) != 0 && (N = CS_GetNextEntry (S, I)) != 0 &&
(N->Info & OF_FBRA) == 0) { !CE_UseLoadFlags (N)) {
/* Check which sort of load or transfer it is */ /* Check which sort of load or transfer it is */
unsigned R; unsigned R;
switch (E->OPC) { switch (E->OPC) {
case OP65_DEA: case OP65_DEA:
case OP65_INA: case OP65_INA:
case OP65_LDA: case OP65_LDA:
case OP65_TXA: case OP65_TXA:
case OP65_TYA: R = REG_A; break; case OP65_TYA: R = REG_A; break;
case OP65_DEX: case OP65_DEX:
case OP65_INX: case OP65_INX:
case OP65_LDX: case OP65_LDX:
case OP65_TAX: R = REG_X; break; case OP65_TAX: R = REG_X; break;
case OP65_DEY: case OP65_DEY:
case OP65_INY: case OP65_INY:
case OP65_LDY: case OP65_LDY:
case OP65_TAY: R = REG_Y; break; case OP65_TAY: R = REG_Y; break;
default: goto NextEntry; /* OOPS */ default: goto NextEntry; /* OOPS */
@ -799,7 +799,7 @@ unsigned OptDupLoads (CodeSeg* S)
CE_KnownImm (E) && /* Value to be loaded is known */ CE_KnownImm (E) && /* Value to be loaded is known */
In->RegA == (long) E->Num && /* Both are equal */ In->RegA == (long) E->Num && /* Both are equal */
(N = CS_GetNextEntry (S, I)) != 0 && /* There is a next entry */ (N = CS_GetNextEntry (S, I)) != 0 && /* There is a next entry */
(N->Info & OF_FBRA) == 0) { /* Which is not a cond branch */ !CE_UseLoadFlags (N)) { /* Which does not use the flags */
Delete = 1; Delete = 1;
} }
break; break;
@ -809,7 +809,7 @@ unsigned OptDupLoads (CodeSeg* S)
CE_KnownImm (E) && /* Value to be loaded is known */ CE_KnownImm (E) && /* Value to be loaded is known */
In->RegX == (long) E->Num && /* Both are equal */ In->RegX == (long) E->Num && /* Both are equal */
(N = CS_GetNextEntry (S, I)) != 0 && /* There is a next entry */ (N = CS_GetNextEntry (S, I)) != 0 && /* There is a next entry */
(N->Info & OF_FBRA) == 0) { /* Which is not a cond branch */ !CE_UseLoadFlags (N)) { /* Which does not use the flags */
Delete = 1; Delete = 1;
} }
break; break;
@ -819,7 +819,7 @@ unsigned OptDupLoads (CodeSeg* S)
CE_KnownImm (E) && /* Value to be loaded is known */ CE_KnownImm (E) && /* Value to be loaded is known */
In->RegY == (long) E->Num && /* Both are equal */ In->RegY == (long) E->Num && /* Both are equal */
(N = CS_GetNextEntry (S, I)) != 0 && /* There is a next entry */ (N = CS_GetNextEntry (S, I)) != 0 && /* There is a next entry */
(N->Info & OF_FBRA) == 0) { /* Which is not a cond branch */ !CE_UseLoadFlags (N)) { /* Which does not use the flags */
Delete = 1; Delete = 1;
} }
break; break;
@ -908,37 +908,37 @@ unsigned OptDupLoads (CodeSeg* S)
if (In->RegA >= 0 && if (In->RegA >= 0 &&
In->RegA == In->RegX && In->RegA == In->RegX &&
(N = CS_GetNextEntry (S, I)) != 0 && (N = CS_GetNextEntry (S, I)) != 0 &&
(N->Info & OF_FBRA) == 0) { !CE_UseLoadFlags (N)) {
/* Value is identical and not followed by a branch */ /* Value is identical and not followed by a branch */
Delete = 1; Delete = 1;
} }
break; break;
case OP65_TAY: case OP65_TAY:
if (In->RegA >= 0 && if (In->RegA >= 0 &&
In->RegA == In->RegY && In->RegA == In->RegY &&
(N = CS_GetNextEntry (S, I)) != 0 && (N = CS_GetNextEntry (S, I)) != 0 &&
(N->Info & OF_FBRA) == 0) { !CE_UseLoadFlags (N)) {
/* Value is identical and not followed by a branch */ /* Value is identical and not followed by a branch */
Delete = 1; Delete = 1;
} }
break; break;
case OP65_TXA: case OP65_TXA:
if (In->RegX >= 0 && if (In->RegX >= 0 &&
In->RegX == In->RegA && In->RegX == In->RegA &&
(N = CS_GetNextEntry (S, I)) != 0 && (N = CS_GetNextEntry (S, I)) != 0 &&
(N->Info & OF_FBRA) == 0) { !CE_UseLoadFlags (N)) {
/* Value is identical and not followed by a branch */ /* Value is identical and not followed by a branch */
Delete = 1; Delete = 1;
} }
break; break;
case OP65_TYA: case OP65_TYA:
if (In->RegY >= 0 && if (In->RegY >= 0 &&
In->RegY == In->RegA && In->RegY == In->RegA &&
(N = CS_GetNextEntry (S, I)) != 0 && (N = CS_GetNextEntry (S, I)) != 0 &&
(N->Info & OF_FBRA) == 0) { !CE_UseLoadFlags (N)) {
/* Value is identical and not followed by a branch */ /* Value is identical and not followed by a branch */
Delete = 1; Delete = 1;
} }
@ -1003,7 +1003,7 @@ unsigned OptStoreLoad (CodeSeg* S)
(E->OPC == OP65_STY && N->OPC == OP65_LDY)) && (E->OPC == OP65_STY && N->OPC == OP65_LDY)) &&
strcmp (E->Arg, N->Arg) == 0 && strcmp (E->Arg, N->Arg) == 0 &&
(X = CS_GetNextEntry (S, I+1)) != 0 && (X = CS_GetNextEntry (S, I+1)) != 0 &&
(X->Info & OF_FBRA) == 0) { !CE_UseLoadFlags (X)) {
/* Register has already the correct value, remove the load */ /* Register has already the correct value, remove the load */
CS_DelEntry (S, I+1); CS_DelEntry (S, I+1);
@ -1061,7 +1061,7 @@ unsigned OptTransfers (CodeSeg* S)
if ((X = CS_GetNextEntry (S, I+1)) == 0) { if ((X = CS_GetNextEntry (S, I+1)) == 0) {
goto NextEntry; goto NextEntry;
} }
if ((X->Info & OF_FBRA) != 0) { if (CE_UseLoadFlags (X)) {
if (I == 0) { if (I == 0) {
/* No preceeding entry */ /* No preceeding entry */
goto NextEntry; goto NextEntry;

View File

@ -281,16 +281,16 @@ unsigned assignadjust (type* lhst, ExprDesc* rhs)
void DefineData (ExprDesc* lval) void DefineData (ExprDesc* Expr)
/* Output a data definition for the given expression */ /* Output a data definition for the given expression */
{ {
unsigned flags = lval->Flags; unsigned Flags = Expr->Flags;
switch (flags & E_MCTYPE) { switch (Flags & E_MCTYPE) {
case E_TCONST: case E_TCONST:
/* Number */ /* Number */
g_defdata (TypeOf (lval->Type) | CF_CONST, lval->ConstVal, 0); g_defdata (TypeOf (Expr->Type) | CF_CONST, Expr->ConstVal, 0);
break; break;
case E_TREGISTER: case E_TREGISTER:
@ -305,33 +305,33 @@ void DefineData (ExprDesc* lval)
case E_TGLAB: case E_TGLAB:
case E_TLLAB: case E_TLLAB:
/* Local or global symbol */ /* Local or global symbol */
g_defdata (GlobalModeFlags (flags), lval->Name, lval->ConstVal); g_defdata (GlobalModeFlags (Flags), Expr->Name, Expr->ConstVal);
break; break;
case E_TLIT: case E_TLIT:
/* a literal of some kind */ /* a literal of some kind */
g_defdata (CF_STATIC, LiteralPoolLabel, lval->ConstVal); g_defdata (CF_STATIC, LiteralPoolLabel, Expr->ConstVal);
break; break;
default: default:
Internal ("Unknown constant type: %04X", flags); Internal ("Unknown constant type: %04X", Flags);
} }
} }
static void lconst (unsigned flags, ExprDesc* lval) static void lconst (unsigned Flags, ExprDesc* Expr)
/* Load primary reg with some constant value. */ /* Load the primary register with some constant value. */
{ {
switch (lval->Flags & E_MCTYPE) { switch (Expr->Flags & E_MCTYPE) {
case E_TLOFFS: case E_TLOFFS:
g_leasp (lval->ConstVal); g_leasp (Expr->ConstVal);
break; break;
case E_TCONST: case E_TCONST:
/* Number constant */ /* Number constant */
g_getimmed (flags | TypeOf (lval->Type) | CF_CONST, lval->ConstVal, 0); g_getimmed (Flags | TypeOf (Expr->Type) | CF_CONST, Expr->ConstVal, 0);
break; break;
case E_TREGISTER: case E_TREGISTER:
@ -346,18 +346,18 @@ static void lconst (unsigned flags, ExprDesc* lval)
case E_TGLAB: case E_TGLAB:
case E_TLLAB: case E_TLLAB:
/* Local or global symbol, load address */ /* Local or global symbol, load address */
flags |= GlobalModeFlags (lval->Flags); Flags |= GlobalModeFlags (Expr->Flags);
flags &= ~CF_CONST; Flags &= ~CF_CONST;
g_getimmed (flags, lval->Name, lval->ConstVal); g_getimmed (Flags, Expr->Name, Expr->ConstVal);
break; break;
case E_TLIT: case E_TLIT:
/* Literal string */ /* Literal string */
g_getimmed (CF_STATIC, LiteralPoolLabel, lval->ConstVal); g_getimmed (CF_STATIC, LiteralPoolLabel, Expr->ConstVal);
break; break;
default: default:
Internal ("Unknown constant type: %04X", lval->Flags); Internal ("Unknown constant type: %04X", Expr->Flags);
} }
} }
@ -411,9 +411,10 @@ static int kcalc (int tok, long val1, long val2)
static GenDesc* FindGen (token_t Tok, GenDesc** Table) static const GenDesc* FindGen (token_t Tok, const GenDesc** Table)
/* Find a token in a generator table */
{ {
GenDesc* G; const GenDesc* G;
while ((G = *Table) != 0) { while ((G = *Table) != 0) {
if (G->Tok == Tok) { if (G->Tok == Tok) {
return G; return G;
@ -1760,7 +1761,7 @@ static int hie10 (ExprDesc* lval)
static int hie_internal (GenDesc** ops, /* List of generators */ static int hie_internal (const GenDesc** ops, /* List of generators */
ExprDesc* lval, /* parent expr's lval */ ExprDesc* lval, /* parent expr's lval */
int (*hienext) (ExprDesc*), int (*hienext) (ExprDesc*),
int* UsedGen) /* next higher level */ int* UsedGen) /* next higher level */
@ -1770,7 +1771,7 @@ static int hie_internal (GenDesc** ops, /* List of generators */
ExprDesc lval2; ExprDesc lval2;
CodeMark Mark1; CodeMark Mark1;
CodeMark Mark2; CodeMark Mark2;
GenDesc* Gen; const GenDesc* Gen;
token_t tok; /* The operator token */ token_t tok; /* The operator token */
unsigned ltype, type; unsigned ltype, type;
int rconst; /* Operand is a constant */ int rconst; /* Operand is a constant */
@ -1870,8 +1871,8 @@ static int hie_internal (GenDesc** ops, /* List of generators */
static int hie_compare (GenDesc** ops, /* List of generators */ static int hie_compare (const GenDesc** ops, /* List of generators */
ExprDesc* lval, /* parent expr's lval */ ExprDesc* lval, /* parent expr's lval */
int (*hienext) (ExprDesc*)) int (*hienext) (ExprDesc*))
/* Helper function for the compare operators */ /* Helper function for the compare operators */
{ {
@ -1879,7 +1880,7 @@ static int hie_compare (GenDesc** ops, /* List of generators */
ExprDesc lval2; ExprDesc lval2;
CodeMark Mark1; CodeMark Mark1;
CodeMark Mark2; CodeMark Mark2;
GenDesc* Gen; const GenDesc* Gen;
token_t tok; /* The operator token */ token_t tok; /* The operator token */
unsigned ltype; unsigned ltype;
int rconst; /* Operand is a constant */ int rconst; /* Operand is a constant */
@ -1997,7 +1998,7 @@ static int hie_compare (GenDesc** ops, /* List of generators */
static int hie9 (ExprDesc *lval) static int hie9 (ExprDesc *lval)
/* Process * and / operators. */ /* Process * and / operators. */
{ {
static GenDesc* hie9_ops [] = { static const GenDesc* hie9_ops [] = {
&GenMUL, &GenDIV, &GenMOD, 0 &GenMUL, &GenDIV, &GenMOD, 0
}; };
int UsedGen; int UsedGen;
@ -2421,7 +2422,7 @@ static int hie8 (ExprDesc* lval)
static int hie7 (ExprDesc *lval) static int hie7 (ExprDesc *lval)
/* Parse << and >>. */ /* Parse << and >>. */
{ {
static GenDesc* hie7_ops [] = { static const GenDesc* hie7_ops [] = {
&GenASL, &GenASR, 0 &GenASL, &GenASR, 0
}; };
int UsedGen; int UsedGen;
@ -2434,7 +2435,7 @@ static int hie7 (ExprDesc *lval)
static int hie6 (ExprDesc *lval) static int hie6 (ExprDesc *lval)
/* process greater-than type comparators */ /* process greater-than type comparators */
{ {
static GenDesc* hie6_ops [] = { static const GenDesc* hie6_ops [] = {
&GenLT, &GenLE, &GenGE, &GenGT, 0 &GenLT, &GenLE, &GenGE, &GenGT, 0
}; };
return hie_compare (hie6_ops, lval, hie7); return hie_compare (hie6_ops, lval, hie7);
@ -2444,7 +2445,7 @@ static int hie6 (ExprDesc *lval)
static int hie5 (ExprDesc *lval) static int hie5 (ExprDesc *lval)
{ {
static GenDesc* hie5_ops[] = { static const GenDesc* hie5_ops[] = {
&GenEQ, &GenNE, 0 &GenEQ, &GenNE, 0
}; };
return hie_compare (hie5_ops, lval, hie6); return hie_compare (hie5_ops, lval, hie6);
@ -2455,7 +2456,7 @@ static int hie5 (ExprDesc *lval)
static int hie4 (ExprDesc* lval) static int hie4 (ExprDesc* lval)
/* Handle & (bitwise and) */ /* Handle & (bitwise and) */
{ {
static GenDesc* hie4_ops [] = { static const GenDesc* hie4_ops [] = {
&GenAND, 0 &GenAND, 0
}; };
int UsedGen; int UsedGen;
@ -2468,7 +2469,7 @@ static int hie4 (ExprDesc* lval)
static int hie3 (ExprDesc *lval) static int hie3 (ExprDesc *lval)
/* Handle ^ (bitwise exclusive or) */ /* Handle ^ (bitwise exclusive or) */
{ {
static GenDesc* hie3_ops [] = { static const GenDesc* hie3_ops [] = {
&GenXOR, 0 &GenXOR, 0
}; };
int UsedGen; int UsedGen;
@ -2481,7 +2482,7 @@ static int hie3 (ExprDesc *lval)
static int hie2 (ExprDesc *lval) static int hie2 (ExprDesc *lval)
/* Handle | (bitwise or) */ /* Handle | (bitwise or) */
{ {
static GenDesc* hie2_ops [] = { static const GenDesc* hie2_ops [] = {
&GenOR, 0 &GenOR, 0
}; };
int UsedGen; int UsedGen;
@ -2810,7 +2811,7 @@ static int hieQuest (ExprDesc *lval)
static void opeq (GenDesc* Gen, ExprDesc *lval, int k) static void opeq (const GenDesc* Gen, ExprDesc *lval, int k)
/* Process "op=" operators. */ /* Process "op=" operators. */
{ {
ExprDesc lval2; ExprDesc lval2;
@ -2891,7 +2892,7 @@ static void opeq (GenDesc* Gen, ExprDesc *lval, int k)
static void addsubeq (GenDesc* Gen, ExprDesc *lval, int k) static void addsubeq (const GenDesc* Gen, ExprDesc *lval, int k)
/* Process the += and -= operators */ /* Process the += and -= operators */
{ {
ExprDesc lval2; ExprDesc lval2;