// File: /workspace/github_cpp_makefile_star2_O3/luooofan[P]hblzbd_compiler/src/Pass/convert_ssa.cpp
// Function: ConvertSSA::ConstructSSA4BB(IRBasicBlock*, SSAFunction*, std::unordered_map<IRBasicBlock*, SSABasicBlock*, std::hash<IRBasicBlock*>, std::equal_to<IRBasicBlock*>, std::allocator<std::pair<IRBasicBlock* const, SSABasicBlock*>>>&)
void ConvertSSA::ConstructSSA4BB(IRBasicBlock* bb, SSAFunction* ssafunc,
                                 std::unordered_map<IRBasicBlock*, SSABasicBlock*>& bb_map) {
  if (nullptr == bb) return;
#ifdef DEBUG_CONSTRUCT_SSA_PROCESS
  std::cout << "---Process BB:" << std::endl;
#endif

  auto ssabb = bb_map[bb];
  MyAssert(nullptr != ssabb);

  // for every ir
  for (auto ir_iter = bb->ir_list_.begin(); ir_iter != bb->ir_list_.end(); ++ir_iter) {
    auto ir = **ir_iter;
#ifdef DEBUG_CONSTRUCT_SSA_PROCESS
    // std::cout << "----Process IR:" << std::endl;
    ir.PrintIR(std::cout);
#endif
    switch (ir.op_) {
      // NOTE: assign和param可能传递i32 pointer 其他传递i32或者void arraytype只在alloca中不会传递
      // 从数组中取元素值只会出现在assign offset ir中 给数组元素赋值只会出现在assign ir中
      case ir::IR::OpKind::ADD:
      case ir::IR::OpKind::SUB:
      case ir::IR::OpKind::MUL:
      case ir::IR::OpKind::DIV:
      case ir::IR::OpKind::MOD: {
        auto lhs = ResolveOpn2Value(&(ir.opn1_), ssabb);
        auto rhs = ResolveOpn2Value(&(ir.opn2_), ssabb);
        auto res_comp_name = ir.res_.GetCompName();
        auto res =
            new BinaryOperator(new Type(Type::IntegerTyID), static_cast<BinaryOperator::OpKind>(GetOpKind(ir.op_)),
                               res_comp_name, lhs, rhs, ssabb);
        ProcessResValue(res_comp_name, &(ir.res_), res, ssabb);
        break;
      }
      case ir::IR::OpKind::NOT:
      case ir::IR::OpKind::NEG: {
        auto lhs = ResolveOpn2Value(&(ir.opn1_), ssabb);
        auto res_comp_name = ir.res_.GetCompName();
        auto res = new UnaryOperator(new Type(Type::IntegerTyID), static_cast<UnaryOperator::OpKind>(GetOpKind(ir.op_)),
                                     res_comp_name, lhs, ssabb);
        ProcessResValue(res_comp_name, &(ir.res_), res, ssabb);
        break;
      }
      case ir::IR::OpKind::LABEL: {  // label ir已经全被删了 执行流不会到这里
        MyAssert(0);
        break;
      }
      case ir::IR::OpKind::PARAM: {  // param ir全部跳过 等call的时候处理
        break;
      }
      case ir::IR::OpKind::CALL: {
        auto func_value = dynamic_cast<FunctionValue*>(glob_map[ir.opn1_.GetCompName()]);
        MyAssert(nullptr != func_value);
        // maintain call_func
        ssafunc->AddCallFunc(func_value);

        CallInst* call_inst = nullptr;
        if (ir.res_.type_ == Opn::Type::Null) {
          call_inst = new CallInst(func_value, ssabb);
        } else {
          auto res_comp_name = ir.res_.GetCompName();
          call_inst = new CallInst(new Type(Type::IntegerTyID), res_comp_name, func_value, ssabb);
          ProcessResValue(res_comp_name, &(ir.res_), call_inst, ssabb);
        }

        // 添加参数
        MyAssert(ir.opn2_.type_ == Opn::Type::Imm);
        // NOTE: a[10][10][10]  func(a[10]) many_params1|2 chaos_token
        static int temp_for_array_address_compute = 1;
        int arg_num = ir.opn2_.imm_num_;
        for (int i = 1; i <= arg_num; ++i) {
          auto param_ir = **(ir_iter - i);
          auto val = ResolveOpn2Value(&(param_ir.opn1_), ssabb);
          if (param_ir.opn1_.type_ == Opn::Type::Array) {
            // 先把基址+偏移算到一个temp value里 再把temp value加到arg里 不必记录
            // param_ir.PrintIR(std::cout);
            auto offset_val = ResolveOpn2Value(param_ir.opn1_.offset_, ssabb) /*一定找得到 不会新加指令*/;
            auto final_address = new BinaryOperator(val->GetType(), BinaryOperator::ADD,
                                                    std::to_string(temp_for_array_address_compute++) + "-temp", val,
                                                    offset_val, call_inst);
            call_inst->AddArg(final_address);
          } else {
            call_inst->AddArg(val);
          }
        }
        break;
      }
      case ir::IR::OpKind::RET: {
        if (ir.opn1_.type_ != ir::Opn::Type::Null) {  // return int;
          auto ret_val = ResolveOpn2Value(&(ir.opn1_), ssabb);
          new ReturnInst(ret_val, ssabb);
        } else {  // return void;
          new ReturnInst(ssabb);
        }
        break;
      }
      case ir::IR::OpKind::GOTO: {
        auto bb_val = dynamic_cast<BasicBlockValue*>(ResolveOpn2Value(&(ir.opn1_), ssabb));
        MyAssert(nullptr != bb_val);
        new BranchInst(bb_val, ssabb);
        break;
      }
      case ir::IR::OpKind::ASSIGN: {
        auto val = ResolveOpn2Value(&(ir.opn1_), ssabb);
        auto res_comp_name = ir.res_.GetCompName();
        Value* res = nullptr;
        if (ir.res_.type_ != ir::Opn::Type::Array) {  // NOTE: consider array address
          if (0 == ir.res_.scope_id_) {
            auto glob_var = glob_map[res_comp_name];
            new StoreInst(val, glob_var, ssabb);

            // maintain used_glob_var
            ssafunc->AddUsedGlobVar(dynamic_cast<GlobalVariable*>(glob_var));
          } else {
            res = new MovInst(val->GetType(), res_comp_name, val, ssabb);
            work_map[res_comp_name] = res;
          }
        } else {
          auto arr_base_ptr = ResolveOpn2Value(&(ir.res_), ssabb);
          MyAssert(arr_base_ptr->GetType()->IsPointer());
          auto offset = ResolveOpn2Value(ir.res_.offset_, ssabb);
          new StoreInst(val, arr_base_ptr, offset, ssabb);
        }
        break;
      }
      case ir::IR::OpKind::ASSIGN_OFFSET: {
        MyAssert(ir.opn1_.type_ == ir::Opn::Type::Array);
        auto arr_base_ptr = ResolveOpn2Value(&(ir.opn1_), ssabb);
        MyAssert(arr_base_ptr->GetType()->IsPointer());
        auto offset = ResolveOpn2Value(ir.opn1_.offset_, ssabb);

        auto res_comp_name = ir.res_.GetCompName();
        auto res = new LoadInst(new Type(Type::IntegerTyID), res_comp_name, arr_base_ptr, offset, ssabb);
        ProcessResValue(res_comp_name, &(ir.res_), res, ssabb);
        break;
      }
      case ir::IR::OpKind::JEQ:
      case ir::IR::OpKind::JNE:
      case ir::IR::OpKind::JLT:
      case ir::IR::OpKind::JLE:
      case ir::IR::OpKind::JGT:
      case ir::IR::OpKind::JGE: {
        auto lhs = ResolveOpn2Value(&(ir.opn1_), ssabb);
        auto rhs = ResolveOpn2Value(&(ir.opn2_), ssabb);
        auto bb_val = dynamic_cast<BasicBlockValue*>(ResolveOpn2Value(&(ir.res_), ssabb));
        MyAssert(nullptr != bb_val);
        new BranchInst(static_cast<BranchInst::Cond>(GetOpKind(ir.op_)), lhs, rhs, bb_val, ssabb);
        break;
      }
      case ir::IR::OpKind::VOID: {
        MyAssert(0);
        break;
      }
      case ir::IR::OpKind::PHI: {
        MyAssert(0 != ir.res_.scope_id_);  // 不会出现全局变量的phi结点
        auto res_comp_name = ir.res_.GetCompName();
        auto phi_inst = new PhiInst(new Type(Type::IntegerTyID), res_comp_name, ssabb);
        // 此时有的变量还未定义 不能在现在填
        // for (int i = 0; i < ir.phi_args_.size(); ++i) {
        //   auto arg_val = ResolveOpn2Value(&ir.phi_args_[i], ssabb);
        //   phi_inst->AddParam(arg_val, bb_map[bb->pred_[i]]->GetValue());
        // }
        ProcessResValue(res_comp_name, &(ir.res_), phi_inst, ssabb);
        break;
      }
      case ir::IR::OpKind::ALLOCA: {
        // alloca opn - imm : alloca quad-ir only for array. regard opn as one dimensional array
        MyAssert(ir.res_.type_ == ir::Opn::Type::Imm);

        // create a value which owns i32 pointer type
        auto ptr_type = new Type(Type::PointerTyID);
        const auto& array_name = ir.opn1_.GetCompName();
        auto value = new Value(ptr_type, array_name);
        work_map[array_name] = value;

        // auto type = new ArrayType(ir.res_.imm_num_);
        // new AllocaInst(type, ssabb);
        new AllocaInst(new ConstantInt(ir.res_.imm_num_), value, ssabb);

        break;
      }
      case ir::IR::OpKind::DECLARE: {
        // 生成argument 记录映射 以防函数参数被认为是未定义变量
        auto arg_comp_name = ir.opn1_.GetCompName();
        if (ir.opn1_.type_ == Opn::Type::Var) {
          work_map[arg_comp_name] =
              new Argument(new Type(Type::IntegerTyID), arg_comp_name, ir.res_.imm_num_, ssafunc->GetValue());
        } else {
          work_map[arg_comp_name] =
              new Argument(new Type(Type::PointerTyID), arg_comp_name, ir.res_.imm_num_, ssafunc->GetValue());
        }
        break;
      }
      default: {
        MyAssert(0);
        break;
      }
    }  // end of ir_op switch
  }    // end of ir for loop
}

