From 7da0da3cadc37be056832d8c6e9b8912436e9e7f Mon Sep 17 00:00:00 2001 From: cuz Date: Sun, 5 Aug 2001 22:50:00 +0000 Subject: [PATCH] More optimizations git-svn-id: svn://svn.cc65.org/cc65/trunk@842 b7a2c559-68d2-44c3-8de9-860c34a00d81 --- src/cc65/codeinfo.c | 8 ++++++ src/cc65/codeopt.c | 65 ++++++++++++++++++++++++++++++++++++++++++--- 2 files changed, 69 insertions(+), 4 deletions(-) diff --git a/src/cc65/codeinfo.c b/src/cc65/codeinfo.c index 3430dbeae..982ce4cec 100644 --- a/src/cc65/codeinfo.c +++ b/src/cc65/codeinfo.c @@ -67,6 +67,10 @@ struct FuncInfo { static const FuncInfo FuncInfoTable[] = { { "addysp", REG_Y, REG_NONE }, + { "aslax1", REG_AX, REG_AX }, + { "aslax2", REG_AX, REG_AX }, + { "aslax3", REG_AX, REG_AX }, + { "aslax4", REG_AX, REG_AX }, { "bnega", REG_A, REG_AX }, { "bnegax", REG_AX, REG_AX }, { "bnegeax", REG_AX, REG_AX }, @@ -122,6 +126,10 @@ static const FuncInfo FuncInfoTable[] = { { "pusheax", REG_AX, REG_Y }, { "pushw0sp", REG_NONE, REG_AXY }, { "pushwysp", REG_Y, REG_AXY }, + { "shlax1", REG_AX, REG_AX }, + { "shlax2", REG_AX, REG_AX }, + { "shlax3", REG_AX, REG_AX }, + { "shlax4", REG_AX, REG_AX }, { "shrax1", REG_AX, REG_AX }, { "shrax2", REG_AX, REG_AX }, { "shrax3", REG_AX, REG_AX }, diff --git a/src/cc65/codeopt.c b/src/cc65/codeopt.c index fce4c1f34..3ec3f12db 100644 --- a/src/cc65/codeopt.c +++ b/src/cc65/codeopt.c @@ -37,6 +37,7 @@ /* common */ #include "abend.h" +#include "chartype.h" #include "print.h" #include "xsprintf.h" @@ -692,7 +693,7 @@ static unsigned OptAdd2 (CodeSeg* S) strcmp (L[6]->Arg, "addeqysp") == 0 && !CE_HasLabel (L[6]) && (GetRegInfo (S, I+7) & REG_AX) == 0) { - + char Buf [20]; CodeEntry* X; int Offs; @@ -809,6 +810,60 @@ static unsigned OptAdd3 (CodeSeg* S) +/*****************************************************************************/ +/* Optimize shifts */ +/*****************************************************************************/ + + + +static unsigned OptShift1 (CodeSeg* S) +/* A call to the shlaxN routine may get replaced by one or more asl insns + * if the value of X is not used later. + */ +{ + unsigned Changes = 0; + + /* Walk over the entries */ + unsigned I = 0; + while (I < CS_GetEntryCount (S)) { + + /* Get next entry */ + CodeEntry* E = CS_GetEntry (S, I); + + /* Check for the sequence */ + if (E->OPC == OP65_JSR && + (strncmp (E->Arg, "shlax", 5) == 0 || + strncmp (E->Arg, "aslax", 5) == 0) && + strlen (E->Arg) == 6 && + IsDigit (E->Arg[5]) && + !RegXUsed (S, I+1)) { + + /* Insert shift insns */ + unsigned Count = E->Arg[5] - '0'; + while (Count--) { + CodeEntry* X = NewCodeEntry (OP65_ASL, AM65_ACC, "a", 0, E->LI); + CS_InsertEntry (S, X, I+1); + } + + /* Delete the call to shlax */ + CS_DelEntry (S, I); + + /* Remember, we had changes */ + ++Changes; + + } + + /* Next entry */ + ++I; + + } + + /* Return the number of changes made */ + return Changes; +} + + + /*****************************************************************************/ /* Optimizations for compares */ /*****************************************************************************/ @@ -984,7 +1039,7 @@ static unsigned OptCmp3 (CodeSeg* S) CE_ReplaceOPC (L[1], OP65_CMP); /* Beware: If the first LDA instruction had a label, we have - * to move this label to the top of the sequence again. + * to move this label to the top of the sequence again. */ if (CE_HasLabel (E)) { CS_MoveLabels (S, E, L[0]); @@ -1629,7 +1684,7 @@ static unsigned OptNegAX4 (CodeSeg* S) /* Insert apropriate test code */ if (ByteSized) { - /* Test bytes */ + /* Test bytes */ X = NewCodeEntry (OP65_TAX, AM65_IMP, 0, 0, L[0]->LI); CS_InsertEntry (S, X, I+2); } else { @@ -2017,7 +2072,7 @@ static unsigned OptPtrLoad2 (CodeSeg* S) L[7]->OPC == OP65_JSR && strcmp (L[7]->Arg, "ldauidx") == 0 && !CE_HasLabel (L[7])) { - + CodeEntry* X; /* Store the low byte and remove the TAY instead */ @@ -2278,6 +2333,8 @@ static OptFunc OptFuncs [] = { OptEntry (OptAdd1, optPre), OptEntry (OptAdd2, optPre), OptEntry (OptAdd3, optMain), + /* Optimize shifts */ + OptEntry (OptShift1, optPre), /* Optimize jump cascades */ OptEntry (OptJumpCascades, optMain), /* Remove dead jumps */