Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(172)

Side by Side Diff: src/IceInstX86BaseImpl.h

Issue 1419903002: Subzero: Refactor x86 register definitions to use the alias mechanism. (Closed) Base URL: https://chromium.googlesource.com/native_client/pnacl-subzero.git@master
Patch Set: Add some comments Created 5 years, 1 month ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 //===- subzero/src/IceInstX86BaseImpl.h - Generic X86 instructions -*- C++ -*=// 1 //===- subzero/src/IceInstX86BaseImpl.h - Generic X86 instructions -*- C++ -*=//
2 // 2 //
3 // The Subzero Code Generator 3 // The Subzero Code Generator
4 // 4 //
5 // This file is distributed under the University of Illinois Open Source 5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details. 6 // License. See LICENSE.TXT for details.
7 // 7 //
8 //===----------------------------------------------------------------------===// 8 //===----------------------------------------------------------------------===//
9 /// 9 ///
10 /// \file 10 /// \file
(...skipping 188 matching lines...) Expand 10 before | Expand all | Expand 10 after
199 this->addSource(Source); 199 this->addSource(Source);
200 } 200 }
201 201
202 template <class Machine> 202 template <class Machine>
203 InstX86Cmpxchg<Machine>::InstX86Cmpxchg(Cfg *Func, Operand *DestOrAddr, 203 InstX86Cmpxchg<Machine>::InstX86Cmpxchg(Cfg *Func, Operand *DestOrAddr,
204 Variable *Eax, Variable *Desired, 204 Variable *Eax, Variable *Desired,
205 bool Locked) 205 bool Locked)
206 : InstX86BaseLockable<Machine>(Func, InstX86Base<Machine>::Cmpxchg, 3, 206 : InstX86BaseLockable<Machine>(Func, InstX86Base<Machine>::Cmpxchg, 3,
207 llvm::dyn_cast<Variable>(DestOrAddr), 207 llvm::dyn_cast<Variable>(DestOrAddr),
208 Locked) { 208 Locked) {
209 assert(Eax->getRegNum() == 209 assert(InstX86Base<Machine>::Traits::getBaseReg(Eax->getRegNum()) ==
210 InstX86Base<Machine>::Traits::RegisterSet::Reg_eax); 210 InstX86Base<Machine>::Traits::RegisterSet::Reg_eax);
211 this->addSource(DestOrAddr); 211 this->addSource(DestOrAddr);
212 this->addSource(Eax); 212 this->addSource(Eax);
213 this->addSource(Desired); 213 this->addSource(Desired);
214 } 214 }
215 215
216 template <class Machine> 216 template <class Machine>
217 InstX86Cmpxchg8b<Machine>::InstX86Cmpxchg8b( 217 InstX86Cmpxchg8b<Machine>::InstX86Cmpxchg8b(
218 Cfg *Func, typename InstX86Base<Machine>::Traits::X86OperandMem *Addr, 218 Cfg *Func, typename InstX86Base<Machine>::Traits::X86OperandMem *Addr,
219 Variable *Edx, Variable *Eax, Variable *Ecx, Variable *Ebx, bool Locked) 219 Variable *Edx, Variable *Eax, Variable *Ecx, Variable *Ebx, bool Locked)
(...skipping 294 matching lines...) Expand 10 before | Expand all | Expand 10 after
514 Str << "\tjmp\t*"; 514 Str << "\tjmp\t*";
515 getJmpTarget()->emit(Func); 515 getJmpTarget()->emit(Func);
516 } 516 }
517 517
518 template <class Machine> 518 template <class Machine>
519 void InstX86Jmp<Machine>::emitIAS(const Cfg *Func) const { 519 void InstX86Jmp<Machine>::emitIAS(const Cfg *Func) const {
520 // Note: Adapted (mostly copied) from InstX86Call<Machine>::emitIAS(). 520 // Note: Adapted (mostly copied) from InstX86Call<Machine>::emitIAS().
521 typename InstX86Base<Machine>::Traits::Assembler *Asm = 521 typename InstX86Base<Machine>::Traits::Assembler *Asm =
522 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>(); 522 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>();
523 Operand *Target = getJmpTarget(); 523 Operand *Target = getJmpTarget();
524 if (const auto Var = llvm::dyn_cast<Variable>(Target)) { 524 if (const auto *Var = llvm::dyn_cast<Variable>(Target)) {
525 if (Var->hasReg()) { 525 if (Var->hasReg()) {
526 Asm->jmp(InstX86Base<Machine>::Traits::RegisterSet::getEncodedGPR( 526 Asm->jmp(InstX86Base<Machine>::Traits::getEncodedGPR(Var->getRegNum()));
527 Var->getRegNum()));
528 } else { 527 } else {
529 // The jmp instruction with a memory operand should be possible to 528 // The jmp instruction with a memory operand should be possible to
530 // encode, but it isn't a valid sandboxed instruction, and there 529 // encode, but it isn't a valid sandboxed instruction, and there
531 // shouldn't be a register allocation issue to jump through a scratch 530 // shouldn't be a register allocation issue to jump through a scratch
532 // register, so we don't really need to bother implementing it. 531 // register, so we don't really need to bother implementing it.
533 llvm::report_fatal_error("Assembler can't jmp to memory operand"); 532 llvm::report_fatal_error("Assembler can't jmp to memory operand");
534 } 533 }
535 } else if (const auto Mem = llvm::dyn_cast< 534 } else if (const auto *Mem = llvm::dyn_cast<
536 typename InstX86Base<Machine>::Traits::X86OperandMem>( 535 typename InstX86Base<Machine>::Traits::X86OperandMem>(
537 Target)) { 536 Target)) {
538 (void)Mem; 537 (void)Mem;
539 assert(Mem->getSegmentRegister() == 538 assert(Mem->getSegmentRegister() ==
540 InstX86Base<Machine>::Traits::X86OperandMem::DefaultSegment); 539 InstX86Base<Machine>::Traits::X86OperandMem::DefaultSegment);
541 llvm::report_fatal_error("Assembler can't jmp to memory operand"); 540 llvm::report_fatal_error("Assembler can't jmp to memory operand");
542 } else if (const auto CR = llvm::dyn_cast<ConstantRelocatable>(Target)) { 541 } else if (const auto *CR = llvm::dyn_cast<ConstantRelocatable>(Target)) {
543 assert(CR->getOffset() == 0 && "We only support jumping to a function"); 542 assert(CR->getOffset() == 0 && "We only support jumping to a function");
544 Asm->jmp(CR); 543 Asm->jmp(CR);
545 } else if (const auto Imm = llvm::dyn_cast<ConstantInteger32>(Target)) { 544 } else if (const auto *Imm = llvm::dyn_cast<ConstantInteger32>(Target)) {
546 // NaCl trampoline calls refer to an address within the sandbox directly. 545 // NaCl trampoline calls refer to an address within the sandbox directly.
547 // This is usually only needed for non-IRT builds and otherwise not very 546 // This is usually only needed for non-IRT builds and otherwise not very
548 // portable or stable. Usually this is only done for "calls" and not jumps. 547 // portable or stable. Usually this is only done for "calls" and not jumps.
549 // TODO(jvoung): Support this when there is a lowering that actually 548 // TODO(jvoung): Support this when there is a lowering that actually
550 // triggers this case. 549 // triggers this case.
551 (void)Imm; 550 (void)Imm;
552 llvm::report_fatal_error("Unexpected jmp to absolute address"); 551 llvm::report_fatal_error("Unexpected jmp to absolute address");
553 } else { 552 } else {
554 llvm::report_fatal_error("Unexpected operand type"); 553 llvm::report_fatal_error("Unexpected operand type");
555 } 554 }
556 } 555 }
557 556
558 template <class Machine> void InstX86Jmp<Machine>::dump(const Cfg *Func) const { 557 template <class Machine> void InstX86Jmp<Machine>::dump(const Cfg *Func) const {
559 if (!BuildDefs::dump()) 558 if (!BuildDefs::dump())
560 return; 559 return;
561 Ostream &Str = Func->getContext()->getStrDump(); 560 Ostream &Str = Func->getContext()->getStrDump();
562 Str << "jmp "; 561 Str << "jmp ";
563 getJmpTarget()->dump(Func); 562 getJmpTarget()->dump(Func);
564 } 563 }
565 564
566 template <class Machine> 565 template <class Machine>
567 void InstX86Call<Machine>::emit(const Cfg *Func) const { 566 void InstX86Call<Machine>::emit(const Cfg *Func) const {
568 if (!BuildDefs::dump()) 567 if (!BuildDefs::dump())
569 return; 568 return;
570 Ostream &Str = Func->getContext()->getStrEmit(); 569 Ostream &Str = Func->getContext()->getStrEmit();
571 assert(this->getSrcSize() == 1); 570 assert(this->getSrcSize() == 1);
572 Str << "\tcall\t"; 571 Str << "\tcall\t";
573 if (const auto CI = llvm::dyn_cast<ConstantInteger32>(getCallTarget())) { 572 if (const auto *CI = llvm::dyn_cast<ConstantInteger32>(getCallTarget())) {
574 // Emit without a leading '$'. 573 // Emit without a leading '$'.
575 Str << CI->getValue(); 574 Str << CI->getValue();
576 } else if (const auto CallTarget = 575 } else if (const auto CallTarget =
577 llvm::dyn_cast<ConstantRelocatable>(getCallTarget())) { 576 llvm::dyn_cast<ConstantRelocatable>(getCallTarget())) {
578 CallTarget->emitWithoutPrefix(Func->getTarget()); 577 CallTarget->emitWithoutPrefix(Func->getTarget());
579 } else { 578 } else {
580 Str << "*"; 579 Str << "*";
581 getCallTarget()->emit(Func); 580 getCallTarget()->emit(Func);
582 } 581 }
583 Func->getTarget()->resetStackAdjustment(); 582 Func->getTarget()->resetStackAdjustment();
584 } 583 }
585 584
586 template <class Machine> 585 template <class Machine>
587 void InstX86Call<Machine>::emitIAS(const Cfg *Func) const { 586 void InstX86Call<Machine>::emitIAS(const Cfg *Func) const {
588 typename InstX86Base<Machine>::Traits::Assembler *Asm = 587 typename InstX86Base<Machine>::Traits::Assembler *Asm =
589 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>(); 588 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>();
590 Operand *Target = getCallTarget(); 589 Operand *Target = getCallTarget();
591 if (const auto Var = llvm::dyn_cast<Variable>(Target)) { 590 if (const auto *Var = llvm::dyn_cast<Variable>(Target)) {
592 if (Var->hasReg()) { 591 if (Var->hasReg()) {
593 Asm->call(InstX86Base<Machine>::Traits::RegisterSet::getEncodedGPR( 592 Asm->call(InstX86Base<Machine>::Traits::getEncodedGPR(Var->getRegNum()));
594 Var->getRegNum()));
595 } else { 593 } else {
596 Asm->call( 594 Asm->call(
597 static_cast<typename InstX86Base<Machine>::Traits::TargetLowering *>( 595 static_cast<typename InstX86Base<Machine>::Traits::TargetLowering *>(
598 Func->getTarget()) 596 Func->getTarget())
599 ->stackVarToAsmOperand(Var)); 597 ->stackVarToAsmOperand(Var));
600 } 598 }
601 } else if (const auto Mem = llvm::dyn_cast< 599 } else if (const auto *Mem = llvm::dyn_cast<
602 typename InstX86Base<Machine>::Traits::X86OperandMem>( 600 typename InstX86Base<Machine>::Traits::X86OperandMem>(
603 Target)) { 601 Target)) {
604 assert(Mem->getSegmentRegister() == 602 assert(Mem->getSegmentRegister() ==
605 InstX86Base<Machine>::Traits::X86OperandMem::DefaultSegment); 603 InstX86Base<Machine>::Traits::X86OperandMem::DefaultSegment);
606 Asm->call(Mem->toAsmAddress(Asm)); 604 Asm->call(Mem->toAsmAddress(Asm));
607 } else if (const auto CR = llvm::dyn_cast<ConstantRelocatable>(Target)) { 605 } else if (const auto *CR = llvm::dyn_cast<ConstantRelocatable>(Target)) {
608 assert(CR->getOffset() == 0 && "We only support calling a function"); 606 assert(CR->getOffset() == 0 && "We only support calling a function");
609 Asm->call(CR); 607 Asm->call(CR);
610 } else if (const auto Imm = llvm::dyn_cast<ConstantInteger32>(Target)) { 608 } else if (const auto *Imm = llvm::dyn_cast<ConstantInteger32>(Target)) {
611 Asm->call(Immediate(Imm->getValue())); 609 Asm->call(Immediate(Imm->getValue()));
612 } else { 610 } else {
613 llvm_unreachable("Unexpected operand type"); 611 llvm_unreachable("Unexpected operand type");
614 } 612 }
615 Func->getTarget()->resetStackAdjustment(); 613 Func->getTarget()->resetStackAdjustment();
616 } 614 }
617 615
618 template <class Machine> 616 template <class Machine>
619 void InstX86Call<Machine>::dump(const Cfg *Func) const { 617 void InstX86Call<Machine>::dump(const Cfg *Func) const {
620 if (!BuildDefs::dump()) 618 if (!BuildDefs::dump())
621 return; 619 return;
622 Ostream &Str = Func->getContext()->getStrDump(); 620 Ostream &Str = Func->getContext()->getStrDump();
623 if (this->getDest()) { 621 if (this->getDest()) {
624 this->dumpDest(Func); 622 this->dumpDest(Func);
625 Str << " = "; 623 Str << " = ";
626 } 624 }
627 Str << "call "; 625 Str << "call ";
628 getCallTarget()->dump(Func); 626 getCallTarget()->dump(Func);
629 } 627 }
630 628
631 // The ShiftHack parameter is used to emit "cl" instead of "ecx" for shift 629 // The this->Opcode parameter needs to be char* and not IceString because of
632 // instructions, in order to be syntactically valid. The this->Opcode parameter 630 // template issues.
633 // needs to be char* and not IceString because of template issues.
634 template <class Machine> 631 template <class Machine>
635 void InstX86Base<Machine>::emitTwoAddress(const char *Opcode, const Inst *Inst, 632 void InstX86Base<Machine>::emitTwoAddress(const char *Opcode, const Inst *Inst,
636 const Cfg *Func, bool ShiftHack) { 633 const Cfg *Func) {
637 if (!BuildDefs::dump()) 634 if (!BuildDefs::dump())
638 return; 635 return;
639 Ostream &Str = Func->getContext()->getStrEmit(); 636 Ostream &Str = Func->getContext()->getStrEmit();
640 assert(Inst->getSrcSize() == 2); 637 assert(Inst->getSrcSize() == 2);
641 Operand *Dest = Inst->getDest(); 638 Operand *Dest = Inst->getDest();
642 if (Dest == nullptr) 639 if (Dest == nullptr)
643 Dest = Inst->getSrc(0); 640 Dest = Inst->getSrc(0);
644 assert(Dest == Inst->getSrc(0)); 641 assert(Dest == Inst->getSrc(0));
645 Operand *Src1 = Inst->getSrc(1); 642 Operand *Src1 = Inst->getSrc(1);
646 Str << "\t" << Opcode << InstX86Base<Machine>::getWidthString(Dest->getType()) 643 Str << "\t" << Opcode << InstX86Base<Machine>::getWidthString(Dest->getType())
647 << "\t"; 644 << "\t";
648 const auto ShiftReg = llvm::dyn_cast<Variable>(Src1); 645 Src1->emit(Func);
649 if (ShiftHack && ShiftReg &&
650 ShiftReg->getRegNum() ==
651 InstX86Base<Machine>::Traits::RegisterSet::Reg_ecx)
652 Str << "%cl";
653 else
654 Src1->emit(Func);
655 Str << ", "; 646 Str << ", ";
656 Dest->emit(Func); 647 Dest->emit(Func);
657 } 648 }
658 649
659 template <class Machine> 650 template <class Machine>
660 void emitIASOpTyGPR(const Cfg *Func, Type Ty, const Operand *Op, 651 void emitIASOpTyGPR(const Cfg *Func, Type Ty, const Operand *Op,
661 const typename InstX86Base< 652 const typename InstX86Base<
662 Machine>::Traits::Assembler::GPREmitterOneOp &Emitter) { 653 Machine>::Traits::Assembler::GPREmitterOneOp &Emitter) {
663 typename InstX86Base<Machine>::Traits::Assembler *Asm = 654 typename InstX86Base<Machine>::Traits::Assembler *Asm =
664 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>(); 655 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>();
665 if (const auto Var = llvm::dyn_cast<Variable>(Op)) { 656 if (const auto *Var = llvm::dyn_cast<Variable>(Op)) {
666 if (Var->hasReg()) { 657 if (Var->hasReg()) {
667 // We cheat a little and use GPRRegister even for byte operations. 658 // We cheat a little and use GPRRegister even for byte operations.
668 typename InstX86Base<Machine>::Traits::RegisterSet::GPRRegister VarReg = 659 typename InstX86Base<Machine>::Traits::RegisterSet::GPRRegister VarReg =
669 InstX86Base<Machine>::Traits::RegisterSet::getEncodedByteRegOrGPR( 660 InstX86Base<Machine>::Traits::getEncodedGPR(Var->getRegNum());
670 Ty, Var->getRegNum());
671 (Asm->*(Emitter.Reg))(Ty, VarReg); 661 (Asm->*(Emitter.Reg))(Ty, VarReg);
672 } else { 662 } else {
673 typename InstX86Base<Machine>::Traits::Address StackAddr( 663 typename InstX86Base<Machine>::Traits::Address StackAddr(
674 static_cast<typename InstX86Base<Machine>::Traits::TargetLowering *>( 664 static_cast<typename InstX86Base<Machine>::Traits::TargetLowering *>(
675 Func->getTarget()) 665 Func->getTarget())
676 ->stackVarToAsmOperand(Var)); 666 ->stackVarToAsmOperand(Var));
677 (Asm->*(Emitter.Addr))(Ty, StackAddr); 667 (Asm->*(Emitter.Addr))(Ty, StackAddr);
678 } 668 }
679 } else if (const auto Mem = llvm::dyn_cast< 669 } else if (const auto *Mem = llvm::dyn_cast<
680 typename InstX86Base<Machine>::Traits::X86OperandMem>(Op)) { 670 typename InstX86Base<Machine>::Traits::X86OperandMem>(Op)) {
681 Mem->emitSegmentOverride(Asm); 671 Mem->emitSegmentOverride(Asm);
682 (Asm->*(Emitter.Addr))(Ty, Mem->toAsmAddress(Asm)); 672 (Asm->*(Emitter.Addr))(Ty, Mem->toAsmAddress(Asm));
683 } else { 673 } else {
684 llvm_unreachable("Unexpected operand type"); 674 llvm_unreachable("Unexpected operand type");
685 } 675 }
686 } 676 }
687 677
688 template <class Machine, bool VarCanBeByte, bool SrcCanBeByte> 678 template <class Machine, bool VarCanBeByte, bool SrcCanBeByte>
689 void emitIASRegOpTyGPR( 679 void emitIASRegOpTyGPR(
690 const Cfg *Func, Type Ty, const Variable *Var, const Operand *Src, 680 const Cfg *Func, Type Ty, const Variable *Var, const Operand *Src,
691 const typename InstX86Base<Machine>::Traits::Assembler::GPREmitterRegOp 681 const typename InstX86Base<Machine>::Traits::Assembler::GPREmitterRegOp
692 &Emitter) { 682 &Emitter) {
693 typename InstX86Base<Machine>::Traits::Assembler *Asm = 683 typename InstX86Base<Machine>::Traits::Assembler *Asm =
694 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>(); 684 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>();
695 assert(Var->hasReg()); 685 assert(Var->hasReg());
696 // We cheat a little and use GPRRegister even for byte operations. 686 // We cheat a little and use GPRRegister even for byte operations.
697 typename InstX86Base<Machine>::Traits::RegisterSet::GPRRegister VarReg = 687 typename InstX86Base<Machine>::Traits::RegisterSet::GPRRegister VarReg =
698 VarCanBeByte 688 VarCanBeByte
699 ? InstX86Base<Machine>::Traits::RegisterSet::getEncodedByteRegOrGPR( 689 ? InstX86Base<Machine>::Traits::getEncodedGPR(Var->getRegNum())
700 Ty, Var->getRegNum()) 690 : InstX86Base<Machine>::Traits::getEncodedGPR(Var->getRegNum());
701 : InstX86Base<Machine>::Traits::RegisterSet::getEncodedGPR( 691 if (const auto *SrcVar = llvm::dyn_cast<Variable>(Src)) {
702 Var->getRegNum());
703 if (const auto SrcVar = llvm::dyn_cast<Variable>(Src)) {
704 if (SrcVar->hasReg()) { 692 if (SrcVar->hasReg()) {
705 typename InstX86Base<Machine>::Traits::RegisterSet::GPRRegister SrcReg = 693 typename InstX86Base<Machine>::Traits::RegisterSet::GPRRegister SrcReg =
706 SrcCanBeByte 694 SrcCanBeByte
707 ? InstX86Base<Machine>::Traits::RegisterSet:: 695 ? InstX86Base<Machine>::Traits::getEncodedGPR(SrcVar->getRegNum())
708 getEncodedByteRegOrGPR(Ty, SrcVar->getRegNum()) 696 : InstX86Base<Machine>::Traits::getEncodedGPR(
709 : InstX86Base<Machine>::Traits::RegisterSet::getEncodedGPR(
710 SrcVar->getRegNum()); 697 SrcVar->getRegNum());
711 (Asm->*(Emitter.GPRGPR))(Ty, VarReg, SrcReg); 698 (Asm->*(Emitter.GPRGPR))(Ty, VarReg, SrcReg);
712 } else { 699 } else {
713 typename InstX86Base<Machine>::Traits::Address SrcStackAddr = 700 typename InstX86Base<Machine>::Traits::Address SrcStackAddr =
714 static_cast<typename InstX86Base<Machine>::Traits::TargetLowering *>( 701 static_cast<typename InstX86Base<Machine>::Traits::TargetLowering *>(
715 Func->getTarget()) 702 Func->getTarget())
716 ->stackVarToAsmOperand(SrcVar); 703 ->stackVarToAsmOperand(SrcVar);
717 (Asm->*(Emitter.GPRAddr))(Ty, VarReg, SrcStackAddr); 704 (Asm->*(Emitter.GPRAddr))(Ty, VarReg, SrcStackAddr);
718 } 705 }
719 } else if (const auto Mem = llvm::dyn_cast< 706 } else if (const auto *Mem = llvm::dyn_cast<
720 typename InstX86Base<Machine>::Traits::X86OperandMem>(Src)) { 707 typename InstX86Base<Machine>::Traits::X86OperandMem>(Src)) {
721 Mem->emitSegmentOverride(Asm); 708 Mem->emitSegmentOverride(Asm);
722 (Asm->*(Emitter.GPRAddr))(Ty, VarReg, Mem->toAsmAddress(Asm)); 709 (Asm->*(Emitter.GPRAddr))(Ty, VarReg, Mem->toAsmAddress(Asm));
723 } else if (const auto Imm = llvm::dyn_cast<ConstantInteger32>(Src)) { 710 } else if (const auto *Imm = llvm::dyn_cast<ConstantInteger32>(Src)) {
724 (Asm->*(Emitter.GPRImm))(Ty, VarReg, Immediate(Imm->getValue())); 711 (Asm->*(Emitter.GPRImm))(Ty, VarReg, Immediate(Imm->getValue()));
725 } else if (const auto Reloc = llvm::dyn_cast<ConstantRelocatable>(Src)) { 712 } else if (const auto *Reloc = llvm::dyn_cast<ConstantRelocatable>(Src)) {
726 AssemblerFixup *Fixup = 713 AssemblerFixup *Fixup =
727 Asm->createFixup(InstX86Base<Machine>::Traits::RelFixup, Reloc); 714 Asm->createFixup(InstX86Base<Machine>::Traits::RelFixup, Reloc);
728 (Asm->*(Emitter.GPRImm))(Ty, VarReg, Immediate(Reloc->getOffset(), Fixup)); 715 (Asm->*(Emitter.GPRImm))(Ty, VarReg, Immediate(Reloc->getOffset(), Fixup));
729 } else if (const auto Split = llvm::dyn_cast< 716 } else if (const auto *Split = llvm::dyn_cast<
730 typename InstX86Base<Machine>::Traits::VariableSplit>(Src)) { 717 typename InstX86Base<Machine>::Traits::VariableSplit>(Src)) {
731 (Asm->*(Emitter.GPRAddr))(Ty, VarReg, Split->toAsmAddress(Func)); 718 (Asm->*(Emitter.GPRAddr))(Ty, VarReg, Split->toAsmAddress(Func));
732 } else { 719 } else {
733 llvm_unreachable("Unexpected operand type"); 720 llvm_unreachable("Unexpected operand type");
734 } 721 }
735 } 722 }
736 723
737 template <class Machine> 724 template <class Machine>
738 void emitIASAddrOpTyGPR( 725 void emitIASAddrOpTyGPR(
739 const Cfg *Func, Type Ty, 726 const Cfg *Func, Type Ty,
740 const typename InstX86Base<Machine>::Traits::Address &Addr, 727 const typename InstX86Base<Machine>::Traits::Address &Addr,
741 const Operand *Src, 728 const Operand *Src,
742 const typename InstX86Base<Machine>::Traits::Assembler::GPREmitterAddrOp 729 const typename InstX86Base<Machine>::Traits::Assembler::GPREmitterAddrOp
743 &Emitter) { 730 &Emitter) {
744 typename InstX86Base<Machine>::Traits::Assembler *Asm = 731 typename InstX86Base<Machine>::Traits::Assembler *Asm =
745 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>(); 732 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>();
746 // Src can only be Reg or Immediate. 733 // Src can only be Reg or Immediate.
747 if (const auto SrcVar = llvm::dyn_cast<Variable>(Src)) { 734 if (const auto *SrcVar = llvm::dyn_cast<Variable>(Src)) {
748 assert(SrcVar->hasReg()); 735 assert(SrcVar->hasReg());
749 typename InstX86Base<Machine>::Traits::RegisterSet::GPRRegister SrcReg = 736 typename InstX86Base<Machine>::Traits::RegisterSet::GPRRegister SrcReg =
750 InstX86Base<Machine>::Traits::RegisterSet::getEncodedByteRegOrGPR( 737 InstX86Base<Machine>::Traits::getEncodedGPR(SrcVar->getRegNum());
751 Ty, SrcVar->getRegNum());
752 (Asm->*(Emitter.AddrGPR))(Ty, Addr, SrcReg); 738 (Asm->*(Emitter.AddrGPR))(Ty, Addr, SrcReg);
753 } else if (const auto Imm = llvm::dyn_cast<ConstantInteger32>(Src)) { 739 } else if (const auto *Imm = llvm::dyn_cast<ConstantInteger32>(Src)) {
754 (Asm->*(Emitter.AddrImm))(Ty, Addr, Immediate(Imm->getValue())); 740 (Asm->*(Emitter.AddrImm))(Ty, Addr, Immediate(Imm->getValue()));
755 } else if (const auto Reloc = llvm::dyn_cast<ConstantRelocatable>(Src)) { 741 } else if (const auto *Reloc = llvm::dyn_cast<ConstantRelocatable>(Src)) {
756 AssemblerFixup *Fixup = 742 AssemblerFixup *Fixup =
757 Asm->createFixup(InstX86Base<Machine>::Traits::RelFixup, Reloc); 743 Asm->createFixup(InstX86Base<Machine>::Traits::RelFixup, Reloc);
758 (Asm->*(Emitter.AddrImm))(Ty, Addr, Immediate(Reloc->getOffset(), Fixup)); 744 (Asm->*(Emitter.AddrImm))(Ty, Addr, Immediate(Reloc->getOffset(), Fixup));
759 } else { 745 } else {
760 llvm_unreachable("Unexpected operand type"); 746 llvm_unreachable("Unexpected operand type");
761 } 747 }
762 } 748 }
763 749
764 template <class Machine> 750 template <class Machine>
765 void emitIASAsAddrOpTyGPR( 751 void emitIASAsAddrOpTyGPR(
766 const Cfg *Func, Type Ty, const Operand *Op0, const Operand *Op1, 752 const Cfg *Func, Type Ty, const Operand *Op0, const Operand *Op1,
767 const typename InstX86Base<Machine>::Traits::Assembler::GPREmitterAddrOp 753 const typename InstX86Base<Machine>::Traits::Assembler::GPREmitterAddrOp
768 &Emitter) { 754 &Emitter) {
769 if (const auto Op0Var = llvm::dyn_cast<Variable>(Op0)) { 755 if (const auto *Op0Var = llvm::dyn_cast<Variable>(Op0)) {
770 assert(!Op0Var->hasReg()); 756 assert(!Op0Var->hasReg());
771 typename InstX86Base<Machine>::Traits::Address StackAddr( 757 typename InstX86Base<Machine>::Traits::Address StackAddr(
772 static_cast<typename InstX86Base<Machine>::Traits::TargetLowering *>( 758 static_cast<typename InstX86Base<Machine>::Traits::TargetLowering *>(
773 Func->getTarget()) 759 Func->getTarget())
774 ->stackVarToAsmOperand(Op0Var)); 760 ->stackVarToAsmOperand(Op0Var));
775 emitIASAddrOpTyGPR<Machine>(Func, Ty, StackAddr, Op1, Emitter); 761 emitIASAddrOpTyGPR<Machine>(Func, Ty, StackAddr, Op1, Emitter);
776 } else if (const auto Op0Mem = llvm::dyn_cast< 762 } else if (const auto *Op0Mem = llvm::dyn_cast<
777 typename InstX86Base<Machine>::Traits::X86OperandMem>(Op0)) { 763 typename InstX86Base<Machine>::Traits::X86OperandMem>(Op0)) {
778 typename InstX86Base<Machine>::Traits::Assembler *Asm = 764 typename InstX86Base<Machine>::Traits::Assembler *Asm =
779 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>(); 765 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>();
780 Op0Mem->emitSegmentOverride(Asm); 766 Op0Mem->emitSegmentOverride(Asm);
781 emitIASAddrOpTyGPR<Machine>(Func, Ty, Op0Mem->toAsmAddress(Asm), Op1, 767 emitIASAddrOpTyGPR<Machine>(Func, Ty, Op0Mem->toAsmAddress(Asm), Op1,
782 Emitter); 768 Emitter);
783 } else if (const auto Split = llvm::dyn_cast< 769 } else if (const auto *Split = llvm::dyn_cast<
784 typename InstX86Base<Machine>::Traits::VariableSplit>(Op0)) { 770 typename InstX86Base<Machine>::Traits::VariableSplit>(Op0)) {
785 emitIASAddrOpTyGPR<Machine>(Func, Ty, Split->toAsmAddress(Func), Op1, 771 emitIASAddrOpTyGPR<Machine>(Func, Ty, Split->toAsmAddress(Func), Op1,
786 Emitter); 772 Emitter);
787 } else { 773 } else {
788 llvm_unreachable("Unexpected operand type"); 774 llvm_unreachable("Unexpected operand type");
789 } 775 }
790 } 776 }
791 777
792 template <class Machine> 778 template <class Machine>
793 void InstX86Base<Machine>::emitIASGPRShift( 779 void InstX86Base<Machine>::emitIASGPRShift(
794 const Cfg *Func, Type Ty, const Variable *Var, const Operand *Src, 780 const Cfg *Func, Type Ty, const Variable *Var, const Operand *Src,
795 const typename InstX86Base<Machine>::Traits::Assembler::GPREmitterShiftOp 781 const typename InstX86Base<Machine>::Traits::Assembler::GPREmitterShiftOp
796 &Emitter) { 782 &Emitter) {
797 typename InstX86Base<Machine>::Traits::Assembler *Asm = 783 typename InstX86Base<Machine>::Traits::Assembler *Asm =
798 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>(); 784 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>();
799 // Technically, the Dest Var can be mem as well, but we only use Reg. We can 785 // Technically, the Dest Var can be mem as well, but we only use Reg. We can
800 // extend this to check Dest if we decide to use that form. 786 // extend this to check Dest if we decide to use that form.
801 assert(Var->hasReg()); 787 assert(Var->hasReg());
802 // We cheat a little and use GPRRegister even for byte operations. 788 // We cheat a little and use GPRRegister even for byte operations.
803 typename InstX86Base<Machine>::Traits::RegisterSet::GPRRegister VarReg = 789 typename InstX86Base<Machine>::Traits::RegisterSet::GPRRegister VarReg =
804 InstX86Base<Machine>::Traits::RegisterSet::getEncodedByteRegOrGPR( 790 InstX86Base<Machine>::Traits::getEncodedGPR(Var->getRegNum());
805 Ty, Var->getRegNum());
806 // Src must be reg == ECX or an Imm8. This is asserted by the assembler. 791 // Src must be reg == ECX or an Imm8. This is asserted by the assembler.
807 if (const auto SrcVar = llvm::dyn_cast<Variable>(Src)) { 792 if (const auto *SrcVar = llvm::dyn_cast<Variable>(Src)) {
808 assert(SrcVar->hasReg()); 793 assert(SrcVar->hasReg());
809 typename InstX86Base<Machine>::Traits::RegisterSet::GPRRegister SrcReg = 794 typename InstX86Base<Machine>::Traits::RegisterSet::GPRRegister SrcReg =
810 InstX86Base<Machine>::Traits::RegisterSet::getEncodedByteRegOrGPR( 795 InstX86Base<Machine>::Traits::getEncodedGPR(SrcVar->getRegNum());
811 Ty, SrcVar->getRegNum());
812 (Asm->*(Emitter.GPRGPR))(Ty, VarReg, SrcReg); 796 (Asm->*(Emitter.GPRGPR))(Ty, VarReg, SrcReg);
813 } else if (const auto Imm = llvm::dyn_cast<ConstantInteger32>(Src)) { 797 } else if (const auto *Imm = llvm::dyn_cast<ConstantInteger32>(Src)) {
814 (Asm->*(Emitter.GPRImm))(Ty, VarReg, Immediate(Imm->getValue())); 798 (Asm->*(Emitter.GPRImm))(Ty, VarReg, Immediate(Imm->getValue()));
815 } else { 799 } else {
816 llvm_unreachable("Unexpected operand type"); 800 llvm_unreachable("Unexpected operand type");
817 } 801 }
818 } 802 }
819 803
820 template <class Machine> 804 template <class Machine>
821 void emitIASGPRShiftDouble( 805 void emitIASGPRShiftDouble(
822 const Cfg *Func, const Variable *Dest, const Operand *Src1Op, 806 const Cfg *Func, const Variable *Dest, const Operand *Src1Op,
823 const Operand *Src2Op, 807 const Operand *Src2Op,
824 const typename InstX86Base<Machine>::Traits::Assembler::GPREmitterShiftD 808 const typename InstX86Base<Machine>::Traits::Assembler::GPREmitterShiftD
825 &Emitter) { 809 &Emitter) {
826 typename InstX86Base<Machine>::Traits::Assembler *Asm = 810 typename InstX86Base<Machine>::Traits::Assembler *Asm =
827 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>(); 811 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>();
828 // Dest can be reg or mem, but we only use the reg variant. 812 // Dest can be reg or mem, but we only use the reg variant.
829 assert(Dest->hasReg()); 813 assert(Dest->hasReg());
830 typename InstX86Base<Machine>::Traits::RegisterSet::GPRRegister DestReg = 814 typename InstX86Base<Machine>::Traits::RegisterSet::GPRRegister DestReg =
831 InstX86Base<Machine>::Traits::RegisterSet::getEncodedGPR( 815 InstX86Base<Machine>::Traits::getEncodedGPR(Dest->getRegNum());
832 Dest->getRegNum());
833 // SrcVar1 must be reg. 816 // SrcVar1 must be reg.
834 const auto SrcVar1 = llvm::cast<Variable>(Src1Op); 817 const auto *SrcVar1 = llvm::cast<Variable>(Src1Op);
835 assert(SrcVar1->hasReg()); 818 assert(SrcVar1->hasReg());
836 typename InstX86Base<Machine>::Traits::RegisterSet::GPRRegister SrcReg = 819 typename InstX86Base<Machine>::Traits::RegisterSet::GPRRegister SrcReg =
837 InstX86Base<Machine>::Traits::RegisterSet::getEncodedGPR( 820 InstX86Base<Machine>::Traits::getEncodedGPR(SrcVar1->getRegNum());
838 SrcVar1->getRegNum());
839 Type Ty = SrcVar1->getType(); 821 Type Ty = SrcVar1->getType();
840 // Src2 can be the implicit CL register or an immediate. 822 // Src2 can be the implicit CL register or an immediate.
841 if (const auto Imm = llvm::dyn_cast<ConstantInteger32>(Src2Op)) { 823 if (const auto *Imm = llvm::dyn_cast<ConstantInteger32>(Src2Op)) {
842 (Asm->*(Emitter.GPRGPRImm))(Ty, DestReg, SrcReg, 824 (Asm->*(Emitter.GPRGPRImm))(Ty, DestReg, SrcReg,
843 Immediate(Imm->getValue())); 825 Immediate(Imm->getValue()));
844 } else { 826 } else {
845 assert(llvm::cast<Variable>(Src2Op)->getRegNum() == 827 assert(llvm::cast<Variable>(Src2Op)->getRegNum() ==
846 InstX86Base<Machine>::Traits::RegisterSet::Reg_ecx); 828 InstX86Base<Machine>::Traits::RegisterSet::Reg_cl);
847 (Asm->*(Emitter.GPRGPR))(Ty, DestReg, SrcReg); 829 (Asm->*(Emitter.GPRGPR))(Ty, DestReg, SrcReg);
848 } 830 }
849 } 831 }
850 832
851 template <class Machine> 833 template <class Machine>
852 void emitIASXmmShift( 834 void emitIASXmmShift(
853 const Cfg *Func, Type Ty, const Variable *Var, const Operand *Src, 835 const Cfg *Func, Type Ty, const Variable *Var, const Operand *Src,
854 const typename InstX86Base<Machine>::Traits::Assembler::XmmEmitterShiftOp 836 const typename InstX86Base<Machine>::Traits::Assembler::XmmEmitterShiftOp
855 &Emitter) { 837 &Emitter) {
856 typename InstX86Base<Machine>::Traits::Assembler *Asm = 838 typename InstX86Base<Machine>::Traits::Assembler *Asm =
857 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>(); 839 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>();
858 assert(Var->hasReg()); 840 assert(Var->hasReg());
859 typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister VarReg = 841 typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister VarReg =
860 InstX86Base<Machine>::Traits::RegisterSet::getEncodedXmm( 842 InstX86Base<Machine>::Traits::getEncodedXmm(Var->getRegNum());
861 Var->getRegNum()); 843 if (const auto *SrcVar = llvm::dyn_cast<Variable>(Src)) {
862 if (const auto SrcVar = llvm::dyn_cast<Variable>(Src)) {
863 if (SrcVar->hasReg()) { 844 if (SrcVar->hasReg()) {
864 typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister SrcReg = 845 typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister SrcReg =
865 InstX86Base<Machine>::Traits::RegisterSet::getEncodedXmm( 846 InstX86Base<Machine>::Traits::getEncodedXmm(SrcVar->getRegNum());
866 SrcVar->getRegNum());
867 (Asm->*(Emitter.XmmXmm))(Ty, VarReg, SrcReg); 847 (Asm->*(Emitter.XmmXmm))(Ty, VarReg, SrcReg);
868 } else { 848 } else {
869 typename InstX86Base<Machine>::Traits::Address SrcStackAddr = 849 typename InstX86Base<Machine>::Traits::Address SrcStackAddr =
870 static_cast<typename InstX86Base<Machine>::Traits::TargetLowering *>( 850 static_cast<typename InstX86Base<Machine>::Traits::TargetLowering *>(
871 Func->getTarget()) 851 Func->getTarget())
872 ->stackVarToAsmOperand(SrcVar); 852 ->stackVarToAsmOperand(SrcVar);
873 (Asm->*(Emitter.XmmAddr))(Ty, VarReg, SrcStackAddr); 853 (Asm->*(Emitter.XmmAddr))(Ty, VarReg, SrcStackAddr);
874 } 854 }
875 } else if (const auto Mem = llvm::dyn_cast< 855 } else if (const auto *Mem = llvm::dyn_cast<
876 typename InstX86Base<Machine>::Traits::X86OperandMem>(Src)) { 856 typename InstX86Base<Machine>::Traits::X86OperandMem>(Src)) {
877 assert(Mem->getSegmentRegister() == 857 assert(Mem->getSegmentRegister() ==
878 InstX86Base<Machine>::Traits::X86OperandMem::DefaultSegment); 858 InstX86Base<Machine>::Traits::X86OperandMem::DefaultSegment);
879 (Asm->*(Emitter.XmmAddr))(Ty, VarReg, Mem->toAsmAddress(Asm)); 859 (Asm->*(Emitter.XmmAddr))(Ty, VarReg, Mem->toAsmAddress(Asm));
880 } else if (const auto Imm = llvm::dyn_cast<ConstantInteger32>(Src)) { 860 } else if (const auto *Imm = llvm::dyn_cast<ConstantInteger32>(Src)) {
881 (Asm->*(Emitter.XmmImm))(Ty, VarReg, Immediate(Imm->getValue())); 861 (Asm->*(Emitter.XmmImm))(Ty, VarReg, Immediate(Imm->getValue()));
882 } else { 862 } else {
883 llvm_unreachable("Unexpected operand type"); 863 llvm_unreachable("Unexpected operand type");
884 } 864 }
885 } 865 }
886 866
887 template <class Machine> 867 template <class Machine>
888 void emitIASRegOpTyXMM( 868 void emitIASRegOpTyXMM(
889 const Cfg *Func, Type Ty, const Variable *Var, const Operand *Src, 869 const Cfg *Func, Type Ty, const Variable *Var, const Operand *Src,
890 const typename InstX86Base<Machine>::Traits::Assembler::XmmEmitterRegOp 870 const typename InstX86Base<Machine>::Traits::Assembler::XmmEmitterRegOp
891 &Emitter) { 871 &Emitter) {
892 typename InstX86Base<Machine>::Traits::Assembler *Asm = 872 typename InstX86Base<Machine>::Traits::Assembler *Asm =
893 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>(); 873 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>();
894 assert(Var->hasReg()); 874 assert(Var->hasReg());
895 typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister VarReg = 875 typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister VarReg =
896 InstX86Base<Machine>::Traits::RegisterSet::getEncodedXmm( 876 InstX86Base<Machine>::Traits::getEncodedXmm(Var->getRegNum());
897 Var->getRegNum()); 877 if (const auto *SrcVar = llvm::dyn_cast<Variable>(Src)) {
898 if (const auto SrcVar = llvm::dyn_cast<Variable>(Src)) {
899 if (SrcVar->hasReg()) { 878 if (SrcVar->hasReg()) {
900 typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister SrcReg = 879 typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister SrcReg =
901 InstX86Base<Machine>::Traits::RegisterSet::getEncodedXmm( 880 InstX86Base<Machine>::Traits::getEncodedXmm(SrcVar->getRegNum());
902 SrcVar->getRegNum());
903 (Asm->*(Emitter.XmmXmm))(Ty, VarReg, SrcReg); 881 (Asm->*(Emitter.XmmXmm))(Ty, VarReg, SrcReg);
904 } else { 882 } else {
905 typename InstX86Base<Machine>::Traits::Address SrcStackAddr = 883 typename InstX86Base<Machine>::Traits::Address SrcStackAddr =
906 static_cast<typename InstX86Base<Machine>::Traits::TargetLowering *>( 884 static_cast<typename InstX86Base<Machine>::Traits::TargetLowering *>(
907 Func->getTarget()) 885 Func->getTarget())
908 ->stackVarToAsmOperand(SrcVar); 886 ->stackVarToAsmOperand(SrcVar);
909 (Asm->*(Emitter.XmmAddr))(Ty, VarReg, SrcStackAddr); 887 (Asm->*(Emitter.XmmAddr))(Ty, VarReg, SrcStackAddr);
910 } 888 }
911 } else if (const auto Mem = llvm::dyn_cast< 889 } else if (const auto *Mem = llvm::dyn_cast<
912 typename InstX86Base<Machine>::Traits::X86OperandMem>(Src)) { 890 typename InstX86Base<Machine>::Traits::X86OperandMem>(Src)) {
913 assert(Mem->getSegmentRegister() == 891 assert(Mem->getSegmentRegister() ==
914 InstX86Base<Machine>::Traits::X86OperandMem::DefaultSegment); 892 InstX86Base<Machine>::Traits::X86OperandMem::DefaultSegment);
915 (Asm->*(Emitter.XmmAddr))(Ty, VarReg, Mem->toAsmAddress(Asm)); 893 (Asm->*(Emitter.XmmAddr))(Ty, VarReg, Mem->toAsmAddress(Asm));
916 } else if (const auto Imm = llvm::dyn_cast<Constant>(Src)) { 894 } else if (const auto *Imm = llvm::dyn_cast<Constant>(Src)) {
917 (Asm->*(Emitter.XmmAddr))( 895 (Asm->*(Emitter.XmmAddr))(
918 Ty, VarReg, 896 Ty, VarReg,
919 InstX86Base<Machine>::Traits::Address::ofConstPool(Asm, Imm)); 897 InstX86Base<Machine>::Traits::Address::ofConstPool(Asm, Imm));
920 } else { 898 } else {
921 llvm_unreachable("Unexpected operand type"); 899 llvm_unreachable("Unexpected operand type");
922 } 900 }
923 } 901 }
924 902
925 template <class Machine, typename DReg_t, typename SReg_t, 903 template <class Machine, typename DReg_t, typename SReg_t,
926 DReg_t (*destEnc)(int32_t), SReg_t (*srcEnc)(int32_t)> 904 DReg_t (*destEnc)(int32_t), SReg_t (*srcEnc)(int32_t)>
927 void emitIASCastRegOp(const Cfg *Func, Type DestTy, const Variable *Dest, 905 void emitIASCastRegOp(const Cfg *Func, Type DestTy, const Variable *Dest,
928 Type SrcTy, const Operand *Src, 906 Type SrcTy, const Operand *Src,
929 const typename InstX86Base<Machine>::Traits::Assembler:: 907 const typename InstX86Base<Machine>::Traits::Assembler::
930 template CastEmitterRegOp<DReg_t, SReg_t> &Emitter) { 908 template CastEmitterRegOp<DReg_t, SReg_t> &Emitter) {
931 typename InstX86Base<Machine>::Traits::Assembler *Asm = 909 typename InstX86Base<Machine>::Traits::Assembler *Asm =
932 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>(); 910 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>();
933 assert(Dest->hasReg()); 911 assert(Dest->hasReg());
934 DReg_t DestReg = destEnc(Dest->getRegNum()); 912 DReg_t DestReg = destEnc(Dest->getRegNum());
935 if (const auto SrcVar = llvm::dyn_cast<Variable>(Src)) { 913 if (const auto *SrcVar = llvm::dyn_cast<Variable>(Src)) {
936 if (SrcVar->hasReg()) { 914 if (SrcVar->hasReg()) {
937 SReg_t SrcReg = srcEnc(SrcVar->getRegNum()); 915 SReg_t SrcReg = srcEnc(SrcVar->getRegNum());
938 (Asm->*(Emitter.RegReg))(DestTy, DestReg, SrcTy, SrcReg); 916 (Asm->*(Emitter.RegReg))(DestTy, DestReg, SrcTy, SrcReg);
939 } else { 917 } else {
940 typename InstX86Base<Machine>::Traits::Address SrcStackAddr = 918 typename InstX86Base<Machine>::Traits::Address SrcStackAddr =
941 static_cast<typename InstX86Base<Machine>::Traits::TargetLowering *>( 919 static_cast<typename InstX86Base<Machine>::Traits::TargetLowering *>(
942 Func->getTarget()) 920 Func->getTarget())
943 ->stackVarToAsmOperand(SrcVar); 921 ->stackVarToAsmOperand(SrcVar);
944 (Asm->*(Emitter.RegAddr))(DestTy, DestReg, SrcTy, SrcStackAddr); 922 (Asm->*(Emitter.RegAddr))(DestTy, DestReg, SrcTy, SrcStackAddr);
945 } 923 }
946 } else if (const auto Mem = llvm::dyn_cast< 924 } else if (const auto *Mem = llvm::dyn_cast<
947 typename InstX86Base<Machine>::Traits::X86OperandMem>(Src)) { 925 typename InstX86Base<Machine>::Traits::X86OperandMem>(Src)) {
948 Mem->emitSegmentOverride(Asm); 926 Mem->emitSegmentOverride(Asm);
949 (Asm->*(Emitter.RegAddr))(DestTy, DestReg, SrcTy, Mem->toAsmAddress(Asm)); 927 (Asm->*(Emitter.RegAddr))(DestTy, DestReg, SrcTy, Mem->toAsmAddress(Asm));
950 } else { 928 } else {
951 llvm_unreachable("Unexpected operand type"); 929 llvm_unreachable("Unexpected operand type");
952 } 930 }
953 } 931 }
954 932
955 template <class Machine, typename DReg_t, typename SReg_t, 933 template <class Machine, typename DReg_t, typename SReg_t,
956 DReg_t (*destEnc)(int32_t), SReg_t (*srcEnc)(int32_t)> 934 DReg_t (*destEnc)(int32_t), SReg_t (*srcEnc)(int32_t)>
957 void emitIASThreeOpImmOps( 935 void emitIASThreeOpImmOps(
958 const Cfg *Func, Type DispatchTy, const Variable *Dest, const Operand *Src0, 936 const Cfg *Func, Type DispatchTy, const Variable *Dest, const Operand *Src0,
959 const Operand *Src1, 937 const Operand *Src1,
960 const typename InstX86Base<Machine>::Traits::Assembler:: 938 const typename InstX86Base<Machine>::Traits::Assembler::
961 template ThreeOpImmEmitter<DReg_t, SReg_t> Emitter) { 939 template ThreeOpImmEmitter<DReg_t, SReg_t> Emitter) {
962 typename InstX86Base<Machine>::Traits::Assembler *Asm = 940 typename InstX86Base<Machine>::Traits::Assembler *Asm =
963 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>(); 941 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>();
964 // This only handles Dest being a register, and Src1 being an immediate. 942 // This only handles Dest being a register, and Src1 being an immediate.
965 assert(Dest->hasReg()); 943 assert(Dest->hasReg());
966 DReg_t DestReg = destEnc(Dest->getRegNum()); 944 DReg_t DestReg = destEnc(Dest->getRegNum());
967 Immediate Imm(llvm::cast<ConstantInteger32>(Src1)->getValue()); 945 Immediate Imm(llvm::cast<ConstantInteger32>(Src1)->getValue());
968 if (const auto SrcVar = llvm::dyn_cast<Variable>(Src0)) { 946 if (const auto *SrcVar = llvm::dyn_cast<Variable>(Src0)) {
969 if (SrcVar->hasReg()) { 947 if (SrcVar->hasReg()) {
970 SReg_t SrcReg = srcEnc(SrcVar->getRegNum()); 948 SReg_t SrcReg = srcEnc(SrcVar->getRegNum());
971 (Asm->*(Emitter.RegRegImm))(DispatchTy, DestReg, SrcReg, Imm); 949 (Asm->*(Emitter.RegRegImm))(DispatchTy, DestReg, SrcReg, Imm);
972 } else { 950 } else {
973 typename InstX86Base<Machine>::Traits::Address SrcStackAddr = 951 typename InstX86Base<Machine>::Traits::Address SrcStackAddr =
974 static_cast<typename InstX86Base<Machine>::Traits::TargetLowering *>( 952 static_cast<typename InstX86Base<Machine>::Traits::TargetLowering *>(
975 Func->getTarget()) 953 Func->getTarget())
976 ->stackVarToAsmOperand(SrcVar); 954 ->stackVarToAsmOperand(SrcVar);
977 (Asm->*(Emitter.RegAddrImm))(DispatchTy, DestReg, SrcStackAddr, Imm); 955 (Asm->*(Emitter.RegAddrImm))(DispatchTy, DestReg, SrcStackAddr, Imm);
978 } 956 }
979 } else if (const auto Mem = llvm::dyn_cast< 957 } else if (const auto *Mem = llvm::dyn_cast<
980 typename InstX86Base<Machine>::Traits::X86OperandMem>(Src0)) { 958 typename InstX86Base<Machine>::Traits::X86OperandMem>(Src0)) {
981 Mem->emitSegmentOverride(Asm); 959 Mem->emitSegmentOverride(Asm);
982 (Asm->*(Emitter.RegAddrImm))(DispatchTy, DestReg, Mem->toAsmAddress(Asm), 960 (Asm->*(Emitter.RegAddrImm))(DispatchTy, DestReg, Mem->toAsmAddress(Asm),
983 Imm); 961 Imm);
984 } else { 962 } else {
985 llvm_unreachable("Unexpected operand type"); 963 llvm_unreachable("Unexpected operand type");
986 } 964 }
987 } 965 }
988 966
989 template <class Machine> 967 template <class Machine>
990 void emitIASMovlikeXMM( 968 void emitIASMovlikeXMM(
991 const Cfg *Func, const Variable *Dest, const Operand *Src, 969 const Cfg *Func, const Variable *Dest, const Operand *Src,
992 const typename InstX86Base<Machine>::Traits::Assembler::XmmEmitterMovOps 970 const typename InstX86Base<Machine>::Traits::Assembler::XmmEmitterMovOps
993 Emitter) { 971 Emitter) {
994 typename InstX86Base<Machine>::Traits::Assembler *Asm = 972 typename InstX86Base<Machine>::Traits::Assembler *Asm =
995 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>(); 973 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>();
996 if (Dest->hasReg()) { 974 if (Dest->hasReg()) {
997 typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister DestReg = 975 typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister DestReg =
998 InstX86Base<Machine>::Traits::RegisterSet::getEncodedXmm( 976 InstX86Base<Machine>::Traits::getEncodedXmm(Dest->getRegNum());
999 Dest->getRegNum()); 977 if (const auto *SrcVar = llvm::dyn_cast<Variable>(Src)) {
1000 if (const auto SrcVar = llvm::dyn_cast<Variable>(Src)) {
1001 if (SrcVar->hasReg()) { 978 if (SrcVar->hasReg()) {
1002 (Asm->*(Emitter.XmmXmm))( 979 (Asm->*(Emitter.XmmXmm))(
1003 DestReg, InstX86Base<Machine>::Traits::RegisterSet::getEncodedXmm( 980 DestReg,
1004 SrcVar->getRegNum())); 981 InstX86Base<Machine>::Traits::getEncodedXmm(SrcVar->getRegNum()));
1005 } else { 982 } else {
1006 typename InstX86Base<Machine>::Traits::Address StackAddr( 983 typename InstX86Base<Machine>::Traits::Address StackAddr(
1007 static_cast<typename InstX86Base<Machine>::Traits::TargetLowering 984 static_cast<typename InstX86Base<Machine>::Traits::TargetLowering
1008 *>(Func->getTarget()) 985 *>(Func->getTarget())
1009 ->stackVarToAsmOperand(SrcVar)); 986 ->stackVarToAsmOperand(SrcVar));
1010 (Asm->*(Emitter.XmmAddr))(DestReg, StackAddr); 987 (Asm->*(Emitter.XmmAddr))(DestReg, StackAddr);
1011 } 988 }
1012 } else if (const auto SrcMem = llvm::dyn_cast< 989 } else if (const auto *SrcMem = llvm::dyn_cast<
1013 typename InstX86Base<Machine>::Traits::X86OperandMem>(Src)) { 990 typename InstX86Base<Machine>::Traits::X86OperandMem>(Src)) {
1014 assert(SrcMem->getSegmentRegister() == 991 assert(SrcMem->getSegmentRegister() ==
1015 InstX86Base<Machine>::Traits::X86OperandMem::DefaultSegment); 992 InstX86Base<Machine>::Traits::X86OperandMem::DefaultSegment);
1016 (Asm->*(Emitter.XmmAddr))(DestReg, SrcMem->toAsmAddress(Asm)); 993 (Asm->*(Emitter.XmmAddr))(DestReg, SrcMem->toAsmAddress(Asm));
1017 } else { 994 } else {
1018 llvm_unreachable("Unexpected operand type"); 995 llvm_unreachable("Unexpected operand type");
1019 } 996 }
1020 } else { 997 } else {
1021 typename InstX86Base<Machine>::Traits::Address StackAddr( 998 typename InstX86Base<Machine>::Traits::Address StackAddr(
1022 static_cast<typename InstX86Base<Machine>::Traits::TargetLowering *>( 999 static_cast<typename InstX86Base<Machine>::Traits::TargetLowering *>(
1023 Func->getTarget()) 1000 Func->getTarget())
1024 ->stackVarToAsmOperand(Dest)); 1001 ->stackVarToAsmOperand(Dest));
1025 // Src must be a register in this case. 1002 // Src must be a register in this case.
1026 const auto SrcVar = llvm::cast<Variable>(Src); 1003 const auto *SrcVar = llvm::cast<Variable>(Src);
1027 assert(SrcVar->hasReg()); 1004 assert(SrcVar->hasReg());
1028 (Asm->*(Emitter.AddrXmm))( 1005 (Asm->*(Emitter.AddrXmm))(
1029 StackAddr, InstX86Base<Machine>::Traits::RegisterSet::getEncodedXmm( 1006 StackAddr,
1030 SrcVar->getRegNum())); 1007 InstX86Base<Machine>::Traits::getEncodedXmm(SrcVar->getRegNum()));
1031 } 1008 }
1032 } 1009 }
1033 1010
1034 template <class Machine> 1011 template <class Machine>
1035 void InstX86Sqrtss<Machine>::emit(const Cfg *Func) const { 1012 void InstX86Sqrtss<Machine>::emit(const Cfg *Func) const {
1036 if (!BuildDefs::dump()) 1013 if (!BuildDefs::dump())
1037 return; 1014 return;
1038 Ostream &Str = Func->getContext()->getStrEmit(); 1015 Ostream &Str = Func->getContext()->getStrEmit();
1039 assert(this->getSrcSize() == 1); 1016 assert(this->getSrcSize() == 1);
1040 Type Ty = this->getSrc(0)->getType(); 1017 Type Ty = this->getSrc(0)->getType();
(...skipping 244 matching lines...) Expand 10 before | Expand all | Expand 10 after
1285 1262
1286 template <class Machine> 1263 template <class Machine>
1287 void InstX86Imul<Machine>::emit(const Cfg *Func) const { 1264 void InstX86Imul<Machine>::emit(const Cfg *Func) const {
1288 if (!BuildDefs::dump()) 1265 if (!BuildDefs::dump())
1289 return; 1266 return;
1290 Ostream &Str = Func->getContext()->getStrEmit(); 1267 Ostream &Str = Func->getContext()->getStrEmit();
1291 assert(this->getSrcSize() == 2); 1268 assert(this->getSrcSize() == 2);
1292 Variable *Dest = this->getDest(); 1269 Variable *Dest = this->getDest();
1293 if (isByteSizedArithType(Dest->getType())) { 1270 if (isByteSizedArithType(Dest->getType())) {
1294 // The 8-bit version of imul only allows the form "imul r/m8". 1271 // The 8-bit version of imul only allows the form "imul r/m8".
1295 const auto Src0Var = llvm::dyn_cast<Variable>(this->getSrc(0)); 1272 const auto *Src0Var = llvm::dyn_cast<Variable>(this->getSrc(0));
1296 (void)Src0Var; 1273 (void)Src0Var;
1297 assert(Src0Var && 1274 assert(Src0Var->getRegNum() ==
1298 Src0Var->getRegNum() == 1275 InstX86Base<Machine>::Traits::RegisterSet::Reg_al);
1299 InstX86Base<Machine>::Traits::RegisterSet::Reg_eax);
1300 Str << "\timulb\t"; 1276 Str << "\timulb\t";
1301 this->getSrc(1)->emit(Func); 1277 this->getSrc(1)->emit(Func);
1302 } else if (llvm::isa<Constant>(this->getSrc(1))) { 1278 } else if (llvm::isa<Constant>(this->getSrc(1))) {
1303 Str << "\timul" << this->getWidthString(Dest->getType()) << "\t"; 1279 Str << "\timul" << this->getWidthString(Dest->getType()) << "\t";
1304 this->getSrc(1)->emit(Func); 1280 this->getSrc(1)->emit(Func);
1305 Str << ", "; 1281 Str << ", ";
1306 this->getSrc(0)->emit(Func); 1282 this->getSrc(0)->emit(Func);
1307 Str << ", "; 1283 Str << ", ";
1308 Dest->emit(Func); 1284 Dest->emit(Func);
1309 } else { 1285 } else {
1310 this->emitTwoAddress("imul", this, Func); 1286 this->emitTwoAddress("imul", this, Func);
1311 } 1287 }
1312 } 1288 }
1313 1289
1314 template <class Machine> 1290 template <class Machine>
1315 void InstX86Imul<Machine>::emitIAS(const Cfg *Func) const { 1291 void InstX86Imul<Machine>::emitIAS(const Cfg *Func) const {
1316 assert(this->getSrcSize() == 2); 1292 assert(this->getSrcSize() == 2);
1317 const Variable *Var = this->getDest(); 1293 const Variable *Var = this->getDest();
1318 Type Ty = Var->getType(); 1294 Type Ty = Var->getType();
1319 const Operand *Src = this->getSrc(1); 1295 const Operand *Src = this->getSrc(1);
1320 if (isByteSizedArithType(Ty)) { 1296 if (isByteSizedArithType(Ty)) {
1321 // The 8-bit version of imul only allows the form "imul r/m8". 1297 // The 8-bit version of imul only allows the form "imul r/m8".
1322 const auto Src0Var = llvm::dyn_cast<Variable>(this->getSrc(0)); 1298 const auto *Src0Var = llvm::dyn_cast<Variable>(this->getSrc(0));
1323 (void)Src0Var; 1299 (void)Src0Var;
1324 assert(Src0Var && 1300 assert(Src0Var->getRegNum() ==
1325 Src0Var->getRegNum() == 1301 InstX86Base<Machine>::Traits::RegisterSet::Reg_al);
1326 InstX86Base<Machine>::Traits::RegisterSet::Reg_eax);
1327 static const typename InstX86Base< 1302 static const typename InstX86Base<
1328 Machine>::Traits::Assembler::GPREmitterOneOp Emitter = { 1303 Machine>::Traits::Assembler::GPREmitterOneOp Emitter = {
1329 &InstX86Base<Machine>::Traits::Assembler::imul, 1304 &InstX86Base<Machine>::Traits::Assembler::imul,
1330 &InstX86Base<Machine>::Traits::Assembler::imul}; 1305 &InstX86Base<Machine>::Traits::Assembler::imul};
1331 emitIASOpTyGPR<Machine>(Func, Ty, this->getSrc(1), Emitter); 1306 emitIASOpTyGPR<Machine>(Func, Ty, this->getSrc(1), Emitter);
1332 } else { 1307 } else {
1333 // The two-address version is used when multiplying by a non-constant 1308 // The two-address version is used when multiplying by a non-constant
1334 // or doing an 8-bit multiply. 1309 // or doing an 8-bit multiply.
1335 assert(Var == this->getSrc(0)); 1310 assert(Var == this->getSrc(0));
1336 static const typename InstX86Base< 1311 static const typename InstX86Base<
(...skipping 30 matching lines...) Expand all
1367 assert(llvm::isa<Constant>(this->getSrc(1))); 1342 assert(llvm::isa<Constant>(this->getSrc(1)));
1368 static const typename InstX86Base<Machine>::Traits::Assembler:: 1343 static const typename InstX86Base<Machine>::Traits::Assembler::
1369 template ThreeOpImmEmitter< 1344 template ThreeOpImmEmitter<
1370 typename InstX86Base<Machine>::Traits::RegisterSet::GPRRegister, 1345 typename InstX86Base<Machine>::Traits::RegisterSet::GPRRegister,
1371 typename InstX86Base<Machine>::Traits::RegisterSet::GPRRegister> 1346 typename InstX86Base<Machine>::Traits::RegisterSet::GPRRegister>
1372 Emitter = {&InstX86Base<Machine>::Traits::Assembler::imul, 1347 Emitter = {&InstX86Base<Machine>::Traits::Assembler::imul,
1373 &InstX86Base<Machine>::Traits::Assembler::imul}; 1348 &InstX86Base<Machine>::Traits::Assembler::imul};
1374 emitIASThreeOpImmOps< 1349 emitIASThreeOpImmOps<
1375 Machine, typename InstX86Base<Machine>::Traits::RegisterSet::GPRRegister, 1350 Machine, typename InstX86Base<Machine>::Traits::RegisterSet::GPRRegister,
1376 typename InstX86Base<Machine>::Traits::RegisterSet::GPRRegister, 1351 typename InstX86Base<Machine>::Traits::RegisterSet::GPRRegister,
1377 InstX86Base<Machine>::Traits::RegisterSet::getEncodedGPR, 1352 InstX86Base<Machine>::Traits::getEncodedGPR,
1378 InstX86Base<Machine>::Traits::RegisterSet::getEncodedGPR>( 1353 InstX86Base<Machine>::Traits::getEncodedGPR>(
1379 Func, Ty, Dest, this->getSrc(0), this->getSrc(1), Emitter); 1354 Func, Ty, Dest, this->getSrc(0), this->getSrc(1), Emitter);
1380 } 1355 }
1381 1356
1382 template <class Machine> 1357 template <class Machine>
1383 void InstX86Insertps<Machine>::emitIAS(const Cfg *Func) const { 1358 void InstX86Insertps<Machine>::emitIAS(const Cfg *Func) const {
1384 assert(this->getSrcSize() == 3); 1359 assert(this->getSrcSize() == 3);
1385 assert(static_cast<typename InstX86Base<Machine>::Traits::TargetLowering *>( 1360 assert(static_cast<typename InstX86Base<Machine>::Traits::TargetLowering *>(
1386 Func->getTarget()) 1361 Func->getTarget())
1387 ->getInstructionSet() >= InstX86Base<Machine>::Traits::SSE4_1); 1362 ->getInstructionSet() >= InstX86Base<Machine>::Traits::SSE4_1);
1388 const Variable *Dest = this->getDest(); 1363 const Variable *Dest = this->getDest();
1389 assert(Dest == this->getSrc(0)); 1364 assert(Dest == this->getSrc(0));
1390 Type Ty = Dest->getType(); 1365 Type Ty = Dest->getType();
1391 static const typename InstX86Base<Machine>::Traits::Assembler:: 1366 static const typename InstX86Base<Machine>::Traits::Assembler::
1392 template ThreeOpImmEmitter< 1367 template ThreeOpImmEmitter<
1393 typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister, 1368 typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister,
1394 typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister> 1369 typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister>
1395 Emitter = {&InstX86Base<Machine>::Traits::Assembler::insertps, 1370 Emitter = {&InstX86Base<Machine>::Traits::Assembler::insertps,
1396 &InstX86Base<Machine>::Traits::Assembler::insertps}; 1371 &InstX86Base<Machine>::Traits::Assembler::insertps};
1397 emitIASThreeOpImmOps< 1372 emitIASThreeOpImmOps<
1398 Machine, typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister, 1373 Machine, typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister,
1399 typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister, 1374 typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister,
1400 InstX86Base<Machine>::Traits::RegisterSet::getEncodedXmm, 1375 InstX86Base<Machine>::Traits::getEncodedXmm,
1401 InstX86Base<Machine>::Traits::RegisterSet::getEncodedXmm>( 1376 InstX86Base<Machine>::Traits::getEncodedXmm>(
1402 Func, Ty, Dest, this->getSrc(1), this->getSrc(2), Emitter); 1377 Func, Ty, Dest, this->getSrc(1), this->getSrc(2), Emitter);
1403 } 1378 }
1404 1379
1405 template <class Machine> 1380 template <class Machine>
1406 void InstX86Cbwdq<Machine>::emit(const Cfg *Func) const { 1381 void InstX86Cbwdq<Machine>::emit(const Cfg *Func) const {
1407 if (!BuildDefs::dump()) 1382 if (!BuildDefs::dump())
1408 return; 1383 return;
1409 Ostream &Str = Func->getContext()->getStrEmit(); 1384 Ostream &Str = Func->getContext()->getStrEmit();
1410 assert(this->getSrcSize() == 1); 1385 assert(this->getSrcSize() == 1);
1411 Operand *Src0 = this->getSrc(0); 1386 Operand *Src0 = this->getSrc(0);
1412 assert(llvm::isa<Variable>(Src0)); 1387 assert(llvm::isa<Variable>(Src0));
1413 assert(llvm::cast<Variable>(Src0)->getRegNum() ==
1414 InstX86Base<Machine>::Traits::RegisterSet::Reg_eax);
1415 switch (Src0->getType()) { 1388 switch (Src0->getType()) {
1416 default: 1389 default:
1417 llvm_unreachable("unexpected source type!"); 1390 llvm_unreachable("unexpected source type!");
1418 break; 1391 break;
1419 case IceType_i8: 1392 case IceType_i8:
1393 assert(llvm::cast<Variable>(Src0)->getRegNum() ==
1394 InstX86Base<Machine>::Traits::RegisterSet::Reg_al);
1420 assert(this->getDest()->getRegNum() == 1395 assert(this->getDest()->getRegNum() ==
1421 InstX86Base<Machine>::Traits::RegisterSet::Reg_eax); 1396 InstX86Base<Machine>::Traits::RegisterSet::Reg_ax);
1422 Str << "\t" 1397 Str << "\t"
1423 << "cbtw"; 1398 << "cbtw";
1424 break; 1399 break;
1425 case IceType_i16: 1400 case IceType_i16:
1401 assert(llvm::cast<Variable>(Src0)->getRegNum() ==
1402 InstX86Base<Machine>::Traits::RegisterSet::Reg_ax);
1426 assert(this->getDest()->getRegNum() == 1403 assert(this->getDest()->getRegNum() ==
1427 InstX86Base<Machine>::Traits::RegisterSet::Reg_edx); 1404 InstX86Base<Machine>::Traits::RegisterSet::Reg_dx);
1428 Str << "\t" 1405 Str << "\t"
1429 << "cwtd"; 1406 << "cwtd";
1430 break; 1407 break;
1431 case IceType_i32: 1408 case IceType_i32:
1409 assert(llvm::cast<Variable>(Src0)->getRegNum() ==
1410 InstX86Base<Machine>::Traits::RegisterSet::Reg_eax);
1432 assert(this->getDest()->getRegNum() == 1411 assert(this->getDest()->getRegNum() ==
1433 InstX86Base<Machine>::Traits::RegisterSet::Reg_edx); 1412 InstX86Base<Machine>::Traits::RegisterSet::Reg_edx);
1434 Str << "\t" 1413 Str << "\t"
1435 << "cltd"; 1414 << "cltd";
1436 break; 1415 break;
1437 case IceType_i64: 1416 case IceType_i64:
1438 assert(this->getDest()->getRegNum() == 1417 assert(this->getDest()->getRegNum() ==
1439 InstX86Base<Machine>::Traits::RegisterSet::Reg_edx); 1418 InstX86Base<Machine>::Traits::RegisterSet::Reg_edx);
1440 Str << "\t" 1419 Str << "\t"
1441 << "cdto"; 1420 << "cdto";
1442 break; 1421 break;
1443 } 1422 }
1444 } 1423 }
1445 1424
1446 template <class Machine> 1425 template <class Machine>
1447 void InstX86Cbwdq<Machine>::emitIAS(const Cfg *Func) const { 1426 void InstX86Cbwdq<Machine>::emitIAS(const Cfg *Func) const {
1448 typename InstX86Base<Machine>::Traits::Assembler *Asm = 1427 typename InstX86Base<Machine>::Traits::Assembler *Asm =
1449 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>(); 1428 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>();
1450 assert(this->getSrcSize() == 1); 1429 assert(this->getSrcSize() == 1);
1451 Operand *Src0 = this->getSrc(0); 1430 Operand *Src0 = this->getSrc(0);
1452 assert(llvm::isa<Variable>(Src0)); 1431 assert(llvm::isa<Variable>(Src0));
1453 assert(llvm::cast<Variable>(Src0)->getRegNum() ==
1454 InstX86Base<Machine>::Traits::RegisterSet::Reg_eax);
1455 switch (Src0->getType()) { 1432 switch (Src0->getType()) {
1456 default: 1433 default:
1457 llvm_unreachable("unexpected source type!"); 1434 llvm_unreachable("unexpected source type!");
1458 break; 1435 break;
1459 case IceType_i8: 1436 case IceType_i8:
1437 assert(llvm::cast<Variable>(Src0)->getRegNum() ==
1438 InstX86Base<Machine>::Traits::RegisterSet::Reg_al);
1460 assert(this->getDest()->getRegNum() == 1439 assert(this->getDest()->getRegNum() ==
1461 InstX86Base<Machine>::Traits::RegisterSet::Reg_eax); 1440 InstX86Base<Machine>::Traits::RegisterSet::Reg_ax);
1462 Asm->cbw(); 1441 Asm->cbw();
1463 break; 1442 break;
1464 case IceType_i16: 1443 case IceType_i16:
1444 assert(llvm::cast<Variable>(Src0)->getRegNum() ==
1445 InstX86Base<Machine>::Traits::RegisterSet::Reg_ax);
1465 assert(this->getDest()->getRegNum() == 1446 assert(this->getDest()->getRegNum() ==
1466 InstX86Base<Machine>::Traits::RegisterSet::Reg_edx); 1447 InstX86Base<Machine>::Traits::RegisterSet::Reg_dx);
1467 Asm->cwd(); 1448 Asm->cwd();
1468 break; 1449 break;
1469 case IceType_i32: 1450 case IceType_i32:
1451 assert(llvm::cast<Variable>(Src0)->getRegNum() ==
1452 InstX86Base<Machine>::Traits::RegisterSet::Reg_eax);
1470 assert(this->getDest()->getRegNum() == 1453 assert(this->getDest()->getRegNum() ==
1471 InstX86Base<Machine>::Traits::RegisterSet::Reg_edx); 1454 InstX86Base<Machine>::Traits::RegisterSet::Reg_edx);
1472 Asm->cdq(); 1455 Asm->cdq();
1473 break; 1456 break;
1474 case IceType_i64: 1457 case IceType_i64:
1475 assert(this->getDest()->getRegNum() == 1458 assert(this->getDest()->getRegNum() ==
1476 InstX86Base<Machine>::Traits::RegisterSet::Reg_edx); 1459 InstX86Base<Machine>::Traits::RegisterSet::Reg_edx);
1477 Asm->cqo(); 1460 Asm->cqo();
1478 break; 1461 break;
1479 } 1462 }
(...skipping 42 matching lines...) Expand 10 before | Expand all | Expand 10 after
1522 1505
1523 template <class Machine> 1506 template <class Machine>
1524 void InstX86Shld<Machine>::emit(const Cfg *Func) const { 1507 void InstX86Shld<Machine>::emit(const Cfg *Func) const {
1525 if (!BuildDefs::dump()) 1508 if (!BuildDefs::dump())
1526 return; 1509 return;
1527 Ostream &Str = Func->getContext()->getStrEmit(); 1510 Ostream &Str = Func->getContext()->getStrEmit();
1528 Variable *Dest = this->getDest(); 1511 Variable *Dest = this->getDest();
1529 assert(this->getSrcSize() == 3); 1512 assert(this->getSrcSize() == 3);
1530 assert(Dest == this->getSrc(0)); 1513 assert(Dest == this->getSrc(0));
1531 Str << "\tshld" << this->getWidthString(Dest->getType()) << "\t"; 1514 Str << "\tshld" << this->getWidthString(Dest->getType()) << "\t";
1532 if (const auto ShiftReg = llvm::dyn_cast<Variable>(this->getSrc(2))) { 1515 this->getSrc(2)->emit(Func);
1533 (void)ShiftReg;
1534 assert(ShiftReg->getRegNum() ==
1535 InstX86Base<Machine>::Traits::RegisterSet::Reg_ecx);
1536 Str << "%cl";
1537 } else {
1538 this->getSrc(2)->emit(Func);
1539 }
1540 Str << ", "; 1516 Str << ", ";
1541 this->getSrc(1)->emit(Func); 1517 this->getSrc(1)->emit(Func);
1542 Str << ", "; 1518 Str << ", ";
1543 Dest->emit(Func); 1519 Dest->emit(Func);
1544 } 1520 }
1545 1521
1546 template <class Machine> 1522 template <class Machine>
1547 void InstX86Shld<Machine>::emitIAS(const Cfg *Func) const { 1523 void InstX86Shld<Machine>::emitIAS(const Cfg *Func) const {
1548 assert(this->getSrcSize() == 3); 1524 assert(this->getSrcSize() == 3);
1549 assert(this->getDest() == this->getSrc(0)); 1525 assert(this->getDest() == this->getSrc(0));
(...skipping 19 matching lines...) Expand all
1569 1545
1570 template <class Machine> 1546 template <class Machine>
1571 void InstX86Shrd<Machine>::emit(const Cfg *Func) const { 1547 void InstX86Shrd<Machine>::emit(const Cfg *Func) const {
1572 if (!BuildDefs::dump()) 1548 if (!BuildDefs::dump())
1573 return; 1549 return;
1574 Ostream &Str = Func->getContext()->getStrEmit(); 1550 Ostream &Str = Func->getContext()->getStrEmit();
1575 Variable *Dest = this->getDest(); 1551 Variable *Dest = this->getDest();
1576 assert(this->getSrcSize() == 3); 1552 assert(this->getSrcSize() == 3);
1577 assert(Dest == this->getSrc(0)); 1553 assert(Dest == this->getSrc(0));
1578 Str << "\tshrd" << this->getWidthString(Dest->getType()) << "\t"; 1554 Str << "\tshrd" << this->getWidthString(Dest->getType()) << "\t";
1579 if (const auto ShiftReg = llvm::dyn_cast<Variable>(this->getSrc(2))) { 1555 this->getSrc(2)->emit(Func);
1580 (void)ShiftReg;
1581 assert(ShiftReg->getRegNum() ==
1582 InstX86Base<Machine>::Traits::RegisterSet::Reg_ecx);
1583 Str << "%cl";
1584 } else {
1585 this->getSrc(2)->emit(Func);
1586 }
1587 Str << ", "; 1556 Str << ", ";
1588 this->getSrc(1)->emit(Func); 1557 this->getSrc(1)->emit(Func);
1589 Str << ", "; 1558 Str << ", ";
1590 Dest->emit(Func); 1559 Dest->emit(Func);
1591 } 1560 }
1592 1561
1593 template <class Machine> 1562 template <class Machine>
1594 void InstX86Shrd<Machine>::emitIAS(const Cfg *Func) const { 1563 void InstX86Shrd<Machine>::emitIAS(const Cfg *Func) const {
1595 assert(this->getSrcSize() == 3); 1564 assert(this->getSrcSize() == 3);
1596 assert(this->getDest() == this->getSrc(0)); 1565 assert(this->getDest() == this->getSrc(0));
(...skipping 40 matching lines...) Expand 10 before | Expand all | Expand 10 after
1637 assert(this->getDest()->hasReg()); 1606 assert(this->getDest()->hasReg());
1638 assert(this->getSrcSize() == 2); 1607 assert(this->getSrcSize() == 2);
1639 Operand *Src = this->getSrc(1); 1608 Operand *Src = this->getSrc(1);
1640 Type SrcTy = Src->getType(); 1609 Type SrcTy = Src->getType();
1641 assert(SrcTy == IceType_i16 || SrcTy == IceType_i32 || 1610 assert(SrcTy == IceType_i16 || SrcTy == IceType_i32 ||
1642 (InstX86Base<Machine>::Traits::Is64Bit)); 1611 (InstX86Base<Machine>::Traits::Is64Bit));
1643 typename InstX86Base<Machine>::Traits::Assembler *Asm = 1612 typename InstX86Base<Machine>::Traits::Assembler *Asm =
1644 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>(); 1613 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>();
1645 if (const auto *SrcVar = llvm::dyn_cast<Variable>(Src)) { 1614 if (const auto *SrcVar = llvm::dyn_cast<Variable>(Src)) {
1646 if (SrcVar->hasReg()) { 1615 if (SrcVar->hasReg()) {
1647 Asm->cmov(SrcTy, Condition, 1616 Asm->cmov(
1648 InstX86Base<Machine>::Traits::RegisterSet::getEncodedGPR( 1617 SrcTy, Condition, InstX86Base<Machine>::Traits::getEncodedGPR(
1649 this->getDest()->getRegNum()), 1618 this->getDest()->getRegNum()),
1650 InstX86Base<Machine>::Traits::RegisterSet::getEncodedGPR( 1619 InstX86Base<Machine>::Traits::getEncodedGPR(SrcVar->getRegNum()));
1651 SrcVar->getRegNum()));
1652 } else { 1620 } else {
1653 Asm->cmov( 1621 Asm->cmov(
1654 SrcTy, Condition, 1622 SrcTy, Condition, InstX86Base<Machine>::Traits::getEncodedGPR(
1655 InstX86Base<Machine>::Traits::RegisterSet::getEncodedGPR( 1623 this->getDest()->getRegNum()),
1656 this->getDest()->getRegNum()),
1657 static_cast<typename InstX86Base<Machine>::Traits::TargetLowering *>( 1624 static_cast<typename InstX86Base<Machine>::Traits::TargetLowering *>(
1658 Func->getTarget()) 1625 Func->getTarget())
1659 ->stackVarToAsmOperand(SrcVar)); 1626 ->stackVarToAsmOperand(SrcVar));
1660 } 1627 }
1661 } else if (const auto Mem = llvm::dyn_cast< 1628 } else if (const auto *Mem = llvm::dyn_cast<
1662 typename InstX86Base<Machine>::Traits::X86OperandMem>(Src)) { 1629 typename InstX86Base<Machine>::Traits::X86OperandMem>(Src)) {
1663 assert(Mem->getSegmentRegister() == 1630 assert(Mem->getSegmentRegister() ==
1664 InstX86Base<Machine>::Traits::X86OperandMem::DefaultSegment); 1631 InstX86Base<Machine>::Traits::X86OperandMem::DefaultSegment);
1665 Asm->cmov(SrcTy, Condition, 1632 Asm->cmov(SrcTy, Condition, InstX86Base<Machine>::Traits::getEncodedGPR(
1666 InstX86Base<Machine>::Traits::RegisterSet::getEncodedGPR( 1633 this->getDest()->getRegNum()),
1667 this->getDest()->getRegNum()),
1668 Mem->toAsmAddress(Asm)); 1634 Mem->toAsmAddress(Asm));
1669 } else { 1635 } else {
1670 llvm_unreachable("Unexpected operand type"); 1636 llvm_unreachable("Unexpected operand type");
1671 } 1637 }
1672 } 1638 }
1673 1639
1674 template <class Machine> 1640 template <class Machine>
1675 void InstX86Cmov<Machine>::dump(const Cfg *Func) const { 1641 void InstX86Cmov<Machine>::dump(const Cfg *Func) const {
1676 if (!BuildDefs::dump()) 1642 if (!BuildDefs::dump())
1677 return; 1643 return;
(...skipping 26 matching lines...) Expand all
1704 1670
1705 template <class Machine> 1671 template <class Machine>
1706 void InstX86Cmpps<Machine>::emitIAS(const Cfg *Func) const { 1672 void InstX86Cmpps<Machine>::emitIAS(const Cfg *Func) const {
1707 typename InstX86Base<Machine>::Traits::Assembler *Asm = 1673 typename InstX86Base<Machine>::Traits::Assembler *Asm =
1708 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>(); 1674 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>();
1709 assert(this->getSrcSize() == 2); 1675 assert(this->getSrcSize() == 2);
1710 assert(Condition < InstX86Base<Machine>::Traits::Cond::Cmpps_Invalid); 1676 assert(Condition < InstX86Base<Machine>::Traits::Cond::Cmpps_Invalid);
1711 // Assuming there isn't any load folding for cmpps, and vector constants are 1677 // Assuming there isn't any load folding for cmpps, and vector constants are
1712 // not allowed in PNaCl. 1678 // not allowed in PNaCl.
1713 assert(llvm::isa<Variable>(this->getSrc(1))); 1679 assert(llvm::isa<Variable>(this->getSrc(1)));
1714 const auto SrcVar = llvm::cast<Variable>(this->getSrc(1)); 1680 const auto *SrcVar = llvm::cast<Variable>(this->getSrc(1));
1715 if (SrcVar->hasReg()) { 1681 if (SrcVar->hasReg()) {
1716 Asm->cmpps(InstX86Base<Machine>::Traits::RegisterSet::getEncodedXmm( 1682 Asm->cmpps(InstX86Base<Machine>::Traits::getEncodedXmm(
1717 this->getDest()->getRegNum()), 1683 this->getDest()->getRegNum()),
1718 InstX86Base<Machine>::Traits::RegisterSet::getEncodedXmm( 1684 InstX86Base<Machine>::Traits::getEncodedXmm(SrcVar->getRegNum()),
1719 SrcVar->getRegNum()),
1720 Condition); 1685 Condition);
1721 } else { 1686 } else {
1722 typename InstX86Base<Machine>::Traits::Address SrcStackAddr = 1687 typename InstX86Base<Machine>::Traits::Address SrcStackAddr =
1723 static_cast<typename InstX86Base<Machine>::Traits::TargetLowering *>( 1688 static_cast<typename InstX86Base<Machine>::Traits::TargetLowering *>(
1724 Func->getTarget()) 1689 Func->getTarget())
1725 ->stackVarToAsmOperand(SrcVar); 1690 ->stackVarToAsmOperand(SrcVar);
1726 Asm->cmpps(InstX86Base<Machine>::Traits::RegisterSet::getEncodedXmm( 1691 Asm->cmpps(InstX86Base<Machine>::Traits::getEncodedXmm(
1727 this->getDest()->getRegNum()), 1692 this->getDest()->getRegNum()),
1728 SrcStackAddr, Condition); 1693 SrcStackAddr, Condition);
1729 } 1694 }
1730 } 1695 }
1731 1696
1732 template <class Machine> 1697 template <class Machine>
1733 void InstX86Cmpps<Machine>::dump(const Cfg *Func) const { 1698 void InstX86Cmpps<Machine>::dump(const Cfg *Func) const {
1734 if (!BuildDefs::dump()) 1699 if (!BuildDefs::dump())
1735 return; 1700 return;
1736 Ostream &Str = Func->getContext()->getStrDump(); 1701 Ostream &Str = Func->getContext()->getStrDump();
(...skipping 28 matching lines...) Expand all
1765 typename InstX86Base<Machine>::Traits::Assembler *Asm = 1730 typename InstX86Base<Machine>::Traits::Assembler *Asm =
1766 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>(); 1731 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>();
1767 Type Ty = this->getSrc(0)->getType(); 1732 Type Ty = this->getSrc(0)->getType();
1768 const auto Mem = 1733 const auto Mem =
1769 llvm::cast<typename InstX86Base<Machine>::Traits::X86OperandMem>( 1734 llvm::cast<typename InstX86Base<Machine>::Traits::X86OperandMem>(
1770 this->getSrc(0)); 1735 this->getSrc(0));
1771 assert(Mem->getSegmentRegister() == 1736 assert(Mem->getSegmentRegister() ==
1772 InstX86Base<Machine>::Traits::X86OperandMem::DefaultSegment); 1737 InstX86Base<Machine>::Traits::X86OperandMem::DefaultSegment);
1773 const typename InstX86Base<Machine>::Traits::Address Addr = 1738 const typename InstX86Base<Machine>::Traits::Address Addr =
1774 Mem->toAsmAddress(Asm); 1739 Mem->toAsmAddress(Asm);
1775 const auto VarReg = llvm::cast<Variable>(this->getSrc(2)); 1740 const auto *VarReg = llvm::cast<Variable>(this->getSrc(2));
1776 assert(VarReg->hasReg()); 1741 assert(VarReg->hasReg());
1777 const typename InstX86Base<Machine>::Traits::RegisterSet::GPRRegister Reg = 1742 const typename InstX86Base<Machine>::Traits::RegisterSet::GPRRegister Reg =
1778 InstX86Base<Machine>::Traits::RegisterSet::getEncodedGPR( 1743 InstX86Base<Machine>::Traits::getEncodedGPR(VarReg->getRegNum());
1779 VarReg->getRegNum());
1780 Asm->cmpxchg(Ty, Addr, Reg, this->Locked); 1744 Asm->cmpxchg(Ty, Addr, Reg, this->Locked);
1781 } 1745 }
1782 1746
1783 template <class Machine> 1747 template <class Machine>
1784 void InstX86Cmpxchg<Machine>::dump(const Cfg *Func) const { 1748 void InstX86Cmpxchg<Machine>::dump(const Cfg *Func) const {
1785 if (!BuildDefs::dump()) 1749 if (!BuildDefs::dump())
1786 return; 1750 return;
1787 Ostream &Str = Func->getContext()->getStrDump(); 1751 Ostream &Str = Func->getContext()->getStrDump();
1788 if (this->Locked) { 1752 if (this->Locked) {
1789 Str << "lock "; 1753 Str << "lock ";
(...skipping 80 matching lines...) Expand 10 before | Expand all | Expand 10 after
1870 static const typename InstX86Base<Machine>::Traits::Assembler:: 1834 static const typename InstX86Base<Machine>::Traits::Assembler::
1871 template CastEmitterRegOp< 1835 template CastEmitterRegOp<
1872 typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister, 1836 typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister,
1873 typename InstX86Base<Machine>::Traits::RegisterSet::GPRRegister> 1837 typename InstX86Base<Machine>::Traits::RegisterSet::GPRRegister>
1874 Emitter = {&InstX86Base<Machine>::Traits::Assembler::cvtsi2ss, 1838 Emitter = {&InstX86Base<Machine>::Traits::Assembler::cvtsi2ss,
1875 &InstX86Base<Machine>::Traits::Assembler::cvtsi2ss}; 1839 &InstX86Base<Machine>::Traits::Assembler::cvtsi2ss};
1876 emitIASCastRegOp< 1840 emitIASCastRegOp<
1877 Machine, 1841 Machine,
1878 typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister, 1842 typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister,
1879 typename InstX86Base<Machine>::Traits::RegisterSet::GPRRegister, 1843 typename InstX86Base<Machine>::Traits::RegisterSet::GPRRegister,
1880 InstX86Base<Machine>::Traits::RegisterSet::getEncodedXmm, 1844 InstX86Base<Machine>::Traits::getEncodedXmm,
1881 InstX86Base<Machine>::Traits::RegisterSet::getEncodedGPR>( 1845 InstX86Base<Machine>::Traits::getEncodedGPR>(Func, DestTy, Dest, SrcTy,
1882 Func, DestTy, Dest, SrcTy, Src, Emitter); 1846 Src, Emitter);
1883 return; 1847 return;
1884 } 1848 }
1885 case Tss2si: { 1849 case Tss2si: {
1886 assert(isScalarFloatingType(SrcTy)); 1850 assert(isScalarFloatingType(SrcTy));
1887 assert(isScalarIntegerType(DestTy)); 1851 assert(isScalarIntegerType(DestTy));
1888 if (!InstX86Base<Machine>::Traits::Is64Bit) { 1852 if (!InstX86Base<Machine>::Traits::Is64Bit) {
1889 assert(typeWidthInBytes(DestTy) <= 4); 1853 assert(typeWidthInBytes(DestTy) <= 4);
1890 } else { 1854 } else {
1891 assert(DestTy == IceType_i32 || DestTy == IceType_i64); 1855 assert(DestTy == IceType_i32 || DestTy == IceType_i64);
1892 } 1856 }
1893 static const typename InstX86Base<Machine>::Traits::Assembler:: 1857 static const typename InstX86Base<Machine>::Traits::Assembler::
1894 template CastEmitterRegOp< 1858 template CastEmitterRegOp<
1895 typename InstX86Base<Machine>::Traits::RegisterSet::GPRRegister, 1859 typename InstX86Base<Machine>::Traits::RegisterSet::GPRRegister,
1896 typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister> 1860 typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister>
1897 Emitter = {&InstX86Base<Machine>::Traits::Assembler::cvttss2si, 1861 Emitter = {&InstX86Base<Machine>::Traits::Assembler::cvttss2si,
1898 &InstX86Base<Machine>::Traits::Assembler::cvttss2si}; 1862 &InstX86Base<Machine>::Traits::Assembler::cvttss2si};
1899 emitIASCastRegOp< 1863 emitIASCastRegOp<
1900 Machine, 1864 Machine,
1901 typename InstX86Base<Machine>::Traits::RegisterSet::GPRRegister, 1865 typename InstX86Base<Machine>::Traits::RegisterSet::GPRRegister,
1902 typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister, 1866 typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister,
1903 InstX86Base<Machine>::Traits::RegisterSet::getEncodedGPR, 1867 InstX86Base<Machine>::Traits::getEncodedGPR,
1904 InstX86Base<Machine>::Traits::RegisterSet::getEncodedXmm>( 1868 InstX86Base<Machine>::Traits::getEncodedXmm>(Func, DestTy, Dest, SrcTy,
1905 Func, DestTy, Dest, SrcTy, Src, Emitter); 1869 Src, Emitter);
1906 return; 1870 return;
1907 } 1871 }
1908 case Float2float: { 1872 case Float2float: {
1909 assert(isScalarFloatingType(SrcTy)); 1873 assert(isScalarFloatingType(SrcTy));
1910 assert(isScalarFloatingType(DestTy)); 1874 assert(isScalarFloatingType(DestTy));
1911 assert(DestTy != SrcTy); 1875 assert(DestTy != SrcTy);
1912 static const typename InstX86Base< 1876 static const typename InstX86Base<
1913 Machine>::Traits::Assembler::XmmEmitterRegOp Emitter = { 1877 Machine>::Traits::Assembler::XmmEmitterRegOp Emitter = {
1914 &InstX86Base<Machine>::Traits::Assembler::cvtfloat2float, 1878 &InstX86Base<Machine>::Traits::Assembler::cvtfloat2float,
1915 &InstX86Base<Machine>::Traits::Assembler::cvtfloat2float}; 1879 &InstX86Base<Machine>::Traits::Assembler::cvtfloat2float};
(...skipping 59 matching lines...) Expand 10 before | Expand all | Expand 10 after
1975 const Operand *Src1 = this->getSrc(1); 1939 const Operand *Src1 = this->getSrc(1);
1976 Type Ty = Src0->getType(); 1940 Type Ty = Src0->getType();
1977 static const typename InstX86Base<Machine>::Traits::Assembler::GPREmitterRegOp 1941 static const typename InstX86Base<Machine>::Traits::Assembler::GPREmitterRegOp
1978 RegEmitter = {&InstX86Base<Machine>::Traits::Assembler::cmp, 1942 RegEmitter = {&InstX86Base<Machine>::Traits::Assembler::cmp,
1979 &InstX86Base<Machine>::Traits::Assembler::cmp, 1943 &InstX86Base<Machine>::Traits::Assembler::cmp,
1980 &InstX86Base<Machine>::Traits::Assembler::cmp}; 1944 &InstX86Base<Machine>::Traits::Assembler::cmp};
1981 static const typename InstX86Base< 1945 static const typename InstX86Base<
1982 Machine>::Traits::Assembler::GPREmitterAddrOp AddrEmitter = { 1946 Machine>::Traits::Assembler::GPREmitterAddrOp AddrEmitter = {
1983 &InstX86Base<Machine>::Traits::Assembler::cmp, 1947 &InstX86Base<Machine>::Traits::Assembler::cmp,
1984 &InstX86Base<Machine>::Traits::Assembler::cmp}; 1948 &InstX86Base<Machine>::Traits::Assembler::cmp};
1985 if (const auto SrcVar0 = llvm::dyn_cast<Variable>(Src0)) { 1949 if (const auto *SrcVar0 = llvm::dyn_cast<Variable>(Src0)) {
1986 if (SrcVar0->hasReg()) { 1950 if (SrcVar0->hasReg()) {
1987 emitIASRegOpTyGPR<Machine>(Func, Ty, SrcVar0, Src1, RegEmitter); 1951 emitIASRegOpTyGPR<Machine>(Func, Ty, SrcVar0, Src1, RegEmitter);
1988 return; 1952 return;
1989 } 1953 }
1990 } 1954 }
1991 emitIASAsAddrOpTyGPR<Machine>(Func, Ty, Src0, Src1, AddrEmitter); 1955 emitIASAsAddrOpTyGPR<Machine>(Func, Ty, Src0, Src1, AddrEmitter);
1992 } 1956 }
1993 1957
1994 template <class Machine> 1958 template <class Machine>
1995 void InstX86Icmp<Machine>::dump(const Cfg *Func) const { 1959 void InstX86Icmp<Machine>::dump(const Cfg *Func) const {
(...skipping 18 matching lines...) Expand all
2014 Str << ", "; 1978 Str << ", ";
2015 this->getSrc(0)->emit(Func); 1979 this->getSrc(0)->emit(Func);
2016 } 1980 }
2017 1981
2018 template <class Machine> 1982 template <class Machine>
2019 void InstX86Ucomiss<Machine>::emitIAS(const Cfg *Func) const { 1983 void InstX86Ucomiss<Machine>::emitIAS(const Cfg *Func) const {
2020 assert(this->getSrcSize() == 2); 1984 assert(this->getSrcSize() == 2);
2021 // Currently src0 is always a variable by convention, to avoid having two 1985 // Currently src0 is always a variable by convention, to avoid having two
2022 // memory operands. 1986 // memory operands.
2023 assert(llvm::isa<Variable>(this->getSrc(0))); 1987 assert(llvm::isa<Variable>(this->getSrc(0)));
2024 const auto Src0Var = llvm::cast<Variable>(this->getSrc(0)); 1988 const auto *Src0Var = llvm::cast<Variable>(this->getSrc(0));
2025 Type Ty = Src0Var->getType(); 1989 Type Ty = Src0Var->getType();
2026 static const typename InstX86Base<Machine>::Traits::Assembler::XmmEmitterRegOp 1990 static const typename InstX86Base<Machine>::Traits::Assembler::XmmEmitterRegOp
2027 Emitter = {&InstX86Base<Machine>::Traits::Assembler::ucomiss, 1991 Emitter = {&InstX86Base<Machine>::Traits::Assembler::ucomiss,
2028 &InstX86Base<Machine>::Traits::Assembler::ucomiss}; 1992 &InstX86Base<Machine>::Traits::Assembler::ucomiss};
2029 emitIASRegOpTyXMM<Machine>(Func, Ty, Src0Var, this->getSrc(1), Emitter); 1993 emitIASRegOpTyXMM<Machine>(Func, Ty, Src0Var, this->getSrc(1), Emitter);
2030 } 1994 }
2031 1995
2032 template <class Machine> 1996 template <class Machine>
2033 void InstX86Ucomiss<Machine>::dump(const Cfg *Func) const { 1997 void InstX86Ucomiss<Machine>::dump(const Cfg *Func) const {
2034 if (!BuildDefs::dump()) 1998 if (!BuildDefs::dump())
(...skipping 44 matching lines...) Expand 10 before | Expand all | Expand 10 after
2079 const Operand *Src1 = this->getSrc(1); 2043 const Operand *Src1 = this->getSrc(1);
2080 Type Ty = Src0->getType(); 2044 Type Ty = Src0->getType();
2081 // The Reg/Addr form of test is not encodeable. 2045 // The Reg/Addr form of test is not encodeable.
2082 static const typename InstX86Base<Machine>::Traits::Assembler::GPREmitterRegOp 2046 static const typename InstX86Base<Machine>::Traits::Assembler::GPREmitterRegOp
2083 RegEmitter = {&InstX86Base<Machine>::Traits::Assembler::test, nullptr, 2047 RegEmitter = {&InstX86Base<Machine>::Traits::Assembler::test, nullptr,
2084 &InstX86Base<Machine>::Traits::Assembler::test}; 2048 &InstX86Base<Machine>::Traits::Assembler::test};
2085 static const typename InstX86Base< 2049 static const typename InstX86Base<
2086 Machine>::Traits::Assembler::GPREmitterAddrOp AddrEmitter = { 2050 Machine>::Traits::Assembler::GPREmitterAddrOp AddrEmitter = {
2087 &InstX86Base<Machine>::Traits::Assembler::test, 2051 &InstX86Base<Machine>::Traits::Assembler::test,
2088 &InstX86Base<Machine>::Traits::Assembler::test}; 2052 &InstX86Base<Machine>::Traits::Assembler::test};
2089 if (const auto SrcVar0 = llvm::dyn_cast<Variable>(Src0)) { 2053 if (const auto *SrcVar0 = llvm::dyn_cast<Variable>(Src0)) {
2090 if (SrcVar0->hasReg()) { 2054 if (SrcVar0->hasReg()) {
2091 emitIASRegOpTyGPR<Machine>(Func, Ty, SrcVar0, Src1, RegEmitter); 2055 emitIASRegOpTyGPR<Machine>(Func, Ty, SrcVar0, Src1, RegEmitter);
2092 return; 2056 return;
2093 } 2057 }
2094 } 2058 }
2095 emitIASAsAddrOpTyGPR<Machine>(Func, Ty, Src0, Src1, AddrEmitter); 2059 emitIASAsAddrOpTyGPR<Machine>(Func, Ty, Src0, Src1, AddrEmitter);
2096 } 2060 }
2097 2061
2098 template <class Machine> 2062 template <class Machine>
2099 void InstX86Test<Machine>::dump(const Cfg *Func) const { 2063 void InstX86Test<Machine>::dump(const Cfg *Func) const {
(...skipping 43 matching lines...) Expand 10 before | Expand all | Expand 10 after
2143 } 2107 }
2144 2108
2145 template <class Machine> 2109 template <class Machine>
2146 void InstX86Store<Machine>::emitIAS(const Cfg *Func) const { 2110 void InstX86Store<Machine>::emitIAS(const Cfg *Func) const {
2147 assert(this->getSrcSize() == 2); 2111 assert(this->getSrcSize() == 2);
2148 const Operand *Dest = this->getSrc(1); 2112 const Operand *Dest = this->getSrc(1);
2149 const Operand *Src = this->getSrc(0); 2113 const Operand *Src = this->getSrc(0);
2150 Type DestTy = Dest->getType(); 2114 Type DestTy = Dest->getType();
2151 if (isScalarFloatingType(DestTy)) { 2115 if (isScalarFloatingType(DestTy)) {
2152 // Src must be a register, since Dest is a Mem operand of some kind. 2116 // Src must be a register, since Dest is a Mem operand of some kind.
2153 const auto SrcVar = llvm::cast<Variable>(Src); 2117 const auto *SrcVar = llvm::cast<Variable>(Src);
2154 assert(SrcVar->hasReg()); 2118 assert(SrcVar->hasReg());
2155 typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister SrcReg = 2119 typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister SrcReg =
2156 InstX86Base<Machine>::Traits::RegisterSet::getEncodedXmm( 2120 InstX86Base<Machine>::Traits::getEncodedXmm(SrcVar->getRegNum());
2157 SrcVar->getRegNum());
2158 typename InstX86Base<Machine>::Traits::Assembler *Asm = 2121 typename InstX86Base<Machine>::Traits::Assembler *Asm =
2159 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>(); 2122 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>();
2160 if (const auto DestVar = llvm::dyn_cast<Variable>(Dest)) { 2123 if (const auto *DestVar = llvm::dyn_cast<Variable>(Dest)) {
2161 assert(!DestVar->hasReg()); 2124 assert(!DestVar->hasReg());
2162 typename InstX86Base<Machine>::Traits::Address StackAddr( 2125 typename InstX86Base<Machine>::Traits::Address StackAddr(
2163 static_cast<typename InstX86Base<Machine>::Traits::TargetLowering *>( 2126 static_cast<typename InstX86Base<Machine>::Traits::TargetLowering *>(
2164 Func->getTarget()) 2127 Func->getTarget())
2165 ->stackVarToAsmOperand(DestVar)); 2128 ->stackVarToAsmOperand(DestVar));
2166 Asm->movss(DestTy, StackAddr, SrcReg); 2129 Asm->movss(DestTy, StackAddr, SrcReg);
2167 } else { 2130 } else {
2168 const auto DestMem = 2131 const auto DestMem =
2169 llvm::cast<typename InstX86Base<Machine>::Traits::X86OperandMem>( 2132 llvm::cast<typename InstX86Base<Machine>::Traits::X86OperandMem>(
2170 Dest); 2133 Dest);
(...skipping 34 matching lines...) Expand 10 before | Expand all | Expand 10 after
2205 this->getSrc(0)->emit(Func); 2168 this->getSrc(0)->emit(Func);
2206 Str << ", "; 2169 Str << ", ";
2207 this->getSrc(1)->emit(Func); 2170 this->getSrc(1)->emit(Func);
2208 } 2171 }
2209 2172
2210 template <class Machine> 2173 template <class Machine>
2211 void InstX86StoreP<Machine>::emitIAS(const Cfg *Func) const { 2174 void InstX86StoreP<Machine>::emitIAS(const Cfg *Func) const {
2212 typename InstX86Base<Machine>::Traits::Assembler *Asm = 2175 typename InstX86Base<Machine>::Traits::Assembler *Asm =
2213 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>(); 2176 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>();
2214 assert(this->getSrcSize() == 2); 2177 assert(this->getSrcSize() == 2);
2215 const auto SrcVar = llvm::cast<Variable>(this->getSrc(0)); 2178 const auto *SrcVar = llvm::cast<Variable>(this->getSrc(0));
2216 const auto DestMem = 2179 const auto DestMem =
2217 llvm::cast<typename InstX86Base<Machine>::Traits::X86OperandMem>( 2180 llvm::cast<typename InstX86Base<Machine>::Traits::X86OperandMem>(
2218 this->getSrc(1)); 2181 this->getSrc(1));
2219 assert(DestMem->getSegmentRegister() == 2182 assert(DestMem->getSegmentRegister() ==
2220 InstX86Base<Machine>::Traits::X86OperandMem::DefaultSegment); 2183 InstX86Base<Machine>::Traits::X86OperandMem::DefaultSegment);
2221 assert(SrcVar->hasReg()); 2184 assert(SrcVar->hasReg());
2222 Asm->movups(DestMem->toAsmAddress(Asm), 2185 Asm->movups(DestMem->toAsmAddress(Asm),
2223 InstX86Base<Machine>::Traits::RegisterSet::getEncodedXmm( 2186 InstX86Base<Machine>::Traits::getEncodedXmm(SrcVar->getRegNum()));
2224 SrcVar->getRegNum()));
2225 } 2187 }
2226 2188
2227 template <class Machine> 2189 template <class Machine>
2228 void InstX86StoreP<Machine>::dump(const Cfg *Func) const { 2190 void InstX86StoreP<Machine>::dump(const Cfg *Func) const {
2229 if (!BuildDefs::dump()) 2191 if (!BuildDefs::dump())
2230 return; 2192 return;
2231 Ostream &Str = Func->getContext()->getStrDump(); 2193 Ostream &Str = Func->getContext()->getStrDump();
2232 Str << "storep." << this->getSrc(0)->getType() << " "; 2194 Str << "storep." << this->getSrc(0)->getType() << " ";
2233 this->getSrc(1)->dump(Func); 2195 this->getSrc(1)->dump(Func);
2234 Str << ", "; 2196 Str << ", ";
(...skipping 13 matching lines...) Expand all
2248 this->getSrc(0)->emit(Func); 2210 this->getSrc(0)->emit(Func);
2249 Str << ", "; 2211 Str << ", ";
2250 this->getSrc(1)->emit(Func); 2212 this->getSrc(1)->emit(Func);
2251 } 2213 }
2252 2214
2253 template <class Machine> 2215 template <class Machine>
2254 void InstX86StoreQ<Machine>::emitIAS(const Cfg *Func) const { 2216 void InstX86StoreQ<Machine>::emitIAS(const Cfg *Func) const {
2255 typename InstX86Base<Machine>::Traits::Assembler *Asm = 2217 typename InstX86Base<Machine>::Traits::Assembler *Asm =
2256 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>(); 2218 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>();
2257 assert(this->getSrcSize() == 2); 2219 assert(this->getSrcSize() == 2);
2258 const auto SrcVar = llvm::cast<Variable>(this->getSrc(0)); 2220 const auto *SrcVar = llvm::cast<Variable>(this->getSrc(0));
2259 const auto DestMem = 2221 const auto DestMem =
2260 llvm::cast<typename InstX86Base<Machine>::Traits::X86OperandMem>( 2222 llvm::cast<typename InstX86Base<Machine>::Traits::X86OperandMem>(
2261 this->getSrc(1)); 2223 this->getSrc(1));
2262 assert(DestMem->getSegmentRegister() == 2224 assert(DestMem->getSegmentRegister() ==
2263 InstX86Base<Machine>::Traits::X86OperandMem::DefaultSegment); 2225 InstX86Base<Machine>::Traits::X86OperandMem::DefaultSegment);
2264 assert(SrcVar->hasReg()); 2226 assert(SrcVar->hasReg());
2265 Asm->movq(DestMem->toAsmAddress(Asm), 2227 Asm->movq(DestMem->toAsmAddress(Asm),
2266 InstX86Base<Machine>::Traits::RegisterSet::getEncodedXmm( 2228 InstX86Base<Machine>::Traits::getEncodedXmm(SrcVar->getRegNum()));
2267 SrcVar->getRegNum()));
2268 } 2229 }
2269 2230
2270 template <class Machine> 2231 template <class Machine>
2271 void InstX86StoreQ<Machine>::dump(const Cfg *Func) const { 2232 void InstX86StoreQ<Machine>::dump(const Cfg *Func) const {
2272 if (!BuildDefs::dump()) 2233 if (!BuildDefs::dump())
2273 return; 2234 return;
2274 Ostream &Str = Func->getContext()->getStrDump(); 2235 Ostream &Str = Func->getContext()->getStrDump();
2275 Str << "storeq." << this->getSrc(0)->getType() << " "; 2236 Str << "storeq." << this->getSrc(0)->getType() << " ";
2276 this->getSrc(1)->dump(Func); 2237 this->getSrc(1)->dump(Func);
2277 Str << ", "; 2238 Str << ", ";
2278 this->getSrc(0)->dump(Func); 2239 this->getSrc(0)->dump(Func);
2279 } 2240 }
2280 2241
2281 template <class Machine> void InstX86Lea<Machine>::emit(const Cfg *Func) const { 2242 template <class Machine> void InstX86Lea<Machine>::emit(const Cfg *Func) const {
2282 if (!BuildDefs::dump()) 2243 if (!BuildDefs::dump())
2283 return; 2244 return;
2284 Ostream &Str = Func->getContext()->getStrEmit(); 2245 Ostream &Str = Func->getContext()->getStrEmit();
2285 assert(this->getSrcSize() == 1); 2246 assert(this->getSrcSize() == 1);
2286 assert(this->getDest()->hasReg()); 2247 assert(this->getDest()->hasReg());
2287 Str << "\tleal\t"; 2248 Str << "\tleal\t";
2288 Operand *Src0 = this->getSrc(0); 2249 Operand *Src0 = this->getSrc(0);
2289 if (const auto Src0Var = llvm::dyn_cast<Variable>(Src0)) { 2250 if (const auto *Src0Var = llvm::dyn_cast<Variable>(Src0)) {
2290 Type Ty = Src0Var->getType(); 2251 Type Ty = Src0Var->getType();
2291 // lea on x86-32 doesn't accept mem128 operands, so cast VSrc0 to an 2252 // lea on x86-32 doesn't accept mem128 operands, so cast VSrc0 to an
2292 // acceptable type. 2253 // acceptable type.
2293 Src0Var->asType(isVectorType(Ty) ? IceType_i32 : Ty)->emit(Func); 2254 Src0Var->asType(isVectorType(Ty) ? IceType_i32 : Ty, Variable::NoRegister)
2255 ->emit(Func);
2294 } else { 2256 } else {
2295 Src0->emit(Func); 2257 Src0->emit(Func);
2296 } 2258 }
2297 Str << ", "; 2259 Str << ", ";
2298 this->getDest()->emit(Func); 2260 this->getDest()->emit(Func);
2299 } 2261 }
2300 2262
2301 inline bool isIntegerConstant(const Operand *Op) { 2263 inline bool isIntegerConstant(const Operand *Op) {
2302 return llvm::isa<ConstantInteger32>(Op) || llvm::isa<ConstantInteger64>(Op); 2264 return llvm::isa<ConstantInteger32>(Op) || llvm::isa<ConstantInteger64>(Op);
2303 } 2265 }
(...skipping 23 matching lines...) Expand all
2327 // src. This works even for stack-allocated dest variables because 2289 // src. This works even for stack-allocated dest variables because
2328 // typeWidthOnStack() pads to a 4-byte boundary even if only a lower portion 2290 // typeWidthOnStack() pads to a 4-byte boundary even if only a lower portion
2329 // is used. 2291 // is used.
2330 // TODO: This assert disallows usages such as copying a floating 2292 // TODO: This assert disallows usages such as copying a floating
2331 // point value between a vector and a scalar (which movss is used for). Clean 2293 // point value between a vector and a scalar (which movss is used for). Clean
2332 // this up. 2294 // this up.
2333 assert(Func->getTarget()->typeWidthInBytesOnStack(DestTy) == 2295 assert(Func->getTarget()->typeWidthInBytesOnStack(DestTy) ==
2334 Func->getTarget()->typeWidthInBytesOnStack(SrcTy)); 2296 Func->getTarget()->typeWidthInBytesOnStack(SrcTy));
2335 Src->emit(Func); 2297 Src->emit(Func);
2336 Str << ", "; 2298 Str << ", ";
2337 this->getDest()->asType(SrcTy)->emit(Func); 2299 int32_t NewRegNum = Variable::NoRegister;
2300 if (this->getDest()->hasReg())
2301 NewRegNum = InstX86Base<Machine>::Traits::getGprForType(
2302 SrcTy, this->getDest()->getRegNum());
2303 const Variable *NewDest = SrcTy == DestTy
2304 ? this->getDest()
2305 : this->getDest()->asType(SrcTy, NewRegNum);
2306 NewDest->emit(Func);
2338 } 2307 }
2339 2308
2340 template <class Machine> 2309 template <class Machine>
2341 void InstX86Mov<Machine>::emitIAS(const Cfg *Func) const { 2310 void InstX86Mov<Machine>::emitIAS(const Cfg *Func) const {
2342 assert(this->getSrcSize() == 1); 2311 assert(this->getSrcSize() == 1);
2343 const Variable *Dest = this->getDest(); 2312 const Variable *Dest = this->getDest();
2344 const Operand *Src = this->getSrc(0); 2313 const Operand *Src = this->getSrc(0);
2345 Type DestTy = Dest->getType(); 2314 Type DestTy = Dest->getType();
2346 Type SrcTy = Src->getType(); 2315 Type SrcTy = Src->getType();
2347 // Mov can be used for GPRs or XMM registers. Also, the type does not 2316 // Mov can be used for GPRs or XMM registers. Also, the type does not
(...skipping 36 matching lines...) Expand 10 before | Expand all | Expand 10 after
2384 // when both Src and Dest are integer types. 2353 // when both Src and Dest are integer types.
2385 if (InstX86Base<Machine>::Traits::Is64Bit && DestTy == IceType_i64 && 2354 if (InstX86Base<Machine>::Traits::Is64Bit && DestTy == IceType_i64 &&
2386 isIntegerConstant(Src)) { 2355 isIntegerConstant(Src)) {
2387 uint64_t Value = -1; 2356 uint64_t Value = -1;
2388 if (const auto *C64 = llvm::dyn_cast<ConstantInteger64>(Src)) { 2357 if (const auto *C64 = llvm::dyn_cast<ConstantInteger64>(Src)) {
2389 Value = C64->getValue(); 2358 Value = C64->getValue();
2390 } else { 2359 } else {
2391 Value = llvm::cast<ConstantInteger32>(Src)->getValue(); 2360 Value = llvm::cast<ConstantInteger32>(Src)->getValue();
2392 } 2361 }
2393 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>() 2362 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>()
2394 ->movabs(InstX86Base<Machine>::Traits::RegisterSet::getEncodedGPR( 2363 ->movabs(
2395 Dest->getRegNum()), 2364 InstX86Base<Machine>::Traits::getEncodedGPR(Dest->getRegNum()),
2396 Value); 2365 Value);
2397 return; 2366 return;
2398 } 2367 }
2399 if (isScalarIntegerType(SrcTy)) { 2368 if (isScalarIntegerType(SrcTy)) {
2400 DestTy = SrcTy; 2369 DestTy = SrcTy;
2401 } 2370 }
2402 emitIASRegOpTyGPR<Machine>(Func, DestTy, Dest, Src, GPRRegEmitter); 2371 emitIASRegOpTyGPR<Machine>(Func, DestTy, Dest, Src, GPRRegEmitter);
2403 return; 2372 return;
2404 } 2373 }
2405 } else { 2374 } else {
2406 // Dest must be Stack and Src *could* be a register. Use Src's type to 2375 // Dest must be Stack and Src *could* be a register. Use Src's type to
2407 // decide on the emitters. 2376 // decide on the emitters.
2408 typename InstX86Base<Machine>::Traits::Address StackAddr( 2377 typename InstX86Base<Machine>::Traits::Address StackAddr(
2409 static_cast<typename InstX86Base<Machine>::Traits::TargetLowering *>( 2378 static_cast<typename InstX86Base<Machine>::Traits::TargetLowering *>(
2410 Func->getTarget()) 2379 Func->getTarget())
2411 ->stackVarToAsmOperand(Dest)); 2380 ->stackVarToAsmOperand(Dest));
2412 if (isScalarFloatingType(SrcTy)) { 2381 if (isScalarFloatingType(SrcTy)) {
2413 // Src must be a register. 2382 // Src must be a register.
2414 const auto SrcVar = llvm::cast<Variable>(Src); 2383 const auto *SrcVar = llvm::cast<Variable>(Src);
2415 assert(SrcVar->hasReg()); 2384 assert(SrcVar->hasReg());
2416 typename InstX86Base<Machine>::Traits::Assembler *Asm = 2385 typename InstX86Base<Machine>::Traits::Assembler *Asm =
2417 Func->getAssembler< 2386 Func->getAssembler<
2418 typename InstX86Base<Machine>::Traits::Assembler>(); 2387 typename InstX86Base<Machine>::Traits::Assembler>();
2419 Asm->movss(SrcTy, StackAddr, 2388 Asm->movss(SrcTy, StackAddr, InstX86Base<Machine>::Traits::getEncodedXmm(
2420 InstX86Base<Machine>::Traits::RegisterSet::getEncodedXmm( 2389 SrcVar->getRegNum()));
2421 SrcVar->getRegNum()));
2422 return; 2390 return;
2423 } else { 2391 } else {
2424 // Src can be a register or immediate. 2392 // Src can be a register or immediate.
2425 assert(isScalarIntegerType(SrcTy)); 2393 assert(isScalarIntegerType(SrcTy));
2426 emitIASAddrOpTyGPR<Machine>(Func, SrcTy, StackAddr, Src, GPRAddrEmitter); 2394 emitIASAddrOpTyGPR<Machine>(Func, SrcTy, StackAddr, Src, GPRAddrEmitter);
2427 return; 2395 return;
2428 } 2396 }
2429 return; 2397 return;
2430 } 2398 }
2431 } 2399 }
2432 2400
2433 template <class Machine> 2401 template <class Machine>
2434 void InstX86Movd<Machine>::emitIAS(const Cfg *Func) const { 2402 void InstX86Movd<Machine>::emitIAS(const Cfg *Func) const {
2435 typename InstX86Base<Machine>::Traits::Assembler *Asm = 2403 typename InstX86Base<Machine>::Traits::Assembler *Asm =
2436 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>(); 2404 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>();
2437 assert(this->getSrcSize() == 1); 2405 assert(this->getSrcSize() == 1);
2438 const Variable *Dest = this->getDest(); 2406 const Variable *Dest = this->getDest();
2439 const auto SrcVar = llvm::cast<Variable>(this->getSrc(0)); 2407 const auto *SrcVar = llvm::cast<Variable>(this->getSrc(0));
2440 // For insert/extract element (one of Src/Dest is an Xmm vector and the other 2408 // For insert/extract element (one of Src/Dest is an Xmm vector and the other
2441 // is an int type). 2409 // is an int type).
2442 if (SrcVar->getType() == IceType_i32 || 2410 if (SrcVar->getType() == IceType_i32 ||
2443 (InstX86Base<Machine>::Traits::Is64Bit && 2411 (InstX86Base<Machine>::Traits::Is64Bit &&
2444 SrcVar->getType() == IceType_i64)) { 2412 SrcVar->getType() == IceType_i64)) {
2445 assert(isVectorType(Dest->getType()) || 2413 assert(isVectorType(Dest->getType()) ||
2446 (isScalarFloatingType(Dest->getType()) && 2414 (isScalarFloatingType(Dest->getType()) &&
2447 typeWidthInBytes(SrcVar->getType()) == 2415 typeWidthInBytes(SrcVar->getType()) ==
2448 typeWidthInBytes(Dest->getType()))); 2416 typeWidthInBytes(Dest->getType())));
2449 assert(Dest->hasReg()); 2417 assert(Dest->hasReg());
2450 typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister DestReg = 2418 typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister DestReg =
2451 InstX86Base<Machine>::Traits::RegisterSet::getEncodedXmm( 2419 InstX86Base<Machine>::Traits::getEncodedXmm(Dest->getRegNum());
2452 Dest->getRegNum());
2453 if (SrcVar->hasReg()) { 2420 if (SrcVar->hasReg()) {
2454 Asm->movd(SrcVar->getType(), DestReg, 2421 Asm->movd(
2455 InstX86Base<Machine>::Traits::RegisterSet::getEncodedGPR( 2422 SrcVar->getType(), DestReg,
2456 SrcVar->getRegNum())); 2423 InstX86Base<Machine>::Traits::getEncodedGPR(SrcVar->getRegNum()));
2457 } else { 2424 } else {
2458 typename InstX86Base<Machine>::Traits::Address StackAddr( 2425 typename InstX86Base<Machine>::Traits::Address StackAddr(
2459 static_cast<typename InstX86Base<Machine>::Traits::TargetLowering *>( 2426 static_cast<typename InstX86Base<Machine>::Traits::TargetLowering *>(
2460 Func->getTarget()) 2427 Func->getTarget())
2461 ->stackVarToAsmOperand(SrcVar)); 2428 ->stackVarToAsmOperand(SrcVar));
2462 Asm->movd(SrcVar->getType(), DestReg, StackAddr); 2429 Asm->movd(SrcVar->getType(), DestReg, StackAddr);
2463 } 2430 }
2464 } else { 2431 } else {
2465 assert(isVectorType(SrcVar->getType()) || 2432 assert(isVectorType(SrcVar->getType()) ||
2466 (isScalarFloatingType(SrcVar->getType()) && 2433 (isScalarFloatingType(SrcVar->getType()) &&
2467 typeWidthInBytes(SrcVar->getType()) == 2434 typeWidthInBytes(SrcVar->getType()) ==
2468 typeWidthInBytes(Dest->getType()))); 2435 typeWidthInBytes(Dest->getType())));
2469 assert(SrcVar->hasReg()); 2436 assert(SrcVar->hasReg());
2470 assert(Dest->getType() == IceType_i32 || 2437 assert(Dest->getType() == IceType_i32 ||
2471 (InstX86Base<Machine>::Traits::Is64Bit && 2438 (InstX86Base<Machine>::Traits::Is64Bit &&
2472 Dest->getType() == IceType_i64)); 2439 Dest->getType() == IceType_i64));
2473 typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister SrcReg = 2440 typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister SrcReg =
2474 InstX86Base<Machine>::Traits::RegisterSet::getEncodedXmm( 2441 InstX86Base<Machine>::Traits::getEncodedXmm(SrcVar->getRegNum());
2475 SrcVar->getRegNum());
2476 if (Dest->hasReg()) { 2442 if (Dest->hasReg()) {
2477 Asm->movd(Dest->getType(), 2443 Asm->movd(Dest->getType(),
2478 InstX86Base<Machine>::Traits::RegisterSet::getEncodedGPR( 2444 InstX86Base<Machine>::Traits::getEncodedGPR(Dest->getRegNum()),
2479 Dest->getRegNum()),
2480 SrcReg); 2445 SrcReg);
2481 } else { 2446 } else {
2482 typename InstX86Base<Machine>::Traits::Address StackAddr( 2447 typename InstX86Base<Machine>::Traits::Address StackAddr(
2483 static_cast<typename InstX86Base<Machine>::Traits::TargetLowering *>( 2448 static_cast<typename InstX86Base<Machine>::Traits::TargetLowering *>(
2484 Func->getTarget()) 2449 Func->getTarget())
2485 ->stackVarToAsmOperand(Dest)); 2450 ->stackVarToAsmOperand(Dest));
2486 Asm->movd(Dest->getType(), StackAddr, SrcReg); 2451 Asm->movd(Dest->getType(), StackAddr, SrcReg);
2487 } 2452 }
2488 } 2453 }
2489 } 2454 }
(...skipping 56 matching lines...) Expand 10 before | Expand all | Expand 10 after
2546 emitIASMovlikeXMM<Machine>(Func, Dest, Src, Emitter); 2511 emitIASMovlikeXMM<Machine>(Func, Dest, Src, Emitter);
2547 } 2512 }
2548 2513
2549 template <class Machine> 2514 template <class Machine>
2550 void InstX86MovssRegs<Machine>::emitIAS(const Cfg *Func) const { 2515 void InstX86MovssRegs<Machine>::emitIAS(const Cfg *Func) const {
2551 // This is Binop variant is only intended to be used for reg-reg moves where 2516 // This is Binop variant is only intended to be used for reg-reg moves where
2552 // part of the Dest register is untouched. 2517 // part of the Dest register is untouched.
2553 assert(this->getSrcSize() == 2); 2518 assert(this->getSrcSize() == 2);
2554 const Variable *Dest = this->getDest(); 2519 const Variable *Dest = this->getDest();
2555 assert(Dest == this->getSrc(0)); 2520 assert(Dest == this->getSrc(0));
2556 const auto SrcVar = llvm::cast<Variable>(this->getSrc(1)); 2521 const auto *SrcVar = llvm::cast<Variable>(this->getSrc(1));
2557 assert(Dest->hasReg() && SrcVar->hasReg()); 2522 assert(Dest->hasReg() && SrcVar->hasReg());
2558 typename InstX86Base<Machine>::Traits::Assembler *Asm = 2523 typename InstX86Base<Machine>::Traits::Assembler *Asm =
2559 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>(); 2524 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>();
2560 Asm->movss(IceType_f32, 2525 Asm->movss(IceType_f32,
2561 InstX86Base<Machine>::Traits::RegisterSet::getEncodedXmm( 2526 InstX86Base<Machine>::Traits::getEncodedXmm(Dest->getRegNum()),
2562 Dest->getRegNum()), 2527 InstX86Base<Machine>::Traits::getEncodedXmm(SrcVar->getRegNum()));
2563 InstX86Base<Machine>::Traits::RegisterSet::getEncodedXmm(
2564 SrcVar->getRegNum()));
2565 } 2528 }
2566 2529
2567 template <class Machine> 2530 template <class Machine>
2568 void InstX86Movsx<Machine>::emitIAS(const Cfg *Func) const { 2531 void InstX86Movsx<Machine>::emitIAS(const Cfg *Func) const {
2569 assert(this->getSrcSize() == 1); 2532 assert(this->getSrcSize() == 1);
2570 const Variable *Dest = this->getDest(); 2533 const Variable *Dest = this->getDest();
2571 const Operand *Src = this->getSrc(0); 2534 const Operand *Src = this->getSrc(0);
2572 // Dest must be a > 8-bit register, but Src can be 8-bit. In practice we just 2535 // Dest must be a > 8-bit register, but Src can be 8-bit. In practice we just
2573 // use the full register for Dest to avoid having an OperandSizeOverride 2536 // use the full register for Dest to avoid having an OperandSizeOverride
2574 // prefix. It also allows us to only dispatch on SrcTy. 2537 // prefix. It also allows us to only dispatch on SrcTy.
(...skipping 39 matching lines...) Expand 10 before | Expand all | Expand 10 after
2614 Str << "nop (variant = " << Variant << ")"; 2577 Str << "nop (variant = " << Variant << ")";
2615 } 2578 }
2616 2579
2617 template <class Machine> void InstX86Fld<Machine>::emit(const Cfg *Func) const { 2580 template <class Machine> void InstX86Fld<Machine>::emit(const Cfg *Func) const {
2618 if (!BuildDefs::dump()) 2581 if (!BuildDefs::dump())
2619 return; 2582 return;
2620 Ostream &Str = Func->getContext()->getStrEmit(); 2583 Ostream &Str = Func->getContext()->getStrEmit();
2621 assert(this->getSrcSize() == 1); 2584 assert(this->getSrcSize() == 1);
2622 Type Ty = this->getSrc(0)->getType(); 2585 Type Ty = this->getSrc(0)->getType();
2623 SizeT Width = typeWidthInBytes(Ty); 2586 SizeT Width = typeWidthInBytes(Ty);
2624 const auto Var = llvm::dyn_cast<Variable>(this->getSrc(0)); 2587 const auto *Var = llvm::dyn_cast<Variable>(this->getSrc(0));
2625 if (Var && Var->hasReg()) { 2588 if (Var && Var->hasReg()) {
2626 // This is a physical xmm register, so we need to spill it to a temporary 2589 // This is a physical xmm register, so we need to spill it to a temporary
2627 // stack slot. 2590 // stack slot.
2628 Str << "\tsubl\t$" << Width << ", %esp" 2591 Str << "\tsubl\t$" << Width << ", %esp"
2629 << "\n"; 2592 << "\n";
2630 Str << "\tmov" 2593 Str << "\tmov"
2631 << InstX86Base<Machine>::Traits::TypeAttributes[Ty].SdSsString << "\t"; 2594 << InstX86Base<Machine>::Traits::TypeAttributes[Ty].SdSsString << "\t";
2632 Var->emit(Func); 2595 Var->emit(Func);
2633 Str << ", (%esp)\n"; 2596 Str << ", (%esp)\n";
2634 Str << "\tfld" << this->getFldString(Ty) << "\t" 2597 Str << "\tfld" << this->getFldString(Ty) << "\t"
2635 << "(%esp)\n"; 2598 << "(%esp)\n";
2636 Str << "\taddl\t$" << Width << ", %esp"; 2599 Str << "\taddl\t$" << Width << ", %esp";
2637 return; 2600 return;
2638 } 2601 }
2639 Str << "\tfld" << this->getFldString(Ty) << "\t"; 2602 Str << "\tfld" << this->getFldString(Ty) << "\t";
2640 this->getSrc(0)->emit(Func); 2603 this->getSrc(0)->emit(Func);
2641 } 2604 }
2642 2605
2643 template <class Machine> 2606 template <class Machine>
2644 void InstX86Fld<Machine>::emitIAS(const Cfg *Func) const { 2607 void InstX86Fld<Machine>::emitIAS(const Cfg *Func) const {
2645 typename InstX86Base<Machine>::Traits::Assembler *Asm = 2608 typename InstX86Base<Machine>::Traits::Assembler *Asm =
2646 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>(); 2609 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>();
2647 assert(this->getSrcSize() == 1); 2610 assert(this->getSrcSize() == 1);
2648 const Operand *Src = this->getSrc(0); 2611 const Operand *Src = this->getSrc(0);
2649 Type Ty = Src->getType(); 2612 Type Ty = Src->getType();
2650 if (const auto Var = llvm::dyn_cast<Variable>(Src)) { 2613 if (const auto *Var = llvm::dyn_cast<Variable>(Src)) {
2651 if (Var->hasReg()) { 2614 if (Var->hasReg()) {
2652 // This is a physical xmm register, so we need to spill it to a temporary 2615 // This is a physical xmm register, so we need to spill it to a temporary
2653 // stack slot. 2616 // stack slot.
2654 Immediate Width(typeWidthInBytes(Ty)); 2617 Immediate Width(typeWidthInBytes(Ty));
2655 Asm->sub(IceType_i32, 2618 Asm->sub(IceType_i32,
2656 InstX86Base<Machine>::Traits::RegisterSet::Encoded_Reg_esp, 2619 InstX86Base<Machine>::Traits::RegisterSet::Encoded_Reg_esp,
2657 Width); 2620 Width);
2658 typename InstX86Base<Machine>::Traits::Address StackSlot = 2621 typename InstX86Base<Machine>::Traits::Address StackSlot =
2659 typename InstX86Base<Machine>::Traits::Address( 2622 typename InstX86Base<Machine>::Traits::Address(
2660 InstX86Base<Machine>::Traits::RegisterSet::Encoded_Reg_esp, 0); 2623 InstX86Base<Machine>::Traits::RegisterSet::Encoded_Reg_esp, 0);
2661 Asm->movss(Ty, StackSlot, 2624 Asm->movss(Ty, StackSlot,
2662 InstX86Base<Machine>::Traits::RegisterSet::getEncodedXmm( 2625 InstX86Base<Machine>::Traits::getEncodedXmm(Var->getRegNum()));
2663 Var->getRegNum()));
2664 Asm->fld(Ty, StackSlot); 2626 Asm->fld(Ty, StackSlot);
2665 Asm->add(IceType_i32, 2627 Asm->add(IceType_i32,
2666 InstX86Base<Machine>::Traits::RegisterSet::Encoded_Reg_esp, 2628 InstX86Base<Machine>::Traits::RegisterSet::Encoded_Reg_esp,
2667 Width); 2629 Width);
2668 } else { 2630 } else {
2669 typename InstX86Base<Machine>::Traits::Address StackAddr( 2631 typename InstX86Base<Machine>::Traits::Address StackAddr(
2670 static_cast<typename InstX86Base<Machine>::Traits::TargetLowering *>( 2632 static_cast<typename InstX86Base<Machine>::Traits::TargetLowering *>(
2671 Func->getTarget()) 2633 Func->getTarget())
2672 ->stackVarToAsmOperand(Var)); 2634 ->stackVarToAsmOperand(Var));
2673 Asm->fld(Ty, StackAddr); 2635 Asm->fld(Ty, StackAddr);
2674 } 2636 }
2675 } else if (const auto Mem = llvm::dyn_cast< 2637 } else if (const auto *Mem = llvm::dyn_cast<
2676 typename InstX86Base<Machine>::Traits::X86OperandMem>(Src)) { 2638 typename InstX86Base<Machine>::Traits::X86OperandMem>(Src)) {
2677 assert(Mem->getSegmentRegister() == 2639 assert(Mem->getSegmentRegister() ==
2678 InstX86Base<Machine>::Traits::X86OperandMem::DefaultSegment); 2640 InstX86Base<Machine>::Traits::X86OperandMem::DefaultSegment);
2679 Asm->fld(Ty, Mem->toAsmAddress(Asm)); 2641 Asm->fld(Ty, Mem->toAsmAddress(Asm));
2680 } else if (const auto Imm = llvm::dyn_cast<Constant>(Src)) { 2642 } else if (const auto *Imm = llvm::dyn_cast<Constant>(Src)) {
2681 Asm->fld(Ty, InstX86Base<Machine>::Traits::Address::ofConstPool(Asm, Imm)); 2643 Asm->fld(Ty, InstX86Base<Machine>::Traits::Address::ofConstPool(Asm, Imm));
2682 } else { 2644 } else {
2683 llvm_unreachable("Unexpected operand type"); 2645 llvm_unreachable("Unexpected operand type");
2684 } 2646 }
2685 } 2647 }
2686 2648
2687 template <class Machine> void InstX86Fld<Machine>::dump(const Cfg *Func) const { 2649 template <class Machine> void InstX86Fld<Machine>::dump(const Cfg *Func) const {
2688 if (!BuildDefs::dump()) 2650 if (!BuildDefs::dump())
2689 return; 2651 return;
2690 Ostream &Str = Func->getContext()->getStrDump(); 2652 Ostream &Str = Func->getContext()->getStrDump();
(...skipping 59 matching lines...) Expand 10 before | Expand all | Expand 10 after
2750 // Dest is a physical (xmm) register, so st(0) needs to go through memory. 2712 // Dest is a physical (xmm) register, so st(0) needs to go through memory.
2751 // Hack this by creating a temporary stack slot, spilling st(0) there, 2713 // Hack this by creating a temporary stack slot, spilling st(0) there,
2752 // loading it into the xmm register, and deallocating the stack slot. 2714 // loading it into the xmm register, and deallocating the stack slot.
2753 Immediate Width(typeWidthInBytes(Ty)); 2715 Immediate Width(typeWidthInBytes(Ty));
2754 Asm->sub(IceType_i32, 2716 Asm->sub(IceType_i32,
2755 InstX86Base<Machine>::Traits::RegisterSet::Encoded_Reg_esp, Width); 2717 InstX86Base<Machine>::Traits::RegisterSet::Encoded_Reg_esp, Width);
2756 typename InstX86Base<Machine>::Traits::Address StackSlot = 2718 typename InstX86Base<Machine>::Traits::Address StackSlot =
2757 typename InstX86Base<Machine>::Traits::Address( 2719 typename InstX86Base<Machine>::Traits::Address(
2758 InstX86Base<Machine>::Traits::RegisterSet::Encoded_Reg_esp, 0); 2720 InstX86Base<Machine>::Traits::RegisterSet::Encoded_Reg_esp, 0);
2759 Asm->fstp(Ty, StackSlot); 2721 Asm->fstp(Ty, StackSlot);
2760 Asm->movss(Ty, InstX86Base<Machine>::Traits::RegisterSet::getEncodedXmm( 2722 Asm->movss(Ty,
2761 Dest->getRegNum()), 2723 InstX86Base<Machine>::Traits::getEncodedXmm(Dest->getRegNum()),
2762 StackSlot); 2724 StackSlot);
2763 Asm->add(IceType_i32, 2725 Asm->add(IceType_i32,
2764 InstX86Base<Machine>::Traits::RegisterSet::Encoded_Reg_esp, Width); 2726 InstX86Base<Machine>::Traits::RegisterSet::Encoded_Reg_esp, Width);
2765 } 2727 }
2766 } 2728 }
2767 2729
2768 template <class Machine> 2730 template <class Machine>
2769 void InstX86Fstp<Machine>::dump(const Cfg *Func) const { 2731 void InstX86Fstp<Machine>::dump(const Cfg *Func) const {
2770 if (!BuildDefs::dump()) 2732 if (!BuildDefs::dump())
2771 return; 2733 return;
(...skipping 44 matching lines...) Expand 10 before | Expand all | Expand 10 after
2816 .PackString << "\t"; 2778 .PackString << "\t";
2817 this->getSrc(1)->emit(Func); 2779 this->getSrc(1)->emit(Func);
2818 Str << ", "; 2780 Str << ", ";
2819 this->getSrc(0)->emit(Func); 2781 this->getSrc(0)->emit(Func);
2820 Str << ", "; 2782 Str << ", ";
2821 Variable *Dest = this->getDest(); 2783 Variable *Dest = this->getDest();
2822 // pextrw must take a register dest. There is an SSE4.1 version that takes a 2784 // pextrw must take a register dest. There is an SSE4.1 version that takes a
2823 // memory dest, but we aren't using it. For uniformity, just restrict them 2785 // memory dest, but we aren't using it. For uniformity, just restrict them
2824 // all to have a register dest for now. 2786 // all to have a register dest for now.
2825 assert(Dest->hasReg()); 2787 assert(Dest->hasReg());
2826 Dest->asType(IceType_i32)->emit(Func); 2788 Dest->asType(IceType_i32, Dest->getRegNum())->emit(Func);
2827 } 2789 }
2828 2790
2829 template <class Machine> 2791 template <class Machine>
2830 void InstX86Pextr<Machine>::emitIAS(const Cfg *Func) const { 2792 void InstX86Pextr<Machine>::emitIAS(const Cfg *Func) const {
2831 assert(this->getSrcSize() == 2); 2793 assert(this->getSrcSize() == 2);
2832 // pextrb and pextrd are SSE4.1 instructions. 2794 // pextrb and pextrd are SSE4.1 instructions.
2833 const Variable *Dest = this->getDest(); 2795 const Variable *Dest = this->getDest();
2834 Type DispatchTy = Dest->getType(); 2796 Type DispatchTy = InstX86Base<Machine>::Traits::getInVectorElementType(
2797 this->getSrc(0)->getType());
2835 assert(DispatchTy == IceType_i16 || 2798 assert(DispatchTy == IceType_i16 ||
2836 static_cast<typename InstX86Base<Machine>::Traits::TargetLowering *>( 2799 static_cast<typename InstX86Base<Machine>::Traits::TargetLowering *>(
2837 Func->getTarget()) 2800 Func->getTarget())
2838 ->getInstructionSet() >= InstX86Base<Machine>::Traits::SSE4_1); 2801 ->getInstructionSet() >= InstX86Base<Machine>::Traits::SSE4_1);
2839 // pextrw must take a register dest. There is an SSE4.1 version that takes a 2802 // pextrw must take a register dest. There is an SSE4.1 version that takes a
2840 // memory dest, but we aren't using it. For uniformity, just restrict them 2803 // memory dest, but we aren't using it. For uniformity, just restrict them
2841 // all to have a register dest for now. 2804 // all to have a register dest for now.
2842 assert(Dest->hasReg()); 2805 assert(Dest->hasReg());
2843 // pextrw's Src(0) must be a register (both SSE4.1 and SSE2). 2806 // pextrw's Src(0) must be a register (both SSE4.1 and SSE2).
2844 assert(llvm::cast<Variable>(this->getSrc(0))->hasReg()); 2807 assert(llvm::cast<Variable>(this->getSrc(0))->hasReg());
2845 static const typename InstX86Base<Machine>::Traits::Assembler:: 2808 static const typename InstX86Base<Machine>::Traits::Assembler::
2846 template ThreeOpImmEmitter< 2809 template ThreeOpImmEmitter<
2847 typename InstX86Base<Machine>::Traits::RegisterSet::GPRRegister, 2810 typename InstX86Base<Machine>::Traits::RegisterSet::GPRRegister,
2848 typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister> 2811 typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister>
2849 Emitter = {&InstX86Base<Machine>::Traits::Assembler::pextr, nullptr}; 2812 Emitter = {&InstX86Base<Machine>::Traits::Assembler::pextr, nullptr};
2850 emitIASThreeOpImmOps< 2813 emitIASThreeOpImmOps<
2851 Machine, typename InstX86Base<Machine>::Traits::RegisterSet::GPRRegister, 2814 Machine, typename InstX86Base<Machine>::Traits::RegisterSet::GPRRegister,
2852 typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister, 2815 typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister,
2853 InstX86Base<Machine>::Traits::RegisterSet::getEncodedGPR, 2816 InstX86Base<Machine>::Traits::getEncodedGPR,
2854 InstX86Base<Machine>::Traits::RegisterSet::getEncodedXmm>( 2817 InstX86Base<Machine>::Traits::getEncodedXmm>(
2855 Func, DispatchTy, Dest, this->getSrc(0), this->getSrc(1), Emitter); 2818 Func, DispatchTy, Dest, this->getSrc(0), this->getSrc(1), Emitter);
2856 } 2819 }
2857 2820
2858 template <class Machine> 2821 template <class Machine>
2859 void InstX86Pinsr<Machine>::emit(const Cfg *Func) const { 2822 void InstX86Pinsr<Machine>::emit(const Cfg *Func) const {
2860 if (!BuildDefs::dump()) 2823 if (!BuildDefs::dump())
2861 return; 2824 return;
2862 Ostream &Str = Func->getContext()->getStrEmit(); 2825 Ostream &Str = Func->getContext()->getStrEmit();
2863 assert(this->getSrcSize() == 3); 2826 assert(this->getSrcSize() == 3);
2864 // pinsrb and pinsrd are SSE4.1 instructions. 2827 // pinsrb and pinsrd are SSE4.1 instructions.
2865 assert(this->getDest()->getType() == IceType_v8i16 || 2828 assert(this->getDest()->getType() == IceType_v8i16 ||
2866 this->getDest()->getType() == IceType_v8i1 || 2829 this->getDest()->getType() == IceType_v8i1 ||
2867 static_cast<typename InstX86Base<Machine>::Traits::TargetLowering *>( 2830 static_cast<typename InstX86Base<Machine>::Traits::TargetLowering *>(
2868 Func->getTarget()) 2831 Func->getTarget())
2869 ->getInstructionSet() >= InstX86Base<Machine>::Traits::SSE4_1); 2832 ->getInstructionSet() >= InstX86Base<Machine>::Traits::SSE4_1);
2870 Str << "\t" << this->Opcode 2833 Str << "\t" << this->Opcode
2871 << InstX86Base< 2834 << InstX86Base<
2872 Machine>::Traits::TypeAttributes[this->getDest()->getType()] 2835 Machine>::Traits::TypeAttributes[this->getDest()->getType()]
2873 .PackString << "\t"; 2836 .PackString << "\t";
2874 this->getSrc(2)->emit(Func); 2837 this->getSrc(2)->emit(Func);
2875 Str << ", "; 2838 Str << ", ";
2876 Operand *Src1 = this->getSrc(1); 2839 Operand *Src1 = this->getSrc(1);
2877 if (const auto Src1Var = llvm::dyn_cast<Variable>(Src1)) { 2840 if (const auto *Src1Var = llvm::dyn_cast<Variable>(Src1)) {
2878 // If src1 is a register, it should always be r32. 2841 // If src1 is a register, it should always be r32.
2879 if (Src1Var->hasReg()) { 2842 if (Src1Var->hasReg()) {
2880 Src1Var->asType(IceType_i32)->emit(Func); 2843 int32_t NewRegNum =
2844 InstX86Base<Machine>::Traits::getBaseReg(Src1Var->getRegNum());
2845 const Variable *NewSrc = Src1Var->asType(IceType_i32, NewRegNum);
2846 NewSrc->emit(Func);
2881 } else { 2847 } else {
2882 Src1Var->emit(Func); 2848 Src1Var->emit(Func);
2883 } 2849 }
2884 } else { 2850 } else {
2885 Src1->emit(Func); 2851 Src1->emit(Func);
2886 } 2852 }
2887 Str << ", "; 2853 Str << ", ";
2888 this->getDest()->emit(Func); 2854 this->getDest()->emit(Func);
2889 } 2855 }
2890 2856
2891 template <class Machine> 2857 template <class Machine>
2892 void InstX86Pinsr<Machine>::emitIAS(const Cfg *Func) const { 2858 void InstX86Pinsr<Machine>::emitIAS(const Cfg *Func) const {
2893 assert(this->getSrcSize() == 3); 2859 assert(this->getSrcSize() == 3);
2894 assert(this->getDest() == this->getSrc(0)); 2860 assert(this->getDest() == this->getSrc(0));
2895 // pinsrb and pinsrd are SSE4.1 instructions. 2861 // pinsrb and pinsrd are SSE4.1 instructions.
2896 const Operand *Src0 = this->getSrc(1); 2862 const Operand *Src0 = this->getSrc(1);
2897 Type DispatchTy = Src0->getType(); 2863 Type DispatchTy = Src0->getType();
2898 assert(DispatchTy == IceType_i16 || 2864 assert(DispatchTy == IceType_i16 ||
2899 static_cast<typename InstX86Base<Machine>::Traits::TargetLowering *>( 2865 static_cast<typename InstX86Base<Machine>::Traits::TargetLowering *>(
2900 Func->getTarget()) 2866 Func->getTarget())
2901 ->getInstructionSet() >= InstX86Base<Machine>::Traits::SSE4_1); 2867 ->getInstructionSet() >= InstX86Base<Machine>::Traits::SSE4_1);
2902 // If src1 is a register, it should always be r32 (this should fall out from 2868 // If src1 is a register, it should always be r32 (this should fall out from
2903 // the encodings for ByteRegs overlapping the encodings for r32), but we have 2869 // the encodings for ByteRegs overlapping the encodings for r32), but we have
2904 // to trust the regalloc to not choose "ah", where it doesn't overlap. 2870 // to make sure the register allocator didn't choose an 8-bit high register
2871 // like "ah".
2872 if (BuildDefs::asserts()) {
2873 if (auto *Src0Var = llvm::dyn_cast<Variable>(Src0)) {
2874 if (Src0Var->hasReg()) {
2875 int32_t RegNum = Src0Var->getRegNum();
2876 int32_t BaseRegNum = InstX86Base<Machine>::Traits::getBaseReg(RegNum);
2877 (void)BaseRegNum;
2878 assert(InstX86Base<Machine>::Traits::getEncodedGPR(RegNum) ==
2879 InstX86Base<Machine>::Traits::getEncodedGPR(BaseRegNum));
2880 }
2881 }
2882 }
2905 static const typename InstX86Base<Machine>::Traits::Assembler:: 2883 static const typename InstX86Base<Machine>::Traits::Assembler::
2906 template ThreeOpImmEmitter< 2884 template ThreeOpImmEmitter<
2907 typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister, 2885 typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister,
2908 typename InstX86Base<Machine>::Traits::RegisterSet::GPRRegister> 2886 typename InstX86Base<Machine>::Traits::RegisterSet::GPRRegister>
2909 Emitter = {&InstX86Base<Machine>::Traits::Assembler::pinsr, 2887 Emitter = {&InstX86Base<Machine>::Traits::Assembler::pinsr,
2910 &InstX86Base<Machine>::Traits::Assembler::pinsr}; 2888 &InstX86Base<Machine>::Traits::Assembler::pinsr};
2911 emitIASThreeOpImmOps< 2889 emitIASThreeOpImmOps<
2912 Machine, typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister, 2890 Machine, typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister,
2913 typename InstX86Base<Machine>::Traits::RegisterSet::GPRRegister, 2891 typename InstX86Base<Machine>::Traits::RegisterSet::GPRRegister,
2914 InstX86Base<Machine>::Traits::RegisterSet::getEncodedXmm, 2892 InstX86Base<Machine>::Traits::getEncodedXmm,
2915 InstX86Base<Machine>::Traits::RegisterSet::getEncodedGPR>( 2893 InstX86Base<Machine>::Traits::getEncodedGPR>(
2916 Func, DispatchTy, this->getDest(), Src0, this->getSrc(2), Emitter); 2894 Func, DispatchTy, this->getDest(), Src0, this->getSrc(2), Emitter);
2917 } 2895 }
2918 2896
2919 template <class Machine> 2897 template <class Machine>
2920 void InstX86Pshufd<Machine>::emitIAS(const Cfg *Func) const { 2898 void InstX86Pshufd<Machine>::emitIAS(const Cfg *Func) const {
2921 assert(this->getSrcSize() == 2); 2899 assert(this->getSrcSize() == 2);
2922 const Variable *Dest = this->getDest(); 2900 const Variable *Dest = this->getDest();
2923 Type Ty = Dest->getType(); 2901 Type Ty = Dest->getType();
2924 static const typename InstX86Base<Machine>::Traits::Assembler:: 2902 static const typename InstX86Base<Machine>::Traits::Assembler::
2925 template ThreeOpImmEmitter< 2903 template ThreeOpImmEmitter<
2926 typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister, 2904 typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister,
2927 typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister> 2905 typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister>
2928 Emitter = {&InstX86Base<Machine>::Traits::Assembler::pshufd, 2906 Emitter = {&InstX86Base<Machine>::Traits::Assembler::pshufd,
2929 &InstX86Base<Machine>::Traits::Assembler::pshufd}; 2907 &InstX86Base<Machine>::Traits::Assembler::pshufd};
2930 emitIASThreeOpImmOps< 2908 emitIASThreeOpImmOps<
2931 Machine, typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister, 2909 Machine, typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister,
2932 typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister, 2910 typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister,
2933 InstX86Base<Machine>::Traits::RegisterSet::getEncodedXmm, 2911 InstX86Base<Machine>::Traits::getEncodedXmm,
2934 InstX86Base<Machine>::Traits::RegisterSet::getEncodedXmm>( 2912 InstX86Base<Machine>::Traits::getEncodedXmm>(
2935 Func, Ty, Dest, this->getSrc(0), this->getSrc(1), Emitter); 2913 Func, Ty, Dest, this->getSrc(0), this->getSrc(1), Emitter);
2936 } 2914 }
2937 2915
2938 template <class Machine> 2916 template <class Machine>
2939 void InstX86Shufps<Machine>::emitIAS(const Cfg *Func) const { 2917 void InstX86Shufps<Machine>::emitIAS(const Cfg *Func) const {
2940 assert(this->getSrcSize() == 3); 2918 assert(this->getSrcSize() == 3);
2941 const Variable *Dest = this->getDest(); 2919 const Variable *Dest = this->getDest();
2942 assert(Dest == this->getSrc(0)); 2920 assert(Dest == this->getSrc(0));
2943 Type Ty = Dest->getType(); 2921 Type Ty = Dest->getType();
2944 static const typename InstX86Base<Machine>::Traits::Assembler:: 2922 static const typename InstX86Base<Machine>::Traits::Assembler::
2945 template ThreeOpImmEmitter< 2923 template ThreeOpImmEmitter<
2946 typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister, 2924 typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister,
2947 typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister> 2925 typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister>
2948 Emitter = {&InstX86Base<Machine>::Traits::Assembler::shufps, 2926 Emitter = {&InstX86Base<Machine>::Traits::Assembler::shufps,
2949 &InstX86Base<Machine>::Traits::Assembler::shufps}; 2927 &InstX86Base<Machine>::Traits::Assembler::shufps};
2950 emitIASThreeOpImmOps< 2928 emitIASThreeOpImmOps<
2951 Machine, typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister, 2929 Machine, typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister,
2952 typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister, 2930 typename InstX86Base<Machine>::Traits::RegisterSet::XmmRegister,
2953 InstX86Base<Machine>::Traits::RegisterSet::getEncodedXmm, 2931 InstX86Base<Machine>::Traits::getEncodedXmm,
2954 InstX86Base<Machine>::Traits::RegisterSet::getEncodedXmm>( 2932 InstX86Base<Machine>::Traits::getEncodedXmm>(
2955 Func, Ty, Dest, this->getSrc(1), this->getSrc(2), Emitter); 2933 Func, Ty, Dest, this->getSrc(1), this->getSrc(2), Emitter);
2956 } 2934 }
2957 2935
2958 template <class Machine> void InstX86Pop<Machine>::emit(const Cfg *Func) const { 2936 template <class Machine> void InstX86Pop<Machine>::emit(const Cfg *Func) const {
2959 if (!BuildDefs::dump()) 2937 if (!BuildDefs::dump())
2960 return; 2938 return;
2961 Ostream &Str = Func->getContext()->getStrEmit(); 2939 Ostream &Str = Func->getContext()->getStrEmit();
2962 assert(this->getSrcSize() == 0); 2940 assert(this->getSrcSize() == 0);
2963 Str << "\tpop\t"; 2941 Str << "\tpop\t";
2964 this->getDest()->emit(Func); 2942 this->getDest()->emit(Func);
2965 } 2943 }
2966 2944
2967 template <class Machine> 2945 template <class Machine>
2968 void InstX86Pop<Machine>::emitIAS(const Cfg *Func) const { 2946 void InstX86Pop<Machine>::emitIAS(const Cfg *Func) const {
2969 assert(this->getSrcSize() == 0); 2947 assert(this->getSrcSize() == 0);
2970 typename InstX86Base<Machine>::Traits::Assembler *Asm = 2948 typename InstX86Base<Machine>::Traits::Assembler *Asm =
2971 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>(); 2949 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>();
2972 if (this->getDest()->hasReg()) { 2950 if (this->getDest()->hasReg()) {
2973 Asm->popl(InstX86Base<Machine>::Traits::RegisterSet::getEncodedGPR( 2951 Asm->popl(InstX86Base<Machine>::Traits::getEncodedGPR(
2974 this->getDest()->getRegNum())); 2952 this->getDest()->getRegNum()));
2975 } else { 2953 } else {
2976 Asm->popl( 2954 Asm->popl(
2977 static_cast<typename InstX86Base<Machine>::Traits::TargetLowering *>( 2955 static_cast<typename InstX86Base<Machine>::Traits::TargetLowering *>(
2978 Func->getTarget()) 2956 Func->getTarget())
2979 ->stackVarToAsmOperand(this->getDest())); 2957 ->stackVarToAsmOperand(this->getDest()));
2980 } 2958 }
2981 } 2959 }
2982 2960
2983 template <class Machine> void InstX86Pop<Machine>::dump(const Cfg *Func) const { 2961 template <class Machine> void InstX86Pop<Machine>::dump(const Cfg *Func) const {
(...skipping 31 matching lines...) Expand 10 before | Expand all | Expand 10 after
3015 Str << "esp = sub.i32 esp, " << Amount; 2993 Str << "esp = sub.i32 esp, " << Amount;
3016 } 2994 }
3017 2995
3018 template <class Machine> 2996 template <class Machine>
3019 void InstX86Push<Machine>::emit(const Cfg *Func) const { 2997 void InstX86Push<Machine>::emit(const Cfg *Func) const {
3020 if (!BuildDefs::dump()) 2998 if (!BuildDefs::dump())
3021 return; 2999 return;
3022 Ostream &Str = Func->getContext()->getStrEmit(); 3000 Ostream &Str = Func->getContext()->getStrEmit();
3023 assert(this->getSrcSize() == 1); 3001 assert(this->getSrcSize() == 1);
3024 // Push is currently only used for saving GPRs. 3002 // Push is currently only used for saving GPRs.
3025 const auto Var = llvm::cast<Variable>(this->getSrc(0)); 3003 const auto *Var = llvm::cast<Variable>(this->getSrc(0));
3026 assert(Var->hasReg()); 3004 assert(Var->hasReg());
3027 Str << "\tpush\t"; 3005 Str << "\tpush\t";
3028 Var->emit(Func); 3006 Var->emit(Func);
3029 } 3007 }
3030 3008
3031 template <class Machine> 3009 template <class Machine>
3032 void InstX86Push<Machine>::emitIAS(const Cfg *Func) const { 3010 void InstX86Push<Machine>::emitIAS(const Cfg *Func) const {
3033 assert(this->getSrcSize() == 1); 3011 assert(this->getSrcSize() == 1);
3034 // Push is currently only used for saving GPRs. 3012 // Push is currently only used for saving GPRs.
3035 const auto Var = llvm::cast<Variable>(this->getSrc(0)); 3013 const auto *Var = llvm::cast<Variable>(this->getSrc(0));
3036 assert(Var->hasReg()); 3014 assert(Var->hasReg());
3037 typename InstX86Base<Machine>::Traits::Assembler *Asm = 3015 typename InstX86Base<Machine>::Traits::Assembler *Asm =
3038 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>(); 3016 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>();
3039 Asm->pushl(InstX86Base<Machine>::Traits::RegisterSet::getEncodedGPR( 3017 Asm->pushl(InstX86Base<Machine>::Traits::getEncodedGPR(Var->getRegNum()));
3040 Var->getRegNum()));
3041 } 3018 }
3042 3019
3043 template <class Machine> 3020 template <class Machine>
3044 void InstX86Push<Machine>::dump(const Cfg *Func) const { 3021 void InstX86Push<Machine>::dump(const Cfg *Func) const {
3045 if (!BuildDefs::dump()) 3022 if (!BuildDefs::dump())
3046 return; 3023 return;
3047 Ostream &Str = Func->getContext()->getStrDump(); 3024 Ostream &Str = Func->getContext()->getStrDump();
3048 Str << "push." << this->getSrc(0)->getType() << " "; 3025 Str << "push." << this->getSrc(0)->getType() << " ";
3049 this->dumpSources(Func); 3026 this->dumpSources(Func);
3050 } 3027 }
(...skipping 78 matching lines...) Expand 10 before | Expand all | Expand 10 after
3129 } 3106 }
3130 3107
3131 template <class Machine> 3108 template <class Machine>
3132 void InstX86Setcc<Machine>::emitIAS(const Cfg *Func) const { 3109 void InstX86Setcc<Machine>::emitIAS(const Cfg *Func) const {
3133 assert(Condition != InstX86Base<Machine>::Traits::Cond::Br_None); 3110 assert(Condition != InstX86Base<Machine>::Traits::Cond::Br_None);
3134 assert(this->getDest()->getType() == IceType_i1); 3111 assert(this->getDest()->getType() == IceType_i1);
3135 assert(this->getSrcSize() == 0); 3112 assert(this->getSrcSize() == 0);
3136 typename InstX86Base<Machine>::Traits::Assembler *Asm = 3113 typename InstX86Base<Machine>::Traits::Assembler *Asm =
3137 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>(); 3114 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>();
3138 if (this->getDest()->hasReg()) 3115 if (this->getDest()->hasReg())
3139 Asm->setcc(Condition, 3116 Asm->setcc(Condition, InstX86Base<Machine>::Traits::getEncodedGPR(
3140 InstX86Base<Machine>::Traits::RegisterSet::getEncodedByteReg( 3117 this->getDest()->getRegNum()));
3141 this->getDest()->getRegNum()));
3142 else 3118 else
3143 Asm->setcc( 3119 Asm->setcc(
3144 Condition, 3120 Condition,
3145 static_cast<typename InstX86Base<Machine>::Traits::TargetLowering *>( 3121 static_cast<typename InstX86Base<Machine>::Traits::TargetLowering *>(
3146 Func->getTarget()) 3122 Func->getTarget())
3147 ->stackVarToAsmOperand(this->getDest())); 3123 ->stackVarToAsmOperand(this->getDest()));
3148 return; 3124 return;
3149 } 3125 }
3150 3126
3151 template <class Machine> 3127 template <class Machine>
(...skipping 27 matching lines...) Expand all
3179 typename InstX86Base<Machine>::Traits::Assembler *Asm = 3155 typename InstX86Base<Machine>::Traits::Assembler *Asm =
3180 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>(); 3156 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>();
3181 Type Ty = this->getSrc(0)->getType(); 3157 Type Ty = this->getSrc(0)->getType();
3182 const auto Mem = 3158 const auto Mem =
3183 llvm::cast<typename InstX86Base<Machine>::Traits::X86OperandMem>( 3159 llvm::cast<typename InstX86Base<Machine>::Traits::X86OperandMem>(
3184 this->getSrc(0)); 3160 this->getSrc(0));
3185 assert(Mem->getSegmentRegister() == 3161 assert(Mem->getSegmentRegister() ==
3186 InstX86Base<Machine>::Traits::X86OperandMem::DefaultSegment); 3162 InstX86Base<Machine>::Traits::X86OperandMem::DefaultSegment);
3187 const typename InstX86Base<Machine>::Traits::Address Addr = 3163 const typename InstX86Base<Machine>::Traits::Address Addr =
3188 Mem->toAsmAddress(Asm); 3164 Mem->toAsmAddress(Asm);
3189 const auto VarReg = llvm::cast<Variable>(this->getSrc(1)); 3165 const auto *VarReg = llvm::cast<Variable>(this->getSrc(1));
3190 assert(VarReg->hasReg()); 3166 assert(VarReg->hasReg());
3191 const typename InstX86Base<Machine>::Traits::RegisterSet::GPRRegister Reg = 3167 const typename InstX86Base<Machine>::Traits::RegisterSet::GPRRegister Reg =
3192 InstX86Base<Machine>::Traits::RegisterSet::getEncodedGPR( 3168 InstX86Base<Machine>::Traits::getEncodedGPR(VarReg->getRegNum());
3193 VarReg->getRegNum());
3194 Asm->xadd(Ty, Addr, Reg, this->Locked); 3169 Asm->xadd(Ty, Addr, Reg, this->Locked);
3195 } 3170 }
3196 3171
3197 template <class Machine> 3172 template <class Machine>
3198 void InstX86Xadd<Machine>::dump(const Cfg *Func) const { 3173 void InstX86Xadd<Machine>::dump(const Cfg *Func) const {
3199 if (!BuildDefs::dump()) 3174 if (!BuildDefs::dump())
3200 return; 3175 return;
3201 Ostream &Str = Func->getContext()->getStrDump(); 3176 Ostream &Str = Func->getContext()->getStrDump();
3202 if (this->Locked) { 3177 if (this->Locked) {
3203 Str << "lock "; 3178 Str << "lock ";
(...skipping 16 matching lines...) Expand all
3220 3195
3221 template <class Machine> 3196 template <class Machine>
3222 void InstX86Xchg<Machine>::emitIAS(const Cfg *Func) const { 3197 void InstX86Xchg<Machine>::emitIAS(const Cfg *Func) const {
3223 assert(this->getSrcSize() == 2); 3198 assert(this->getSrcSize() == 2);
3224 typename InstX86Base<Machine>::Traits::Assembler *Asm = 3199 typename InstX86Base<Machine>::Traits::Assembler *Asm =
3225 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>(); 3200 Func->getAssembler<typename InstX86Base<Machine>::Traits::Assembler>();
3226 Type Ty = this->getSrc(0)->getType(); 3201 Type Ty = this->getSrc(0)->getType();
3227 const auto *VarReg1 = llvm::cast<Variable>(this->getSrc(1)); 3202 const auto *VarReg1 = llvm::cast<Variable>(this->getSrc(1));
3228 assert(VarReg1->hasReg()); 3203 assert(VarReg1->hasReg());
3229 const typename InstX86Base<Machine>::Traits::RegisterSet::GPRRegister Reg1 = 3204 const typename InstX86Base<Machine>::Traits::RegisterSet::GPRRegister Reg1 =
3230 InstX86Base<Machine>::Traits::RegisterSet::getEncodedGPR( 3205 InstX86Base<Machine>::Traits::getEncodedGPR(VarReg1->getRegNum());
3231 VarReg1->getRegNum());
3232 3206
3233 if (const auto *VarReg0 = llvm::dyn_cast<Variable>(this->getSrc(0))) { 3207 if (const auto *VarReg0 = llvm::dyn_cast<Variable>(this->getSrc(0))) {
3234 assert(VarReg0->hasReg()); 3208 assert(VarReg0->hasReg());
3235 const typename InstX86Base<Machine>::Traits::RegisterSet::GPRRegister Reg0 = 3209 const typename InstX86Base<Machine>::Traits::RegisterSet::GPRRegister Reg0 =
3236 InstX86Base<Machine>::Traits::RegisterSet::getEncodedGPR( 3210 InstX86Base<Machine>::Traits::getEncodedGPR(VarReg0->getRegNum());
3237 VarReg0->getRegNum());
3238 Asm->xchg(Ty, Reg0, Reg1); 3211 Asm->xchg(Ty, Reg0, Reg1);
3239 return; 3212 return;
3240 } 3213 }
3241 3214
3242 const auto *Mem = 3215 const auto *Mem =
3243 llvm::cast<typename InstX86Base<Machine>::Traits::X86OperandMem>( 3216 llvm::cast<typename InstX86Base<Machine>::Traits::X86OperandMem>(
3244 this->getSrc(0)); 3217 this->getSrc(0));
3245 assert(Mem->getSegmentRegister() == 3218 assert(Mem->getSegmentRegister() ==
3246 InstX86Base<Machine>::Traits::X86OperandMem::DefaultSegment); 3219 InstX86Base<Machine>::Traits::X86OperandMem::DefaultSegment);
3247 const typename InstX86Base<Machine>::Traits::Address Addr = 3220 const typename InstX86Base<Machine>::Traits::Address Addr =
(...skipping 61 matching lines...) Expand 10 before | Expand all | Expand 10 after
3309 return; 3282 return;
3310 Ostream &Str = Func->getContext()->getStrDump(); 3283 Ostream &Str = Func->getContext()->getStrDump();
3311 Str << "IACA_END"; 3284 Str << "IACA_END";
3312 } 3285 }
3313 3286
3314 } // end of namespace X86Internal 3287 } // end of namespace X86Internal
3315 3288
3316 } // end of namespace Ice 3289 } // end of namespace Ice
3317 3290
3318 #endif // SUBZERO_SRC_ICEINSTX86BASEIMPL_H 3291 #endif // SUBZERO_SRC_ICEINSTX86BASEIMPL_H
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698