// Assembly:
pushq %rbp
pushq %r15
pushq %r14
pushq %r13
pushq %r12
pushq %rbx
subq $0x2d8, %rsp            # imm = 0x2D8
movq %rdx, 0x20(%rsp)
movq %rsi, 0x38(%rsp)
testq %rsi, %rsi
je 0x4304b
movq %rdi, %rbp
leaq 0x38(%rsp), %rsi
movq %rcx, %rdi
callq 0x46ac4
movq (%rax), %rax
movq %rax, 0x10(%rsp)
testq %rax, %rax
je 0x43126
movq 0x38(%rsp), %rax
movq 0x8(%rax), %rbx
cmpq 0x10(%rax), %rbx
je 0x4304b
leaq 0xa8(%rbp), %rax
movq %rax, 0x18(%rsp)
leaq 0xe0(%rbp), %rax
movq %rax, 0x120(%rsp)
movl $0xc8, %eax
leaq 0x40(%rsp), %rcx
leaq (%rcx,%rax), %rdx
movq %rdx, 0x1e0(%rsp)
movl $0xa0, %edx
addq %rdx, %rcx
movq %rcx, 0x1d8(%rsp)
leaq 0x1f8(%rsp), %rcx
addq %rcx, %rax
movq %rax, 0x1f0(%rsp)
addq %rcx, %rdx
movq %rdx, 0x1e8(%rsp)
leaq 0x4c4aa(%rip), %rax     # 0x8e818
addq $0x10, %rax
movq %rax, 0x1b0(%rsp)
movq %rbp, 0x28(%rsp)
movq %rbx, 0x128(%rsp)
movq (%rbx), %rsi
leaq 0x1f8(%rsp), %rdi
callq 0x44118
movl 0x1f8(%rsp), %eax
cmpq $0x17, %rax
ja 0x434a3
leaq 0x2f33d(%rip), %rcx     # 0x716ec
movslq (%rcx,%rax,4), %rax
addq %rcx, %rax
jmpq *%rax
movq %rbp, %rdi
leaq 0x200(%rsp), %rsi
movq 0x10(%rsp), %r15
movq %r15, %rdx
callq 0x4091a
movq %rax, %rbx
movq %rbp, %rdi
leaq 0x240(%rsp), %rsi
movq %r15, %rdx
callq 0x4091a
movq %rax, %r14
movq %rbp, %rdi
leaq 0x280(%rsp), %rsi
movq %r15, %rdx
callq 0x4091a
testq %rax, %rax
je 0x4305d
movq %rax, %rdi
leaq 0x4c071(%rip), %rsi     # 0x8e480
leaq 0x4c0aa(%rip), %rdx     # 0x8e4c0
xorl %ecx, %ecx
callq 0x8320
testq %rax, %rax
je 0x4305d
movq %rax, %r12
movl $0x70, %edi
callq 0x8290
movq %rax, %r15
movl 0x1f8(%rsp), %edi
callq 0x40dd7
movq %r15, %rdi
movl %eax, %esi
movq %rbx, %rdx
movq %r14, %rcx
movq %r12, %r8
movq 0x10(%rsp), %r9
callq 0x44d48
jmp 0x42b68
movq %rbp, %rdi
leaq 0x200(%rsp), %rsi
movq 0x10(%rsp), %rbx
movq %rbx, %rdx
callq 0x4091a
movq %rax, %r14
movq %rbp, %rdi
leaq 0x240(%rsp), %rsi
movq %rbx, %rdx
callq 0x4091a
movq %rax, %r15
leaq 0x40(%rsp), %rdi
leaq 0x280(%rsp), %rsi
callq 0x28a4a
movl $0x70, %edi
callq 0x8290
movq %rax, %rbx
movl $0x10, %edi
callq 0x8290
leaq 0x190(%rsp), %r13
movq %rax, %r12
leaq 0x4c3c5(%rip), %rax     # 0x8e890
movq %rax, (%r12)
movl $0x2, 0x8(%r12)
movl 0x1f8(%rsp), %ebp
leaq 0x1a0(%rsp), %rax
movq %rax, 0x190(%rsp)
movq 0x40(%rsp), %rsi
movq 0x48(%rsp), %rdx
addq %rsi, %rdx
movq %r13, %rdi
callq 0xc6dc
movl %ebp, %edi
callq 0x40dd7
movq 0x10(%rsp), %rcx
movq %rcx, (%rsp)
movq %rbx, %rdi
movq %r12, %rsi
movl %eax, %edx
movq %r13, %rcx
movq %r14, %r8
movq %r15, %r9
callq 0x441d0
movq 0x190(%rsp), %rdi
leaq 0x1a0(%rsp), %rax
cmpq %rax, %rdi
movq 0x28(%rsp), %rbp
je 0x42554
movq 0x1a0(%rsp), %rsi
incq %rsi
callq 0x82a0
movq %rbp, %rdi
leaq 0x40(%rsp), %rsi
leaq 0x280(%rsp), %rdx
movq %rbx, %rcx
movq 0x10(%rsp), %r8
callq 0x4080e
jmp 0x42b4c
movq %rbp, %rdi
leaq 0x200(%rsp), %rsi
movq 0x10(%rsp), %rdx
callq 0x4091a
movq %rax, %r14
leaq 0x40(%rsp), %rdi
leaq 0x280(%rsp), %rsi
callq 0x28a4a
movl $0x70, %edi
callq 0x8290
movq %rax, %rbx
movl $0x10, %edi
callq 0x8290
leaq 0x170(%rsp), %r12
movq %rax, %r15
leaq 0x4c2c7(%rip), %rax     # 0x8e890
movq %rax, (%r15)
movl $0x2, 0x8(%r15)
movl 0x1f8(%rsp), %ebp
leaq 0x180(%rsp), %rax
movq %rax, 0x170(%rsp)
movq 0x40(%rsp), %rsi
movq 0x48(%rsp), %rdx
addq %rsi, %rdx
movq %r12, %rdi
callq 0xc6dc
movl %ebp, %edi
callq 0x40dd7
movq %rbx, %rdi
movq %r15, %rsi
movl %eax, %edx
movq %r12, %rcx
movq %r14, %r8
movq 0x10(%rsp), %r9
callq 0x442c6
movq 0x170(%rsp), %rdi
leaq 0x180(%rsp), %rax
cmpq %rax, %rdi
movq 0x28(%rsp), %rbp
je 0x42649
movq 0x180(%rsp), %rsi
incq %rsi
callq 0x82a0
movq %rbp, %rdi
leaq 0x40(%rsp), %rsi
leaq 0x280(%rsp), %rdx
movq %rbx, %rcx
movq 0x10(%rsp), %r8
callq 0x4080e
jmp 0x42b4c
leaq 0x40(%rsp), %rdi
leaq 0x200(%rsp), %rsi
callq 0x28a4a
cmpl $0x0, 0x200(%rsp)
je 0x42af1
movl $0x50, %edi
callq 0x8290
movq %rax, %rbx
movl $0x10, %edi
callq 0x8290
leaq 0x40(%rsp), %r14
leaq 0x4c1e2(%rip), %rcx     # 0x8e890
movq %rcx, (%rax)
movl $0x4, 0x8(%rax)
movl 0x284(%rsp), %ecx
movq 0x20(%rsp), %rdx
movq 0x28(%rdx), %r8
movq %rbx, %rdi
movq %rax, %rsi
movq %r14, %rdx
callq 0x4507c
movq 0x18(%rsp), %rdi
movq %r14, %rsi
callq 0x463ba
jmp 0x42b49
movq %rbp, %rdi
leaq 0x200(%rsp), %rsi
movq 0x10(%rsp), %rdx
callq 0x4091a
testq %rax, %rax
je 0x430c3
movq %rax, %rdi
leaq 0x4bd70(%rip), %rsi     # 0x8e480
leaq 0x4bda9(%rip), %rdx     # 0x8e4c0
xorl %ecx, %ecx
callq 0x8320
testq %rax, %rax
je 0x430c3
movq %rax, %r14
movl $0x70, %edi
callq 0x8290
movq %rax, %rbx
movq %rax, %rdi
movq %r14, %rsi
movq 0x10(%rsp), %rdx
callq 0x448d2
jmp 0x42b68
leaq 0x40(%rsp), %rbx
movq %rbx, %rdi
leaq 0x200(%rsp), %rsi
callq 0x28a4a
movq 0x120(%rsp), %rdi
movq %rbx, %rsi
callq 0x4671a
movq (%rax), %rdi
testq %rdi, %rdi
je 0x42c01
leaq 0x4bcfc(%rip), %rsi     # 0x8e480
leaq 0x4bd4d(%rip), %rdx     # 0x8e4d8
xorl %ecx, %ecx
callq 0x8320
movq %rax, %rbx
jmp 0x42c03
movq %rbp, %rdi
leaq 0x200(%rsp), %rsi
movq 0x10(%rsp), %rdx
callq 0x4091a
movq %rax, %rbx
leaq 0x40(%rsp), %rdi
leaq 0x280(%rsp), %rsi
callq 0x28a4a
cmpl $0x5, 0x280(%rsp)
jne 0x42aa8
movq %rbp, %rdi
leaq 0x280(%rsp), %rsi
movq 0x10(%rsp), %rdx
callq 0x4091a
movq %rax, %r14
movq 0x8(%rax), %rdi
movq (%rdi), %rax
callq *0x30(%rax)
testb %al, %al
je 0x43509
movq 0x2b0(%rsp), %rsi
movq %rbp, %rdi
movq 0x10(%rsp), %rdx
callq 0x4091a
movq %rax, %r12
movl $0x68, %edi
callq 0x8290
movq %rax, %r15
movq %rax, %rdi
movq %rbx, %rsi
movq %r14, %rdx
movq %r12, %rcx
movq 0x10(%rsp), %r8
callq 0x44aa2
jmp 0x42b4c
cmpl $0x4, 0x200(%rsp)
jne 0x42a6e
movl $0x68, %edi
callq 0x8290
movq %rax, %rbx
movq %rax, %rdi
movq 0x10(%rsp), %rsi
callq 0x4481e
jmp 0x42b68
cmpl $0x1, 0x280(%rsp)
jne 0x432a5
movl $0x10, %edi
callq 0x8290
movq %rax, %r14
leaq 0x4c005(%rip), %rax     # 0x8e890
movq %rax, (%r14)
movl $0x4, 0x8(%r14)
leaq 0x40(%rsp), %rdi
leaq 0x200(%rsp), %rsi
callq 0x28a4a
movl $0x48, %edi
callq 0x8290
movq %rax, %rbx
movq %rax, %rdi
movq %r14, %rsi
leaq 0x40(%rsp), %r14
movq %r14, %rdx
callq 0x34ade
movq 0x18(%rsp), %rdi
movq %r14, %rsi
callq 0x463ba
movq %rbx, (%rax)
movl $0x68, %edi
callq 0x8290
movq %rax, %r15
movl $0x50, %edi
callq 0x8290
movq %rax, %r12
movl 0x284(%rsp), %esi
movq %rax, %rdi
callq 0x43db8
movq %r15, %rdi
movq %r12, %rsi
movq %rbx, %rdx
movq 0x10(%rsp), %rcx
callq 0x44f12
jmp 0x42b4c
cmpl $0x5, 0x200(%rsp)
jne 0x43371
movq %rbp, %rdi
leaq 0x200(%rsp), %rsi
movq 0x10(%rsp), %rdx
callq 0x4091a
movq %rax, %rbx
movq 0x8(%rax), %rdi
movq (%rdi), %rax
callq *0x30(%rax)
testb %al, %al
je 0x433d7
movq 0x230(%rsp), %rsi
movq %rbp, %rdi
movq 0x10(%rsp), %rdx
callq 0x4091a
movq %rax, %r14
leaq 0x40(%rsp), %rdi
leaq 0x280(%rsp), %rsi
callq 0x28a4a
movl $0x68, %edi
callq 0x8290
movq %rax, %r15
movl $0x10, %edi
callq 0x8290
leaq 0x40(%rsp), %r12
movq 0x10(%rsp), %r13
leaq 0x4beed(%rip), %rcx     # 0x8e890
movq %rcx, (%rax)
movl $0x2, 0x8(%rax)
movq %r15, %rdi
movq %rax, %rsi
movq %r12, %rdx
movq %rbx, %rcx
movq %r14, %r8
movq %r13, %r9
callq 0x44c6c
movq %rbp, %rdi
movq %r12, %rsi
leaq 0x280(%rsp), %rdx
movq %r15, %rcx
movq %r13, %r8
callq 0x4080e
jmp 0x42b4c
cmpl $0x0, 0x2a8(%rsp)
je 0x4330b
leaq 0x40(%rsp), %rdi
leaq 0x280(%rsp), %rsi
callq 0x28a4a
movl $0x68, %edi
callq 0x8290
movq %rax, %rbx
movl $0x10, %edi
callq 0x8290
leaq 0x40(%rsp), %r14
movq 0x10(%rsp), %r15
leaq 0x4be66(%rip), %rcx     # 0x8e890
movq %rcx, (%rax)
movl $0x2, 0x8(%rax)
movq %rbx, %rdi
movq %rax, %rsi
movq %r14, %rdx
movq %r15, %rcx
callq 0x336bc
movq 0x1b0(%rsp), %rax
movq %rax, (%rbx)
movq %rbp, %rdi
movq %r14, %rsi
leaq 0x280(%rsp), %rdx
movq %rbx, %rcx
movq %r15, %r8
callq 0x4080e
jmp 0x42b4c
movq %rbp, %rdi
leaq 0x200(%rsp), %rsi
movq 0x10(%rsp), %rdx
callq 0x4091a
movq %rax, %r14
movl $0x68, %edi
callq 0x8290
movq %rax, %rbx
movq %rax, %rdi
movq %r14, %rsi
movq 0x10(%rsp), %rdx
callq 0x446f4
jmp 0x42b68
cmpl $0x0, 0x2a8(%rsp)
je 0x42fe3
movl $0x68, %edi
callq 0x8290
movq %rax, %r15
movq 0x8(%rbx), %rsi
movq %rax, %rdi
leaq 0x40(%rsp), %r14
movq %r14, %rdx
movq %rbx, %rcx
movq 0x10(%rsp), %r8
callq 0x44a04
movq 0x18(%rsp), %rdi
movq %r14, %rsi
callq 0x463ba
movq %r15, (%rax)
jmp 0x42b4c
movl $0x50, %edi
callq 0x8290
movq %rax, %rbx
movl $0x10, %edi
callq 0x8290
leaq 0x40(%rsp), %r14
leaq 0x4bd7c(%rip), %rcx     # 0x8e890
movq %rcx, (%rax)
movl $0x2, 0x8(%rax)
movl 0x284(%rsp), %ecx
movq 0x20(%rsp), %rdx
movq 0x28(%rdx), %r8
movq %rbx, %rdi
movq %rax, %rsi
movq %r14, %rdx
callq 0x4507c
movq 0x18(%rsp), %rdi
movq %r14, %rsi
callq 0x463ba
movq %rbx, (%rax)
movq 0x40(%rsp), %rdi
leaq 0x50(%rsp), %rax
cmpq %rax, %rdi
je 0x42b68
movq 0x50(%rsp), %rsi
incq %rsi
callq 0x82a0
movq 0x1f0(%rsp), %rdi
callq 0x2b81c
movq 0x288(%rsp), %rdi
cmpq 0x1e8(%rsp), %rdi
je 0x42b97
movq 0x298(%rsp), %rsi
incq %rsi
callq 0x82a0
movq 0x248(%rsp), %rdi
leaq 0x258(%rsp), %rax
cmpq %rax, %rdi
movq 0x128(%rsp), %rbx
je 0x42bc4
movq 0x258(%rsp), %rsi
incq %rsi
callq 0x82a0
movq 0x208(%rsp), %rdi
leaq 0x218(%rsp), %rax
cmpq %rax, %rdi
je 0x42be9
movq 0x218(%rsp), %rsi
incq %rsi
callq 0x82a0
addq $0x8, %rbx
movq 0x38(%rsp), %rax
cmpq 0x10(%rax), %rbx
jne 0x4237f
jmp 0x4304b
xorl %ebx, %ebx
movq 0x40(%rsp), %rdi
leaq 0x50(%rsp), %rax
cmpq %rax, %rdi
je 0x42c1f
movq 0x50(%rsp), %rsi
incq %rsi
callq 0x82a0
testq %rbx, %rbx
je 0x431d9
movq 0x20(%rsp), %rdi
movq %rbx, %rsi
callq 0x35760
cmpl $0x4, 0x280(%rsp)
jne 0x42c61
movl $0x68, %edi
callq 0x8290
movq %rax, %r12
movq %rax, %rdi
movq %rbx, %rsi
movq 0x10(%rsp), %rdx
callq 0x44368
jmp 0x42cee
leaq 0x40(%rsp), %rdi
leaq 0x280(%rsp), %rsi
callq 0x28a4a
movl $0x68, %edi
callq 0x8290
movq %rax, %r12
movl $0x10, %edi
callq 0x8290
leaq 0x40(%rsp), %r14
movq 0x10(%rsp), %r15
leaq 0x4bbf5(%rip), %rcx     # 0x8e890
movq %rcx, (%rax)
movl $0x2, 0x8(%rax)
movq %r12, %rdi
movq %rax, %rsi
movq %r14, %rdx
movq %rbx, %rcx
movq %r15, %r8
callq 0x44492
movq %rbp, %rdi
movq %r14, %rsi
leaq 0x280(%rsp), %rdx
movq %r12, %rcx
movq %r15, %r8
callq 0x4080e
movq 0x40(%rsp), %rdi
leaq 0x50(%rsp), %rax
cmpq %rax, %rdi
je 0x42cee
movq 0x50(%rsp), %rsi
incq %rsi
callq 0x82a0
cmpl $0x1, 0x240(%rsp)
jne 0x4343d
movl 0x244(%rsp), %r14d
testl %r14d, %r14d
jle 0x42b68
incq %r14
movl $0x1, %ebx
movq %r14, 0x1b8(%rsp)
leaq (,%rbx,8), %rax
movq 0x128(%rsp), %rcx
subq %rax, %rcx
movq (%rcx), %rsi
leaq 0x40(%rsp), %rdi
callq 0x44118
movq %rbp, %rdi
leaq 0x48(%rsp), %rsi
movq 0x10(%rsp), %rdx
callq 0x4091a
movq %rax, %r15
cmpl $0x5, 0x48(%rsp)
jne 0x42df5
movq 0x78(%rsp), %rsi
movq %rbp, %rdi
movq 0x10(%rsp), %rdx
callq 0x4091a
movq %rax, %r13
movl $0x70, %edi
callq 0x8290
movq %r15, 0x1d0(%rsp)
movq 0x8(%r15), %rcx
movq %rcx, 0x1c0(%rsp)
movl 0x4c56d(%rip), %r15d    # 0x8f304
leal 0x1(%r15), %ecx
movl %ecx, 0x4c563(%rip)     # 0x8f304
movl %r15d, %ebp
negl %ebp
cmovsl %r15d, %ebp
movl $0x1, %r14d
cmpl $0xa, %ebp
jb 0x42e0e
movl $0x4, %r14d
movl %ebp, %esi
cmpl $0x63, %esi
jbe 0x42e05
cmpl $0x3e7, %esi            # imm = 0x3E7
jbe 0x42e0b
cmpl $0x2710, %esi           # imm = 0x2710
jb 0x42e0e
movl %esi, %ecx
movl $0xd1b71759, %edx       # imm = 0xD1B71759
imulq %rdx, %rcx
shrq $0x2d, %rcx
addl $0x4, %r14d
cmpl $0x1869f, %esi          # imm = 0x1869F
movl %ecx, %esi
ja 0x42dbd
addl $-0x3, %r14d
jmp 0x42e0e
movq %r12, %rdi
movq %r15, %rsi
callq 0x44626
jmp 0x42f62
addl $-0x2, %r14d
jmp 0x42e0e
decl %r14d
movq %rbx, 0x1c8(%rsp)
movq %r13, %rbx
movq %rax, 0x30(%rsp)
movq %r12, %r13
shrl $0x1f, %r15d
leal (%r14,%r15), %esi
leaq 0x160(%rsp), %rax
movq %rax, 0x150(%rsp)
leaq 0x150(%rsp), %r12
movq %r12, %rdi
movl $0x2d, %edx
callq 0x8350
addq 0x150(%rsp), %r15
movq %r15, %rdi
movl %r14d, %esi
movl %ebp, %edx
callq 0xc35d
movq %r12, %rdi
leaq 0x2e961(%rip), %rsi     # 0x717ce
callq 0x8590
leaq 0x140(%rsp), %rsi
movq %rsi, 0x130(%rsp)
movq (%rax), %rdx
movq %rax, %rcx
addq $0x10, %rcx
cmpq %rcx, %rdx
movq 0x28(%rsp), %rbp
movq %r13, %r12
movq 0x1b8(%rsp), %r14
je 0x42eb6
movq %rdx, 0x130(%rsp)
movq (%rcx), %rdx
movq %rdx, 0x140(%rsp)
jmp 0x42ebc
movups (%rcx), %xmm0
movups %xmm0, (%rsi)
movq 0x30(%rsp), %r15
movq 0x8(%rax), %rdx
movq %rdx, 0x138(%rsp)
movq %rcx, (%rax)
movq $0x0, 0x8(%rax)
movb $0x0, 0x10(%rax)
movq %r12, (%rsp)
movq %r15, %rdi
movq 0x1c0(%rsp), %rsi
xorl %edx, %edx
leaq 0x130(%rsp), %rcx
movq 0x1d0(%rsp), %r8
movq %rbx, %r9
callq 0x44530
movq 0x1c8(%rsp), %rbx
movq 0x130(%rsp), %rdi
leaq 0x140(%rsp), %rax
cmpq %rax, %rdi
je 0x42f32
movq 0x140(%rsp), %rsi
incq %rsi
callq 0x82a0
movq 0x150(%rsp), %rdi
leaq 0x160(%rsp), %rax
cmpq %rax, %rdi
je 0x42f57
movq 0x160(%rsp), %rsi
incq %rsi
callq 0x82a0
movq %r12, %rdi
movq %r15, %rsi
callq 0x44626
movq 0x1e0(%rsp), %rdi
callq 0x2b81c
movq 0xd0(%rsp), %rdi
cmpq 0x1d8(%rsp), %rdi
je 0x42f91
movq 0xe0(%rsp), %rsi
incq %rsi
callq 0x82a0
movq 0x90(%rsp), %rdi
leaq 0xa0(%rsp), %rax
cmpq %rax, %rdi
je 0x42fb6
movq 0xa0(%rsp), %rsi
incq %rsi
callq 0x82a0
movq 0x50(%rsp), %rdi
leaq 0x60(%rsp), %rax
cmpq %rax, %rdi
je 0x42fd2
movq 0x60(%rsp), %rsi
incq %rsi
callq 0x82a0
incq %rbx
cmpq %r14, %rbx
jne 0x42d1d
jmp 0x42b68
movq 0x120(%rsp), %rdi
leaq 0x40(%rsp), %rsi
callq 0x463ba
movq (%rax), %r14
movl $0x68, %edi
callq 0x8290
movq %rax, %r15
movq %rax, %rdi
movq %rbx, %rsi
movq %r14, %rdx
movq 0x10(%rsp), %rcx
callq 0x43c4e
testq %r14, %r14
je 0x4303a
movq %r14, %rdi
leaq 0x4b459(%rip), %rsi     # 0x8e480
leaq 0x4b462(%rip), %rdx     # 0x8e490
xorl %ecx, %ecx
callq 0x8320
movq %rax, %rsi
jmp 0x4303c
xorl %esi, %esi
movq 0x20(%rsp), %rdi
callq 0x357dc
jmp 0x42b4c
addq $0x2d8, %rsp            # imm = 0x2D8
popq %rbx
popq %r12
popq %r13
popq %r14
popq %r15
popq %rbp
retq
movq 0x4bf84(%rip), %rdi     # 0x8efe8
leaq 0x2b0fd(%rip), %rsi     # 0x6e168
movl $0x8, %edx
callq 0x8330
movq 0x4bf6c(%rip), %rdi     # 0x8efe8
leaq 0x2e725(%rip), %rsi     # 0x717a8
movl $0x18, %edx
callq 0x8330
movq 0x4bf54(%rip), %rdi     # 0x8efe8
leaq 0x2c325(%rip), %rsi     # 0x6f3c0
movl $0x1, %edx
callq 0x8330
movq 0x4bf3c(%rip), %rdi     # 0x8efe8
movl $0x19c, %esi            # imm = 0x19C
callq 0x8520
movq %rax, %rdi
callq 0x8180
jmp 0x4316c
movq 0x4bf1e(%rip), %rdi     # 0x8efe8
leaq 0x2b097(%rip), %rsi     # 0x6e168
movl $0x8, %edx
callq 0x8330
movq 0x4bf06(%rip), %rdi     # 0x8efe8
leaq 0x2e6bf(%rip), %rsi     # 0x717a8
movl $0x18, %edx
callq 0x8330
movq 0x4beee(%rip), %rdi     # 0x8efe8
leaq 0x2c2bf(%rip), %rsi     # 0x6f3c0
movl $0x1, %edx
callq 0x8330
movq 0x4bed6(%rip), %rdi     # 0x8efe8
movl $0x16d, %esi            # imm = 0x16D
callq 0x8520
movq %rax, %rdi
callq 0x8180
jmp 0x4316c
movq 0x4bebb(%rip), %rdi     # 0x8efe8
leaq 0x2b034(%rip), %rsi     # 0x6e168
callq 0x8280
leaq 0x2e668(%rip), %rsi     # 0x717a8
movq %rax, %rdi
callq 0x8280
leaq 0x2c271(%rip), %rsi     # 0x6f3c0
movq %rax, %rdi
callq 0x8280
movq %rax, %rdi
movl $0x113, %esi            # imm = 0x113
callq 0x8520
movq %rax, %rdi
callq 0x8180
movl $0xff, %edi
callq 0x8380
movq 0x4be6b(%rip), %rdi     # 0x8efe8
leaq 0x2afe4(%rip), %rsi     # 0x6e168
movl $0x8, %edx
callq 0x8330
movq 0x4be53(%rip), %rdi     # 0x8efe8
leaq 0x2e60c(%rip), %rsi     # 0x717a8
movl $0x18, %edx
callq 0x8330
movq 0x4be3b(%rip), %rdi     # 0x8efe8
leaq 0x2c20c(%rip), %rsi     # 0x6f3c0
movl $0x1, %edx
callq 0x8330
movq 0x4be23(%rip), %rdi     # 0x8efe8
movl $0x1a1, %esi            # imm = 0x1A1
callq 0x8520
movq %rax, %rdi
callq 0x8180
jmp 0x4316c
movq 0x4be08(%rip), %rdi     # 0x8efe8
leaq 0x2af81(%rip), %rsi     # 0x6e168
movl $0x8, %edx
callq 0x8330
movq 0x4bdf0(%rip), %rdi     # 0x8efe8
leaq 0x2e5a9(%rip), %rsi     # 0x717a8
movl $0x18, %edx
callq 0x8330
movq 0x4bdd8(%rip), %rdi     # 0x8efe8
leaq 0x2c1a9(%rip), %rsi     # 0x6f3c0
movl $0x1, %edx
callq 0x8330
movq 0x4bdc0(%rip), %rdi     # 0x8efe8
movl $0x13f, %esi            # imm = 0x13F
callq 0x8520
movq %rax, %rdi
callq 0x8180
jmp 0x4316c
movq 0x4bda2(%rip), %rdi     # 0x8efe8
leaq 0x2af1b(%rip), %rsi     # 0x6e168
movl $0x8, %edx
callq 0x8330
movq 0x4bd8a(%rip), %rdi     # 0x8efe8
leaq 0x2e543(%rip), %rsi     # 0x717a8
movl $0x18, %edx
callq 0x8330
movq 0x4bd72(%rip), %rdi     # 0x8efe8
leaq 0x2c143(%rip), %rsi     # 0x6f3c0
movl $0x1, %edx
callq 0x8330
movq 0x4bd5a(%rip), %rdi     # 0x8efe8
movl $0x137, %esi            # imm = 0x137
callq 0x8520
movq %rax, %rdi
callq 0x8180
jmp 0x4316c
movq 0x4bd3c(%rip), %rdi     # 0x8efe8
leaq 0x2aeb5(%rip), %rsi     # 0x6e168
movl $0x8, %edx
callq 0x8330
movq 0x4bd24(%rip), %rdi     # 0x8efe8
leaq 0x2e4dd(%rip), %rsi     # 0x717a8
movl $0x18, %edx
callq 0x8330
movq 0x4bd0c(%rip), %rdi     # 0x8efe8
leaq 0x2c0dd(%rip), %rsi     # 0x6f3c0
movl $0x1, %edx
callq 0x8330
movq 0x4bcf4(%rip), %rdi     # 0x8efe8
movl $0x1b2, %esi            # imm = 0x1B2
callq 0x8520
movq %rax, %rdi
callq 0x8180
jmp 0x4316c
movq 0x4bcd6(%rip), %rdi     # 0x8efe8
leaq 0x2ae4f(%rip), %rsi     # 0x6e168
movl $0x8, %edx
callq 0x8330
movq 0x4bcbe(%rip), %rdi     # 0x8efe8
leaq 0x2e477(%rip), %rsi     # 0x717a8
movl $0x18, %edx
callq 0x8330
movq 0x4bca6(%rip), %rdi     # 0x8efe8
leaq 0x2c077(%rip), %rsi     # 0x6f3c0
movl $0x1, %edx
callq 0x8330
movq 0x4bc8e(%rip), %rdi     # 0x8efe8
movl $0x1a5, %esi            # imm = 0x1A5
callq 0x8520
movq %rax, %rdi
callq 0x8180
jmp 0x4316c
movq 0x4bc70(%rip), %rdi     # 0x8efe8
leaq 0x2ade9(%rip), %rsi     # 0x6e168
movl $0x8, %edx
callq 0x8330
movq 0x4bc58(%rip), %rdi     # 0x8efe8
leaq 0x2e411(%rip), %rsi     # 0x717a8
movl $0x18, %edx
callq 0x8330
movq 0x4bc40(%rip), %rdi     # 0x8efe8
leaq 0x2c011(%rip), %rsi     # 0x6f3c0
movl $0x1, %edx
callq 0x8330
movq 0x4bc28(%rip), %rdi     # 0x8efe8
movl $0x189, %esi            # imm = 0x189
callq 0x8520
movq %rax, %rdi
callq 0x8180
jmp 0x4316c
movq 0x4bc0a(%rip), %rdi     # 0x8efe8
leaq 0x2ad83(%rip), %rsi     # 0x6e168
movl $0x8, %edx
callq 0x8330
movq 0x4bbf2(%rip), %rdi     # 0x8efe8
leaq 0x2e3ab(%rip), %rsi     # 0x717a8
movl $0x18, %edx
callq 0x8330
movq 0x4bbda(%rip), %rdi     # 0x8efe8
leaq 0x2bfab(%rip), %rsi     # 0x6f3c0
movl $0x1, %edx
callq 0x8330
movq 0x4bbc2(%rip), %rdi     # 0x8efe8
movl $0x18b, %esi            # imm = 0x18B
callq 0x8520
movq %rax, %rdi
callq 0x8180
jmp 0x4316c
movq 0x4bba4(%rip), %rdi     # 0x8efe8
leaq 0x2ad1d(%rip), %rsi     # 0x6e168
movl $0x8, %edx
callq 0x8330
movq 0x4bb8c(%rip), %rdi     # 0x8efe8
leaq 0x2e345(%rip), %rsi     # 0x717a8
movl $0x18, %edx
callq 0x8330
movq 0x4bb74(%rip), %rdi     # 0x8efe8
leaq 0x2bf45(%rip), %rsi     # 0x6f3c0
movl $0x1, %edx
callq 0x8330
movq 0x4bb5c(%rip), %rdi     # 0x8efe8
movl $0x14d, %esi            # imm = 0x14D
callq 0x8520
movq %rax, %rdi
callq 0x8180
jmp 0x4316c
movq 0x4bb3e(%rip), %rdi     # 0x8efe8
leaq 0x2acb7(%rip), %rsi     # 0x6e168
movl $0x8, %edx
callq 0x8330
movq 0x4bb26(%rip), %rdi     # 0x8efe8
leaq 0x2e2df(%rip), %rsi     # 0x717a8
movl $0x18, %edx
callq 0x8330
movq 0x4bb0e(%rip), %rdi     # 0x8efe8
leaq 0x2bedf(%rip), %rsi     # 0x6f3c0
movl $0x1, %edx
callq 0x8330
movq 0x4baf6(%rip), %rdi     # 0x8efe8
movl $0x1cd, %esi            # imm = 0x1CD
callq 0x8520
movq %rax, %rdi
callq 0x8180
jmp 0x4316c
movq 0x4bad8(%rip), %rdi     # 0x8efe8
leaq 0x2ac51(%rip), %rsi     # 0x6e168
movl $0x8, %edx
callq 0x8330
movq 0x4bac0(%rip), %rdi     # 0x8efe8
leaq 0x2e279(%rip), %rsi     # 0x717a8
movl $0x18, %edx
callq 0x8330
movq 0x4baa8(%rip), %rdi     # 0x8efe8
leaq 0x2be79(%rip), %rsi     # 0x6f3c0
movl $0x1, %edx
callq 0x8330
movq 0x4ba90(%rip), %rdi     # 0x8efe8
movl $0x182, %esi            # imm = 0x182
callq 0x8520
movq %rax, %rdi
callq 0x8180
jmp 0x4316c
jmp 0x43686
jmp 0x43686
jmp 0x437ba
movq %rax, %r14
movl $0x68, %esi
movq %r12, %rdi
jmp 0x437d4
jmp 0x437e1
jmp 0x437e1
jmp 0x4359f
jmp 0x437e1
movq %rax, %r14
movl $0x68, %esi
jmp 0x435fd
jmp 0x43686
jmp 0x437ba
jmp 0x437ba
jmp 0x43656
jmp 0x437e1
jmp 0x437e1
jmp 0x437e1
jmp 0x437ba
movq %rax, %r14
movl $0x68, %esi
movq %r12, %rdi
jmp 0x437b3
jmp 0x437e1
jmp 0x437ba
jmp 0x437e1
jmp 0x437e1
movq %rax, %r14
movl $0x70, %esi
movq %rbx, %rdi
jmp 0x437d4
jmp 0x437ba
jmp 0x437ba
jmp 0x437e1
jmp 0x437e1
jmp 0x437e1
jmp 0x437e1
jmp 0x437e1
movq %rax, %r14
movl $0x50, %esi
movq %r12, %rdi
callq 0x82a0
jmp 0x43689
movq %rax, %r14
movl $0x48, %esi
jmp 0x437b0
jmp 0x437e1
jmp 0x437e1
jmp 0x437e1
movq %rax, %r14
movl $0x50, %esi
jmp 0x437b0
jmp 0x437e1
jmp 0x437ba
jmp 0x43686
jmp 0x437e1
jmp 0x437ba
movq %rax, %r14
movl $0x68, %esi
jmp 0x437b0
movq %rax, %r14
movl $0x68, %esi
movq %r15, %rdi
jmp 0x437b3
jmp 0x437ba
movq %rax, %r14
movq 0x170(%rsp), %rdi
leaq 0x180(%rsp), %rax
cmpq %rax, %rdi
je 0x437ab
movq 0x180(%rsp), %rsi
jmp 0x4370d
jmp 0x437e1
jmp 0x437e1
jmp 0x437e1
jmp 0x437ba
jmp 0x437ba
jmp 0x437a8
jmp 0x437e1
jmp 0x437e1
movq %rax, %r14
movq 0x190(%rsp), %rdi
leaq 0x1a0(%rsp), %rax
cmpq %rax, %rdi
je 0x437ab
movq 0x1a0(%rsp), %rsi
incq %rsi
callq 0x82a0
jmp 0x437ab
jmp 0x437e1
jmp 0x437e1
jmp 0x437e1
movq %rax, %r14
movl $0x70, %esi
movq %r15, %rdi
jmp 0x437d4
jmp 0x437e1
movq %rax, %r14
jmp 0x43770
movq %rax, %r14
jmp 0x43795
movq %rax, %r14
movq 0x130(%rsp), %rdi
leaq 0x140(%rsp), %rax
cmpq %rax, %rdi
je 0x43770
movq 0x140(%rsp), %rsi
incq %rsi
callq 0x82a0
movq 0x150(%rsp), %rdi
leaq 0x160(%rsp), %rax
cmpq %rax, %rdi
je 0x43795
movq 0x160(%rsp), %rsi
incq %rsi
callq 0x82a0
movl $0x70, %esi
movq 0x30(%rsp), %rdi
callq 0x82a0
jmp 0x437e9
jmp 0x437e6
movq %rax, %r14
movl $0x70, %esi
movq %rbx, %rdi
callq 0x82a0
jmp 0x437bd
movq %rax, %r14
movq 0x40(%rsp), %rdi
leaq 0x50(%rsp), %rax
cmpq %rax, %rdi
je 0x437f3
movq 0x50(%rsp), %rsi
incq %rsi
callq 0x82a0
jmp 0x437f3
jmp 0x437e1
jmp 0x437e1
jmp 0x437e6
movq %rax, %r14
jmp 0x437f3
movq %rax, %r14
leaq 0x40(%rsp), %rdi
callq 0x44692
leaq 0x1f8(%rsp), %rdi
callq 0x44692
movq %r14, %rdi
callq 0x8540