bool PushPop2MovOptimization::optimize(AsmCode& code, int index){ if( prepare(code[index], code[index + 1]) && *cmd1 == cmdPUSH && *cmd2 == cmdPOP && !(cmd1->argument()->isMemory() && cmd2->argument()->isMemory())){ AsmCmd* optCmd = new AsmCmd2(cmdMOV, cmd2->argument(), cmd1->argument()); code.deleteRange(index, index + 1); code.insert(optCmd, index); return true; } return false; }
bool RegRegCMP2RegIntCmpOptimization::optimize(AsmCode& code, int index){ if( prepare(code[index], code[index + 1]) && *cmd1 == cmdMOV && cmd2 && *cmd2 == cmdCMP && *cmd1->firstArg() == cmd2->secondArg()){ AsmCmd2* optCmd = new AsmCmd2(cmdCMP, cmd2->firstArg(), cmd1->secondArg()); code.deleteRange(index, index + 1); code.insert(optCmd, index); return true; } return false; }
bool MovPush2PushOptimization::optimize(AsmCode& code, int index){ if (prepare(code[index], code[index + 1]) && *cmd1 == cmdMOV && *cmd1->firstArg() == EAX && *cmd2 == cmdPUSH && *cmd1->firstArg() == cmd2->argument()){ AsmCmd1* optCmd = new AsmCmd1(cmdPUSH, cmd1->secondArg()); code.deleteRange(index, index + 1); code.insert(optCmd, index); return true; } return false; }
bool AddZero2MovOptimization::optimize(AsmCode& code, int index){ if( prepare(code[index], code[index + 1], code[index + 2]) && *cmd1 == cmdMOV && *cmd2 == cmdMOV && *cmd3 == cmdADD && (*cmd1->secondArg() == 0 || *cmd2->secondArg() == 0)){ AsmCmd2* optCmd = new AsmCmd2(cmdMOV, cmd3->firstArg(), *cmd1->secondArg() == 0 ? cmd2->secondArg() : cmd1->secondArg()); code.deleteRange(index, index + 2); code.insert(optCmd, index); return true; } return false; }
bool MovChainOptimization::optimize(AsmCode& code, int index){ if (prepare(code[index], code[index + 1]) && *cmd1 == cmdMOV && *cmd1->firstArg() == EAX && *cmd2 == cmdMOV && *cmd2->secondArg() == cmd1->firstArg() && !(cmd1->secondArg()->isMemory() && cmd2->firstArg()->isMemory()) ){ AsmCmd* optCmd = new AsmCmd2(cmdMOV, cmd2->firstArg(), cmd1->secondArg()); code.deleteRange(index, index + 1); code.insert(optCmd, index); return true; } return false; }
bool CompactAdditionOptimization::optimize(AsmCode& code, int index){ if( prepare(code[index], code[index + 1], code[index + 2]) && *cmd1 == cmdMOV && *cmd2 == cmdMOV && *cmd1->firstArg() == EBX && *cmd1->secondArg() == cmd2->firstArg() && *cmd3 == cmdADD && *cmd3->firstArg() == cmd2->firstArg() && *cmd3->secondArg() == cmd1->firstArg()){ AsmCmd2* optCmd = new AsmCmd2(cmdMOV, makeArg(EBX), cmd2->secondArg()); code.deleteRange(index, index + 1); code.insert(optCmd, index); return true; } return false; }
bool Neg2MovOppositeOptimization::optimize(AsmCode& code, int index){ if (prepare(code[index], code[index + 1]) && *cmd1 == cmdMOV && *cmd1->firstArg() == EAX && *cmd2 == cmdNEG && *cmd2->argument() == EAX && dynamic_cast<AsmImmediateArg*>(cmd1->secondArg())){ int val = dynamic_cast<AsmImmediateArg*>(cmd1->secondArg())->value; AsmCmd2* optCmd = new AsmCmd2(cmdMOV, makeArg(EAX), makeArg(-val)); code.deleteRange(index, index + 1); code.insert(optCmd, index); return true; } return false; }
bool MultIntByInt2MovOptimization::optimize(AsmCode& code, int index){ if( prepare(code[index], code[index + 1], code[index + 2]) && *cmd1 == cmdMOV && *cmd2 == cmdMOV && *cmd1->firstArg() == EAX && *cmd2->firstArg() == EBX && cmd1->secondArg()->isImmediate() && cmd2->secondArg()->isImmediate() && *cmd3 == cmdIMUL){ int val1 = dynamic_cast<AsmImmediateArg*>(cmd1->secondArg())->value, val2 = dynamic_cast<AsmImmediateArg*>(cmd2->secondArg())->value; AsmCmd2* optCmd = new AsmCmd2(cmdMOV, cmd3->firstArg(), makeArg(val1 * val2)); code.deleteRange(index, index + 2); code.insert(optCmd, index); return true; } return false; }
bool Mov2MemoryDirectlyOptimization::optimize(AsmCode& code, int index){ AsmCmd2* cmd1 = dynamic_cast<AsmCmd2*>(code[index]); AsmCmd2* cmd2 = dynamic_cast<AsmCmd2*>(code[index + 1]); AsmCmd2* cmd3 = dynamic_cast<AsmCmd2*>(code[index + 2]); AsmCmd2* cmd4 = dynamic_cast<AsmCmd2*>(code[index + 3]); if (cmd1 && *cmd1->firstArg() == EAX && cmd1->secondArg()->isOffset() && cmd2 && *cmd2->firstArg() == EBX && cmd2->secondArg()->isImmediate() && cmd3 && cmd3->firstArg()->isMemory() && *cmd3->secondArg() == EBX && cmd4 && *cmd4 == cmdMOV){ cmd1->secondArg()->clearOffset(); AsmCmd2* optCmd1 = new AsmCmd2(cmdMOV, cmd1->secondArg(), cmd2->secondArg()); AsmCmd2* optCmd2 = new AsmCmd2(cmdMOV, cmd4->firstArg(), cmd2->secondArg()); code.deleteRange(index, index + 3); code.insert(optCmd2, index); code.insert(optCmd1, index); return true; } return false; }