diff --git a/include/AccumExpReduction.h b/include/AccumExpReduction.h
index b2fb4975500304562f56582970d3c3e02261312e..b2268063582e00ffda1781e654631f09666d99b2 100644
--- a/include/AccumExpReduction.h
+++ b/include/AccumExpReduction.h
@@ -11,6 +11,7 @@
 class AccumExpReduction {
     Unit *unit;
     std::map<SymbolEntry*,std::pair<Instruction*,int>> expOps;
+    std::map<int,SymbolEntry*> numberOp_map;
     void insertBefore(Instruction *, Instruction *);
     std::vector<Instruction*> expInsts;
     void findExp(Function *func);
diff --git a/include/InstructionsSchedule.h b/include/InstructionsSchedule.h
new file mode 100644
index 0000000000000000000000000000000000000000..09be95546005ba51b836a9ebc1a143fcd34d1cd4
--- /dev/null
+++ b/include/InstructionsSchedule.h
@@ -0,0 +1,47 @@
+#ifndef SYSYC_INSTRUCTIONSSCHEDULE_H
+#define SYSYC_INSTRUCTIONSSCHEDULE_H
+
+#include "MachineCode.h"
+
+
+class InstructionsScheduling {
+private:
+    MachineUnit* mUnit;
+    struct Node {
+        MachineInstruction* inst;
+        int delay;
+        int priority;
+        int degree;
+        std::vector<int> pred;
+        std::vector<std::pair<int, int>> succ; //(succ_inst, delay);
+        Node();
+        Node(MachineInstruction *i){
+            inst = i;
+            delay = 0;
+            priority = -1;
+            degree = 0;
+        };
+    };
+    std::vector<Node*> Nodelist;
+    
+
+public:
+    InstructionsScheduling(MachineUnit* mUnit) {
+        this->mUnit = mUnit;
+    }
+    void pass();
+    int getInstDelay(MachineInstruction* inst);
+    void calculate_priority(int index);
+    int getIndex(Node* node) {
+        for(int i = 0; i < Nodelist.size(); i++) {
+            if(Nodelist[i] == node) {
+                return i;
+            }
+        }
+        return -1;
+    };
+
+};
+
+
+#endif 
\ No newline at end of file
diff --git a/include/MachineCode.h b/include/MachineCode.h
index 0702ae5d16203c3cc202171e4b91eecdb44f4bf3..6a21d7795336e407c9a64cde90ba0fb85d3fa564 100644
--- a/include/MachineCode.h
+++ b/include/MachineCode.h
@@ -141,6 +141,22 @@ class MachineInstruction {
     void replaceUse(MachineOperand* old, MachineOperand* new_);
     void replaceDef(MachineOperand* old, MachineOperand* new_);
     int getOp() { return op; }
+    bool isVMRS() const { return type == VMRS; };
+
+    bool isSpecial() const {
+      for (auto& ope : def_list) {
+          if (ope->isReg() && ope->getReg() >= 11 && ope->getReg() <= 15) {
+              return true;
+          }
+      }
+      for (auto& ope : use_list) {
+          if (ope->isReg() && ope->getReg() >= 11 && ope->getReg() <= 15) {
+              return true;
+          }
+      }
+      return false;
+    }
+
     MachineBlock *getParent() const { return parent; };
     bool isBX() const { return type == BRANCH && op == 2; };
     bool isBL() const { return type == BRANCH && op == 1; };
diff --git a/src/AccumExpReduction.cpp b/src/AccumExpReduction.cpp
index d74dea8450d61543de3572fb8659c942fc0ddd35..98df642135801f80aaf7b4d6bafbb2ae1d6d8da6 100644
--- a/src/AccumExpReduction.cpp
+++ b/src/AccumExpReduction.cpp
@@ -7,8 +7,10 @@
 #define print(str) //
 #endif
 
-#define MINIMUM_TIMES 3
-#define MINIMUM_PARAMS 15
+#define MINIMUM_TIMES 20
+#define MINIMUM_PARAMS 2
+#define EXPLENGH 100
+bool hasStore = 0;
 
 using namespace std;
 
@@ -44,28 +46,69 @@ void AccumExpReduction::simplifyExp(int res, BasicBlock *bb) {
         if (times < 0)
             opcode = BinaryInstruction::SUB;
 
+        print("Accum = " << Accum->toStr());
+        Operand *sum =
+            new Operand(new ConstantSymbolEntry(TypeSystem::intType, 0));
+
         for (auto const &src : expOps) {
-            auto dst1 = new Operand(new TemporarySymbolEntry(
-                TypeSystem::intType, SymbolTable::getLabel()));
             // auto addr = dynamic_cast<IdentifierSymbolEntry
             // *>(src.first)->getAddr(); print(src.first->toStr());
             // print(addr->toStr());
-            auto load = new LoadInstruction(
-                dst1, (src.second.first)->getUse()[0], tmp_bb);
+
+            Operand *dst1;
+            if (src.first->isConstant()) {
+                dst1 = new Operand(src.first);
+            } else {
+                dst1 = new Operand(new TemporarySymbolEntry(
+                    TypeSystem::intType, SymbolTable::getLabel()));
+                Operand *addr = (src.second.first)->getUse()[0];
+                auto load = new LoadInstruction(dst1, addr, tmp_bb);
+                new_insts.push_back(load);
+            }
+            // print("dst1 = " << dst1->toStr());
+
             // Instruction *load = (src.second).first;
-            new_insts.push_back(load);
             auto dst2 = new Operand(new TemporarySymbolEntry(
                 TypeSystem::intType, SymbolTable::getLabel()));
-            auto bin = new BinaryInstruction(opcode, dst2, Accum, dst1, tmp_bb);
+            auto bin = new BinaryInstruction(opcode, dst2, sum, dst1, tmp_bb);
             new_insts.push_back(bin);
-            Accum = dst2;
+            sum = dst2;
         }
+
+        // 累加次数
+        auto dst = new Operand(new TemporarySymbolEntry(
+            TypeSystem::intType, SymbolTable::getLabel()));
         auto times_op =
             new Operand(new ConstantSymbolEntry(TypeSystem::intType, times));
-        auto mul = new BinaryInstruction(BinaryInstruction::MUL, end, Accum,
+        auto mul = new BinaryInstruction(BinaryInstruction::MUL, dst, sum,
                                          times_op, tmp_bb);
+
+        print("times_op = " << times_op->toStr());
         new_insts.push_back(mul);
 
+        // 加回原op
+        Operand *load_dst;
+        Instruction *add;
+        if (hasStore) {
+            load_dst = new Operand(new TemporarySymbolEntry(
+                TypeSystem::intType, SymbolTable::getLabel()));
+            auto load =
+                new LoadInstruction(load_dst, init->getDef()->getDef(), tmp_bb);
+            new_insts.push_back(load);
+            add = new BinaryInstruction(BinaryInstruction::ADD, end, load_dst,
+                                        dst, tmp_bb);
+        } else {
+            add = new BinaryInstruction(BinaryInstruction::ADD, end, init, dst,
+                                        tmp_bb);
+        }
+        new_insts.push_back(add);
+
+        // 存回值
+        if (hasStore) {
+            auto store = new StoreInstruction(init, end, tmp_bb);
+            new_insts.push_back(store);
+        }
+
         for (auto instr : new_insts) {
             bb->insertBefore(instr, expInsts[0]);
         }
@@ -85,17 +128,33 @@ void AccumExpReduction::findExp(Function *func) {
     bool start = 0;
     Operand *accum = nullptr;
     Operand *load_def = nullptr;
+    Operand *store_def = nullptr;
+    int count = 0;
     for (auto bb : func->getBlockList()) {
-        print("==== bb" << bb->getNo() << " ====") init = nullptr;
+        print("==== bb" << bb->getNo() << " ====");
+        init = nullptr;
         end = nullptr;
         expOps.clear();
         expInsts.clear();
+        count = 0;
         start = 0;
+        hasStore = 0;
         accum = nullptr;
         load_def = nullptr;
         for (auto instr = bb->begin(); instr != bb->end();
              instr = instr->getNext()) {
-                if(instr->isStore())continue;//Fix 可能有问题
+            if (!(isValid(instr)))
+                break;
+            if (
+                // start &&
+                instr->isStore()) {
+                hasStore = true;
+                if (start) {
+                    store_def = instr->getDef();
+                    expInsts.push_back(instr);
+                }
+                continue; // Fix 可能有问题
+            }
             if (instr->getDef()) {
                 print(instr->getDef()->toStr()
                       << " " << instr->getInstName() << " start = " << start);
@@ -109,95 +168,191 @@ void AccumExpReduction::findExp(Function *func) {
                 load_def = instr->getDef();
                 expInsts.push_back(instr);
             } else if (start) {
-                if (load_switch && instr->isBin() &&
-                    instr->getDef()->getType()->isInt()) {
-                    auto binary = dynamic_cast<BinaryInstruction *>(instr);
-                    auto opcode = binary->getOpcode();
-                    if (opcode == BinaryInstruction::ADD ||
-                        opcode == BinaryInstruction::SUB) {
-                        bool link = 0;
-                        for (auto use : instr->getUse()) {
-                            if (load_def == use)
-                                link = 1;
-                        }
-                        if (link) {
-                            if (init == nullptr) {
-                                for (auto use : instr->getUse()) {
-                                    if (load_def != use)
-                                        init = use;
-                                }
+            count++;
+                if (hasStore) {
+                    print("in hasStore");
+                    if (load_switch && instr->isBin() &&
+                        instr->getDef()->getType()->isInt()) {
+                        print("  in hasStore : bin");
+                        auto binary = dynamic_cast<BinaryInstruction *>(instr);
+                        auto opcode = binary->getOpcode();
+                        if (opcode == BinaryInstruction::ADD ||
+                            opcode == BinaryInstruction::SUB) {
+                            bool link = 0;
+                            Operand *src = nullptr;
+                            for (auto use : instr->getUse()) {
+                                // print("use = " << use->toStr());
+
+                                if (load_def == use)
+                                    link = 1;
+                                else
+                                    src = use;
                             }
+                            if (init == nullptr && store_def != nullptr)
+                                init = store_def;
+                            // if (!(load_def->getUse()[0] ==
+                            // store_def->getDef()))
+                            //     link = 0;
+                            if (link) {
+
+                                SymbolEntry *se = src->getSymbolEntry();
+                                // 常量-se映射
+                                if (se->isConstant()) {
+                                    auto se_constant =
+                                        dynamic_cast<ConstantSymbolEntry *>(
+                                            src->getSymbolEntry());
+                                    if (numberOp_map.find(
+                                            se_constant->getValue()) ==
+                                        numberOp_map.end()) {
+                                        numberOp_map[se_constant->getValue()] =
+                                            se;
+                                    } else {
+                                        se = numberOp_map[se_constant
+                                                              ->getValue()];
+                                    }
+                                }
+                                // 更新表达式src记录
+                                if (expOps.find(se) == expOps.end()) {
+                                    print("  store new "
+                                          << src->getSymbolEntry()->toStr());
+                                    expOps[se] =
+                                        std::make_pair(load_def->getDef(),
+                                                       getOperator(opcode));
 
-                            // print("load addr =
-                            // "<<load_def->getDef()->getUse()[0]->getSymbolEntry()->toStr());
-                            if (expOps.find(load_def->getDef()
-                                                ->getUse()[0]
-                                                ->getSymbolEntry()) ==
-                                expOps.end()) {
-                                // print("LOAD use
-                                // ="<<load_def->getDef()->getUse()[0]->toStr());
-                                expOps[load_def->getDef()
-                                           ->getUse()[0]
-                                           ->getSymbolEntry()] =
-                                    std::make_pair(load_def->getDef(),
-                                                   getOperator(opcode));
-
-                            } else {
-                                expOps[load_def->getDef()
-                                           ->getUse()[0]
-                                           ->getSymbolEntry()]
-                                    .second += getOperator(opcode);
+                                } else {
+                                    print("store add "
+                                          << src->getSymbolEntry()->toStr());
+                                    expOps[se].second += getOperator(opcode);
+                                }
+                                load_switch = 0;
+                                accum = instr->getDef();
+                                expInsts.push_back(instr);
+                                continue;
                             }
-                            load_switch = 0;
-                            accum = instr->getDef();
-                            expInsts.push_back(instr);
+                        }else{
+                            init = nullptr;
+                            end = nullptr;
+                            expOps.clear();
+                            expInsts.clear();
+                            start = 0;
+                            hasStore = 0;
+                            count = 0;
+                            accum = nullptr;
+                            load_def = nullptr;
                             continue;
                         }
+                    } else if (!load_switch && instr->isLoad()) {
+                        // print("!load_switch && instr->isLoad()");
+                        if (instr->getUse()[0] == store_def) {
+                            load_switch = 1;
+                            load_def = instr->getDef();
+                            expInsts.push_back(instr);
+                        }
+                        continue;
                     }
-                } else if (!load_switch && instr->isLoad()) {
-                    load_switch = 1;
-                    load_def = instr->getDef();
-                    expInsts.push_back(instr);
-                    continue;
-                }
-                if (instr->isBin()) { // 终了
-                    bool link = 0;
-                    for (auto use : instr->getUse()) {
-                        if (accum == use) {
-                            end = use;
-                            link = 1;
+                    // 处理mem2reg没处理的参数左值情况,会有store
+                    if (count > EXPLENGH && hasStore && instr->isLoad()) {
+                        print("hasStore end count = "<<count);
+                        if (instr->getPrev()->getPrev()->isStore()) {
+                            expInsts.pop_back();
+                            // expInsts.pop_back();
+                            print("store_def = " << store_def->toStr());
+                            print("accum = " << accum->toStr());
+                            end = accum;
+                            int res = rvalCheck();
+                            if (res) {
+                                simplifyExp(res, bb);
+                            }
                         }
                     }
-                    if (!link) {
-                        init = nullptr;
-                        end = nullptr;
-                        expOps.clear();
-                        expInsts.clear();
-                        start = 0;
-                        accum = nullptr;
-                        load_def = nullptr;
+                    print("out hasStore");
+                } else {
+                    if (load_switch && instr->isBin() &&
+                        instr->getDef()->getType()->isInt()) {
+                        auto binary = dynamic_cast<BinaryInstruction *>(instr);
+                        auto opcode = binary->getOpcode();
+                        if (opcode == BinaryInstruction::ADD ||
+                            opcode == BinaryInstruction::SUB) {
+                            bool link = 0;
+                            for (auto use : instr->getUse()) {
+                                if (load_def == use)
+                                    link = 1;
+                            }
+                            if (link) {
+                                if (init == nullptr) {
+                                    for (auto use : instr->getUse()) {
+                                        if (load_def != use)
+                                            init = use;
+                                    }
+                                }
+
+                                // print("load addr =
+                                // "<<load_def->getDef()->getUse()[0]->getSymbolEntry()->toStr());
+                                if (expOps.find(load_def->getDef()
+                                                    ->getUse()[0]
+                                                    ->getSymbolEntry()) ==
+                                    expOps.end()) {
+                                    // print("LOAD use
+                                    // ="<<load_def->getDef()->getUse()[0]->toStr());
+                                    expOps[load_def->getDef()
+                                               ->getUse()[0]
+                                               ->getSymbolEntry()] =
+                                        std::make_pair(load_def->getDef(),
+                                                       getOperator(opcode));
+
+                                } else {
+                                    expOps[load_def->getDef()
+                                               ->getUse()[0]
+                                               ->getSymbolEntry()]
+                                        .second += getOperator(opcode);
+                                }
+                                load_switch = 0;
+                                accum = instr->getDef();
+                                expInsts.push_back(instr);
+                                continue;
+                            }
+                        }
+                    } else if (!load_switch && instr->isLoad()) {
+                        load_switch = 1;
+                        load_def = instr->getDef();
+                        expInsts.push_back(instr);
                         continue;
                     }
-                    int res = rvalCheck();
-                    if (res) {
-                        simplifyExp(res, bb);
+                    print("========EXP END=========");
+                    if (count > EXPLENGH && instr->isBin()) { // 终了
+                        bool link = 0;
+                        for (auto use : instr->getUse()) {
+                            if (accum == use) {
+                                end = use;
+                                link = 1;
+                            }
+                        }
+                        if (!link) {
+                            init = nullptr;
+                            end = nullptr;
+                            expOps.clear();
+                            expInsts.clear();
+                            start = 0;
+                            hasStore = 0;
+                            count = 0;
+                            accum = nullptr;
+                            load_def = nullptr;
+                            continue;
+                        }
+                        int res = rvalCheck();
+                        if (res) {
+                            simplifyExp(res, bb);
+                        }
                     }
                 }
-                // else if(instr->isLoad()){
-                //     expOps.erase(
-                //         load_def->getDef()->getUse()[0]->getSymbolEntry());
-                //     end = accum;
-                //     int res = rvalCheck();
-                //     if (res) {
-                //         simplifyExp(res, bb);
-                //     }
-       
-                // }
+
                 init = nullptr;
                 end = nullptr;
                 expOps.clear();
                 expInsts.clear();
                 start = 0;
+                count = 0;
+                hasStore = 0;
                 accum = nullptr;
                 load_def = nullptr;
             }
@@ -218,6 +373,7 @@ int AccumExpReduction::rvalCheck() {
         if ((src.second).second != times)
             sameTimes = false;
     }
+    print("sameTimes = " << sameTimes);
     if (sameTimes) {
         return 2;
 
diff --git a/src/InstructionsSchedule.cpp b/src/InstructionsSchedule.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..1b1bc057b0730535ea89d5004d404c5eda7911df
--- /dev/null
+++ b/src/InstructionsSchedule.cpp
@@ -0,0 +1,350 @@
+#include "InstructionsSchedule.h"
+
+#define DEBUG_SWITCH_ische 0
+#if DEBUG_SWITCH_ische
+#define printISC(str) std::cout << str << "\n";
+#else
+#define printISC(str) //
+#endif
+
+
+
+//²»Í¬ÀàÐÍ»úÆ÷Ö¸ÁîµÄdelayÖµ£¬²Î¿¼Cortex-A72 Software Optimization Guide
+int InstructionsScheduling::getInstDelay(MachineInstruction* inst) {
+    switch (inst->getType())
+    {
+    case MachineInstruction::VNEG:
+        printISC("    " << "    " << "getInstDelay: MachineInstruction::VNEG");
+        return 3;
+    case MachineInstruction::FUSE:
+        printISC("    " << "    " << "getInstDelay: MachineInstruction::FUSE");
+        return 3;
+    case MachineInstruction::LOAD:
+        printISC("    " << "    " << "getInstDelay: MachineInstruction::LOAD");
+        return 4;
+    case MachineInstruction::STORE:
+        printISC("    " << "    " << "getInstDelay: MachineInstruction::STORE");
+        return 1;
+    case MachineInstruction::BRANCH:
+        printISC("    " << "    " << "getInstDelay: MachineInstruction::BRANCH");
+        return 1;
+    case MachineInstruction::VCVT:
+        printISC("    " << "    " << "getInstDelay: MachineInstruction::VCVT");
+        return 3;
+    case MachineInstruction::VMRS:
+        printISC("    " << "    " << "getInstDelay: MachineInstruction::VMRS");
+        return 1;
+    case MachineInstruction::BINARY:
+        printISC("    " << "    " << "getInstDelay: MachineInstruction::BINARY");
+        switch (inst->getOp())
+        {
+        case BinaryMInstruction::ADD:
+            return 1;
+        case BinaryMInstruction::SUB:
+            return 1;
+        case BinaryMInstruction::MUL:
+            return 3;
+        case BinaryMInstruction::DIV:
+            return 4;
+        case BinaryMInstruction::AND:
+            return 1;
+        case BinaryMInstruction::OR:
+            return 1;
+        case BinaryMInstruction::VADD:
+            return 4;
+        case BinaryMInstruction::VSUB:
+            return 4;
+        case BinaryMInstruction::VMUL:
+            return 4;
+        case BinaryMInstruction::VDIV:
+            return 6;
+        default:
+            return 4;
+        }
+    case MachineInstruction::MOV:
+        printISC("    " << "    " << "getInstDelay: MachineInstruction::MOV");
+        switch (inst->getOp())
+        {
+        case MovMInstruction::VMOV:
+            return 5;
+        case MovMInstruction::VMOVF32:
+            return 3;
+        default:
+            return 1;
+        }
+    case MachineInstruction::CMP:
+        printISC("    " << "    " << "getInstDelay: MachineInstruction::CMP");
+        switch (inst->getOp())
+        {
+        case CmpMInstruction::VCMP:
+            return 3;
+        default:
+            return 1;
+        }
+    case MachineInstruction::STACK:
+        printISC("    " << "    " << "getInstDelay: MachineInstruction::STACK");
+        switch (inst->getOp())
+        {
+        case StackMInstruction::POP:
+            return 3 + ((StackMInstruction*)inst)->getUse().size();
+        case StackMInstruction::VPOP:
+            return 4 + ((StackMInstruction*)inst)->getUse().size();
+        default:
+            return ((StackMInstruction*)inst)->getUse().size();
+        }
+    default:
+        printISC("    " << "    " << "getInstDelay: default");
+        return 6;
+    }
+}
+
+void InstructionsScheduling::calculate_priority(int index) {
+    Node* node = Nodelist[index];
+    if (node->pred.empty()) { //ûÓÐÔ¼ÊøÖ¸Áî;
+        node->priority = 0; 
+        // printISC("    " << "    " << "    " << "node->pred is empty.");
+        printISC("    " << "    " << "    " << "node->priority: " << node->priority);
+        return;
+    }
+    for (auto i: node->pred) {
+        if (Nodelist[i]->priority == -1) { //µÝ¹é¼ÆËãÔ¼ÊøÎÒµÄÖ¸ÁîµÄÓÅÏȼ¶;
+            calculate_priority(i);
+        }
+    }
+    for (auto i: node->pred) {
+        int latency = 0;
+        for(auto succ: Nodelist[i]->succ) {
+            if(succ.first == index) {
+                latency = succ.second;
+            }
+        }
+        node->priority = std::max(node->priority, Nodelist[i]->priority + latency); //DP£º¸üе±Ç°ÓÅÏȼ¶£¬Ö»¿ÉÄܽµ¼¶£»
+    }
+    printISC("    " << "    " << "    " << "node->priority: " << node->priority);
+}
+
+void InstructionsScheduling::pass() {
+
+    printISC("InstructionsScheduling::pass begin: ");
+    for (auto func_iter = mUnit->begin(); func_iter != mUnit->end(); func_iter++) {
+        auto func = *func_iter;
+        for (auto block_iter = func->begin(); block_iter != func->end(); block_iter++) {
+            //ÒÔMblockΪµ¥Î»½øÐÐÓÅ»¯:
+            auto block = *block_iter; 
+            printISC("    " << "Process Mblock: " << block->getNo());
+
+            if (block->getInsts().empty()) {
+                continue;
+            }
+            auto Instlist = block->getInsts();
+
+            //´´½¨Êý¾Ý½á¹¹Nodelist²¢¼ÆËãËùÓÐÖ¸Áî¶ÔÓ¦µÄdelay;
+            Nodelist.clear();
+            for(auto inst: Instlist) {
+                Node* node = new Node(inst);
+                int delay = this->getInstDelay(inst);
+                node->delay = delay;
+                Nodelist.push_back(node);
+                // printISC("    " << "    " << "inst: " << inst->getDef()[0]->toStr());
+            }
+
+            printISC("    " << "    " << "Instlist.size: " << Instlist.size());
+            if(Instlist.size() >= 30000) {
+                return;
+            }
+
+            //¹¹½¨Ô¼Êø¹ØÏµ:
+            for(int i = 0; i < Nodelist.size(); i++) {
+                Node* node = Nodelist[i];
+                if(node->inst->getType() == MachineInstruction::STACK) {
+                    for(int j = i; j < Nodelist.size(); j++) {
+                        node->succ.push_back(std::pair(j, node->delay));
+                        if (Nodelist[j]->inst->isBranch()) { 
+                            break;
+                        }
+                    }
+                    continue;
+                }
+                if(node->inst->getType() == MachineInstruction::BRANCH) {
+                    for(int j = i; j < Nodelist.size(); j++) {
+                        node->succ.push_back(std::pair(j, node->delay));
+                    }
+                    continue;
+                }
+                if(node->inst->isSpecial()) {
+                    for(int j = i; j < Nodelist.size(); j++) {
+                        node->succ.push_back(std::pair(j, node->delay));
+                    }
+                    continue;
+                }
+
+                //general situation:
+                for(int j = i; j < Nodelist.size(); j++) {
+                    auto prev_defs = node->inst->getDef();
+                    auto prev_uses = node->inst->getUse();
+                    auto succ_defs = Nodelist[j]->inst->getDef();
+                    auto succ_uses = Nodelist[j]->inst->getUse();
+
+                    //ÓжÁд¹ØÏµµÄ²»ÄÜͬʱ:
+                    if ((node->inst->isLoad() && Nodelist[j]->inst->isStore()) ||
+                        (node->inst->isStore() && Nodelist[j]->inst->isLoad()) ||
+                        (node->inst->isStore() && Nodelist[j]->inst->isStore())) {
+                        node->succ.push_back(std::pair(j, node->delay));
+                    }
+                    for (auto prev_def : prev_defs) {  // RAW
+                        for (auto succ_use : succ_uses) {
+                            if (*prev_def == *succ_use) {
+                                node->succ.push_back(std::pair(j, node->delay));
+                            }
+                        }
+                    }
+                    for (auto prev_use : prev_uses) { // WAR
+                        for (auto succ_def : succ_defs) {
+                            if (*prev_use == *succ_def) {
+                                node->succ.push_back(std::pair(j, node->delay));
+                            }
+                        }
+                    }
+                    for (auto prev_def : prev_defs) { //WAW;
+                        for (auto succ_def : succ_defs) {
+                            if (*prev_def == *succ_def) {
+                                node->succ.push_back(std::pair(j, node->delay));
+                            }
+                        }
+                    }
+
+                    //ÌØÊâÌõ¼þ£º
+                    if (node->inst->isCmp() && Nodelist[j]->inst->isCondMov()) { 
+                        node->succ.push_back(std::pair(j, node->delay));
+                    }
+                    if (Nodelist[j]->inst->isBranch() 
+                        || Nodelist[j]->inst->isVMRS()
+                        || Nodelist[j]->inst->isSpecial()) {
+                        node->succ.push_back(std::pair(j, node->delay));
+                    }
+                }
+                printISC("    " << "    " << "Instlist: " << i << " general"); 
+            }
+
+
+            printISC("    " << "    " << "delete Nodes. ");
+
+            //ɾ³ý²»ºÏÀíµÄÇéÐÎ:
+            for(int i = 0; i < Nodelist.size(); i++) {
+                if(i % 1000 == 0) printISC("    " << "    " << "Instlist: " << i);
+                for(int j = 0; j < Nodelist[i]->succ.size(); j++) {
+                    if(Nodelist[i]->succ[j].first == i) {
+                        Nodelist[i]->succ.erase(Nodelist[i]->succ.begin() + j);
+                        j--;
+                        continue;
+                    }
+                    if(j < Nodelist[i]->succ.size() - 1) {
+                        if(Nodelist[i]->succ[j].first == Nodelist[i]->succ[j + 1].first) {
+                            Nodelist[i]->succ.erase(Nodelist[i]->succ.begin() + j);
+                            j--;
+                        }
+                    }
+                }
+            }
+            printISC("    " << "    " << "delete Nodes success. ");
+
+            for(int i = 0; i < Nodelist.size(); i++) {
+                Node* node = Nodelist[i];
+                for(auto succ: node->succ) {
+                    int j = succ.first;
+                    Nodelist[j]->pred.push_back(i);
+                    Nodelist[j]->degree++;
+                }
+            }
+            printISC("    " << "    " << "build CFG success. ");
+
+            //´òÓ¡¿´ÊÇ·ñÓл·²úÉú:
+            for(int i = 0; i < Nodelist.size(); i++) {
+                printISC("    " << "    " << "    " << "Node " << i << "(degree "
+                        << Nodelist[i]->degree << "): ")
+                for(int j = 0; j < Nodelist[i]->succ.size(); j++) {
+                   printISC("    " << "    " << "    " << "    " 
+                                    << "succ: " << Nodelist[i]->succ[j].first 
+                                    << " dalay: " << Nodelist[i]->succ[j].second) 
+                }
+            }
+
+            //¼ÆËãÓÅÏȼ¶:
+            printISC("    " << "    " << "calculate_priority begin: ");
+            for (size_t i = 0; i < Nodelist.size(); i++) {
+                if(Nodelist[i]->priority == -1) {
+                    printISC("    " << "    " << "    " << "calculate_priority: " << i);
+                    calculate_priority(i);
+                }
+            }
+
+            printISC("    " << "    " << "calculate_priority success. ");
+            
+
+            //Íê³Éµ÷¶È:
+            printISC("    " << "    " << "schedule begin. ");
+            std::vector<Node*> inWaitlist;
+            std::vector<Node*> inPipeline;
+            std::vector<Node*> scheduledList;
+            for (size_t i = 0; i < Nodelist.size(); i++) {
+                if(Nodelist[i]->pred.empty()) {
+                    inWaitlist.push_back(Nodelist[i]);
+                }
+            }
+
+            printISC("    " << "    " << "inWaitlist.size: " << inWaitlist.size());
+
+            int cpuCycle = 0;
+            std::map<Node*, int> inTime;
+            while(!(inWaitlist.empty() && inPipeline.empty())) {
+                printISC("    " << "    " << "    " << "cpuCycle: " << cpuCycle);
+                std::sort(inWaitlist.begin(), inWaitlist.end(), 
+                            [&](Node* a, Node*b) -> bool {return a->priority < b->priority;}); //±ØÐëÊÇ
+                for(auto node = inWaitlist.begin(); node != inWaitlist.end(); ) {
+                    inPipeline.push_back(*node);
+                    inTime[*node] = cpuCycle;
+                    scheduledList.push_back(*node);
+                    printISC("    " << "    " << "    " << "    " << "inPipeline.push_back: " << getIndex(*node))
+                    node = inWaitlist.erase(node);
+                }
+
+                for(auto node = inPipeline.begin(); node != inPipeline.end(); ) {
+                    if((inTime[*node] + (*node)->delay) <= cpuCycle + 1) {
+                        printISC("    " << "    " << "    " << "    " <<  getIndex(*node) << ": " << inTime[*node] + (*node)->delay << " <= " << cpuCycle + 1)                        
+                        for(auto succ : (*node)->succ) {
+                            printISC("    " << "    " << "    " << "    " << "    " << "Nodelist[" << succ.first << "]->degree --");
+                            Nodelist[succ.first]->degree --;
+                            if(Nodelist[succ.first]->degree <= 0) {
+                                inWaitlist.push_back(Nodelist[succ.first]);
+                                printISC("    " << "    " << "    " << "    " << "    " << "    " << "inWaitlist.push_back " << succ.first);
+                            }
+                        }
+                        node = inPipeline.erase(node);
+                        printISC("    " << "    " << "    " << "    " << "inPipeline.erase: " << getIndex(*node));
+                    } else {
+                        node++;
+                    }
+                }
+                cpuCycle ++;
+            }
+
+            printISC("    " << "    " << "schedule succes. ");
+
+
+            //ʹÓÃÖØÐÂÅÅÐòºóµÄÖ¸ÁîÀ´Ìæ´úÔ­ÓÐÖ¸Áî:
+            printISC("    " << "    " << "replace begin. ");
+            std::vector<MachineInstruction*> scheduledInstlist;
+            
+            for (size_t i = 0; i < scheduledList.size(); i++) {
+                printISC("    " << "    " << "    " << "scheduledInstlist.push_back: " << getIndex(scheduledList[i]));
+                scheduledInstlist.push_back(scheduledList[i]->inst);
+            }
+            block->getInsts() = scheduledInstlist;
+
+            printISC("    " << "    " << "replace success. ");
+
+            /*
+            */
+        }
+    }
+}
\ No newline at end of file
diff --git a/src/main.cpp b/src/main.cpp
index 74cb4605e038932b1a3e1b604e680d7de316ecc2..db16e3958387f4d1563c84dbbe190da5e306b8be 100644
--- a/src/main.cpp
+++ b/src/main.cpp
@@ -1,3 +1,4 @@
+#include "InstructionsSchedule.h"
 #include "AccumExpReduction.h"
 #include "Ast.h"
 #include "BlockMerge.h"
@@ -279,6 +280,9 @@ main:
     if (optimize) {
         PeepholeMInstrOpt pmo(&mUnit);
         pmo.pass();
+
+        InstructionsScheduling ISche(&mUnit);
+        ISche.pass();
     }
 
     if (dump_asm)