Example #1
0
unsigned OptTest2 (CodeSeg* S)
/* Search for an inc/dec operation followed by a load and a conditional
 * branch based on the flags from the load. Remove the load if the insn
 * isn't used later.
 */
{
    unsigned Changes = 0;

    /* Walk over the entries */
    unsigned I = 0;
    while (I < CS_GetEntryCount (S)) {

        CodeEntry* L[3];

        /* Get next entry */
        L[0] = CS_GetEntry (S, I);

        /* Check if it's the sequence we're searching for */
        if ((L[0]->OPC == OP65_INC || L[0]->OPC == OP65_DEC)    &&
            CS_GetEntries (S, L+1, I+1, 2)                      &&
            !CE_HasLabel (L[1])                                 &&
            (L[1]->Info & OF_LOAD) != 0                         &&
            (L[2]->Info & OF_FBRA) != 0                         &&
            L[1]->AM == L[0]->AM                                &&
            strcmp (L[0]->Arg, L[1]->Arg) == 0                  &&
            (GetRegInfo (S, I+2, L[1]->Chg) & L[1]->Chg) == 0) {

            /* Remove the load */
            CS_DelEntry (S, I+1);
             ++Changes;
        }

        /* Next entry */
        ++I;

    }

    /* Return the number of changes made */
    return Changes;
}
Example #2
0
int RegEAXUsed (struct CodeSeg* S, unsigned Index)
/* Check if any of the four bytes in EAX are used. */
{
    return (GetRegInfo (S, Index, REG_EAX) & REG_EAX) != 0;
}
Example #3
0
int RegAXUsed (struct CodeSeg* S, unsigned Index)
/* Check if the value in A or(!) the value in X are used. */
{
    return (GetRegInfo (S, Index, REG_AX) & REG_AX) != 0;
}
Example #4
0
int RegYUsed (struct CodeSeg* S, unsigned Index)
/* Check if the value in Y is used. */
{
    return (GetRegInfo (S, Index, REG_Y) & REG_Y) != 0;
}
Example #5
0
unsigned OptAdd2 (CodeSeg* S)
/* Search for the sequence
 *
 *     	ldy     #xx
 *      jsr     ldaxysp
 *      ldy     #yy
 *      jsr     addeqysp
 *
 * and replace it by:
 *
 *      ldy     #xx-1
 *      lda     (sp),y
 *      ldy     #yy
 *      clc
 *      adc     (sp),y
 *      sta     (sp),y
 *      ldy     #xx
 *      lda     (sp),y
 *      ldy     #yy+1
 *      adc     (sp),y
 *      sta     (sp),y
 *
 * provided that a/x is not used later.
 */
{
    unsigned Changes = 0;

    /* Walk over the entries */
    unsigned I = 0;
    while (I < CS_GetEntryCount (S)) {

     	CodeEntry* L[4];

      	/* Get next entry */
       	L[0] = CS_GetEntry (S, I);

     	/* Check for the sequence */
	if (L[0]->OPC == OP65_LDY               &&
	    CE_IsConstImm (L[0])                &&
	    !CS_RangeHasLabel (S, I+1, 3)       &&
       	    CS_GetEntries (S, L+1, I+1, 3)   	&&
	    CE_IsCallTo (L[1], "ldaxysp")       &&
       	    L[2]->OPC == OP65_LDY               &&
	    CE_IsConstImm (L[2])                &&
       	    CE_IsCallTo (L[3], "addeqysp")      &&
       	    (GetRegInfo (S, I+4, REG_AX) & REG_AX) == 0) {

	    /* Insert new code behind the addeqysp */
	    const char* Arg;
	    CodeEntry* X;

	    /* ldy     #xx-1 */
	    Arg = MakeHexArg (L[0]->Num-1);
	    X = NewCodeEntry (OP65_LDY, AM65_IMM, Arg, 0, L[0]->LI);
	    CS_InsertEntry (S, X, I+4);

	    /* lda     (sp),y */
	    X = NewCodeEntry (OP65_LDA, AM65_ZP_INDY, "sp", 0, L[1]->LI);
	    CS_InsertEntry (S, X, I+5);

	    /* ldy     #yy */
	    X = NewCodeEntry (OP65_LDY, AM65_IMM, L[2]->Arg, 0, L[2]->LI);
	    CS_InsertEntry (S, X, I+6);

	    /* clc */
	    X = NewCodeEntry (OP65_CLC, AM65_IMP, 0, 0, L[3]->LI);
	    CS_InsertEntry (S, X, I+7);

	    /* adc     (sp),y */
       	    X = NewCodeEntry (OP65_ADC, AM65_ZP_INDY, "sp", 0, L[3]->LI);
	    CS_InsertEntry (S, X, I+8);

	    /* sta     (sp),y */
	    X = NewCodeEntry (OP65_STA, AM65_ZP_INDY, "sp", 0, L[3]->LI);
	    CS_InsertEntry (S, X, I+9);

	    /* ldy     #xx */
	    X = NewCodeEntry (OP65_LDY, AM65_IMM, L[0]->Arg, 0, L[0]->LI);
	    CS_InsertEntry (S, X, I+10);

	    /* lda     (sp),y */
	    X = NewCodeEntry (OP65_LDA, AM65_ZP_INDY, "sp", 0, L[1]->LI);
	    CS_InsertEntry (S, X, I+11);

	    /* ldy     #yy+1 */
	    Arg = MakeHexArg (L[2]->Num+1);
	    X = NewCodeEntry (OP65_LDY, AM65_IMM, Arg, 0, L[2]->LI);
	    CS_InsertEntry (S, X, I+12);

	    /* adc     (sp),y */
	    X = NewCodeEntry (OP65_ADC, AM65_ZP_INDY, "sp", 0, L[3]->LI);
	    CS_InsertEntry (S, X, I+13);

	    /* sta     (sp),y */
	    X = NewCodeEntry (OP65_STA, AM65_ZP_INDY, "sp", 0, L[3]->LI);
	    CS_InsertEntry (S, X, I+14);

	    /* Delete the old code */
	    CS_DelEntries (S, I, 4);

	    /* Remember, we had changes */
	    ++Changes;

	}

	/* Next entry */
	++I;

    }

    /* Return the number of changes made */
    return Changes;
}