1 /* 2 * Copyright (c) 2023 Huawei Device Co., Ltd. 3 * Licensed under the Apache License, Version 2.0 (the "License"); 4 * you may not use this file except in compliance with the License. 5 * You may obtain a copy of the License at 6 * 7 * http://www.apache.org/licenses/LICENSE-2.0 8 * 9 * Unless required by applicable law or agreed to in writing, software 10 * distributed under the License is distributed on an "AS IS" BASIS, 11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 * See the License for the specific language governing permissions and 13 * limitations under the License. 14 */ 15 16 #ifndef MAPLEBE_INCLUDE_CG_X86_64_CGFUNC_H 17 #define MAPLEBE_INCLUDE_CG_X86_64_CGFUNC_H 18 19 #include "cgfunc.h" 20 #include "x64_memlayout.h" 21 #include "x64_isa.h" 22 #include "x64_reg_info.h" 23 #include "x64_optimize_common.h" 24 25 namespace maplebe { 26 class X64CGFunc : public CGFunc { 27 public: X64CGFunc(MIRModule & mod,CG & c,MIRFunction & f,BECommon & b,MemPool & memPool,StackMemPool & stackMp,MapleAllocator & mallocator,uint32 funcId)28 X64CGFunc(MIRModule &mod, CG &c, MIRFunction &f, BECommon &b, MemPool &memPool, StackMemPool &stackMp, 29 MapleAllocator &mallocator, uint32 funcId) 30 : CGFunc(mod, c, f, b, memPool, stackMp, mallocator, funcId), calleeSavedRegs(mallocator.Adapter()) 31 { 32 CGFunc::SetMemlayout(*memPool.New<X64MemLayout>(b, f, mallocator)); 33 CGFunc::GetMemlayout()->SetCurrFunction(*this); 34 CGFunc::SetTargetRegInfo(*memPool.New<X64RegInfo>(mallocator, X64CallConvImpl::GetCallConvKind(f))); 35 CGFunc::GetTargetRegInfo()->SetCurrFunction(*this); 36 } 37 /* null implementation yet */ NewInsnModifier()38 InsnVisitor *NewInsnModifier() override 39 { 40 return memPool->New<X64InsnVisitor>(*this); 41 } 42 void MergeReturn() override; 43 void SelectDassign(DassignNode &stmt, Operand &opnd0) override; 44 void SelectRegassign(RegassignNode &stmt, Operand &opnd0) override; 45 void SelectIassign(IassignNode &stmt) override; 46 void SelectReturn(Operand *opnd) override; 47 void SelectCondGoto(CondGotoNode &stmt, Operand &opnd0, Operand &opnd1) override; 48 void SelectCondSpecialCase1(CondGotoNode &stmt, BaseNode &opnd0) override; 49 void SelectCondSpecialCase2(const CondGotoNode &stmt, BaseNode &opnd0) override; 50 void SelectGoto(GotoNode &stmt) override; 51 void SelectCall(CallNode &callNode) override; 52 void SelectIcall(IcallNode &icallNode) override; 53 void SelectIntrinsicCall(IntrinsiccallNode &intrinsiccallNode) override; 54 Operand *SelectCclz(IntrinsicopNode &intrinopNode) override; 55 void SelectComment(CommentNode &comment) override; 56 Operand *SelectDread(const BaseNode &parent, AddrofNode &expr) override; 57 RegOperand *SelectRegread(RegreadNode &expr) override; 58 Operand *SelectIread(const BaseNode &parent, IreadNode &expr, int extraOffset = 0, 59 PrimType finalBitFieldDestType = kPtyInvalid) override; 60 Operand *SelectIntConst(const MIRIntConst &intConst, const BaseNode &parent) override; 61 Operand *SelectFloatConst(MIRFloatConst &floatConst, const BaseNode &parent) override; 62 Operand *SelectDoubleConst(MIRDoubleConst &doubleConst, const BaseNode &parent) override; 63 void SelectAdd(Operand &resOpnd, Operand &opnd0, Operand &opnd1, PrimType primType) override; 64 Operand *SelectAdd(BinaryNode &node, Operand &opnd0, Operand &opnd1, const BaseNode &parent) override; 65 Operand *SelectShift(BinaryNode &node, Operand &opnd0, Operand &opnd1, const BaseNode &parent) override; 66 void SelectMpy(Operand &resOpnd, Operand &opnd0, Operand &opnd1, PrimType primType) override; 67 Operand *SelectMpy(BinaryNode &node, Operand &opnd0, Operand &opnd1, const BaseNode &parent) override; 68 Operand *SelectRem(BinaryNode &node, Operand &opnd0, Operand &opnd1, const BaseNode &parent) override; 69 void SelectDiv(Operand &resOpnd, Operand &opnd0, Operand &opnd1, PrimType primType) override; 70 Operand *SelectDiv(BinaryNode &node, Operand &opnd0, Operand &opnd1, const BaseNode &parent) override; 71 Operand *SelectSub(BinaryNode &node, Operand &opnd0, Operand &opnd1, const BaseNode &parent) override; 72 void SelectSub(Operand &resOpnd, Operand &opnd0, Operand &opnd1, PrimType primType) override; 73 Operand *SelectBand(BinaryNode &node, Operand &opnd0, Operand &opnd1, const BaseNode &parent) override; 74 void SelectBand(Operand &resOpnd, Operand &opnd0, Operand &opnd1, PrimType primType) override; 75 void SelectMin(Operand &resOpnd, Operand &opnd0, Operand &opnd1, PrimType primType) override; 76 Operand *SelectMin(BinaryNode &node, Operand &opnd0, Operand &opnd1, const BaseNode &parent) override; 77 void SelectMax(Operand &resOpnd, Operand &opnd0, Operand &opnd1, PrimType primType) override; 78 Operand *SelectMax(BinaryNode &node, Operand &opnd0, Operand &opnd1, const BaseNode &parent) override; 79 Operand *SelectCmpOp(CompareNode &node, Operand &opnd0, Operand &opnd1, const BaseNode &parent) override; 80 Operand *SelectBior(BinaryNode &node, Operand &opnd0, Operand &opnd1, const BaseNode &parent) override; 81 void SelectBior(Operand &resOpnd, Operand &opnd0, Operand &opnd1, PrimType primType) override; 82 Operand *SelectBxor(BinaryNode &node, Operand &opnd0, Operand &opnd1, const BaseNode &parent) override; 83 void SelectBxor(Operand &resOpnd, Operand &opnd0, Operand &opnd1, PrimType primType) override; 84 Operand *SelectAbs(UnaryNode &node, Operand &opnd0) override; 85 Operand *SelectBnot(UnaryNode &node, Operand &opnd0, const BaseNode &parent) override; 86 Operand *SelectExtractbits(ExtractbitsNode &node, Operand &opnd0, const BaseNode &parent) override; 87 Operand *SelectRegularBitFieldLoad(ExtractbitsNode &node, const BaseNode &parent) override; 88 Operand *SelectLnot(UnaryNode &node, Operand &opnd0, const BaseNode &parent) override; 89 Operand *SelectNeg(UnaryNode &node, Operand &opnd0, const BaseNode &parent) override; 90 Operand *SelectSqrt(UnaryNode &node, Operand &opnd0, const BaseNode &parent) override; 91 Operand *SelectCeil(TypeCvtNode &node, Operand &opnd0, const BaseNode &parent) override; 92 Operand *SelectFloor(TypeCvtNode &node, Operand &opnd0, const BaseNode &parent) override; 93 Operand *SelectRetype(TypeCvtNode &node, Operand &opnd0) override; 94 Operand *SelectCvt(const BaseNode &parent, TypeCvtNode &node, Operand &opnd0) override; 95 Operand *SelectTrunc(TypeCvtNode &node, Operand &opnd0, const BaseNode &parent) override; 96 RegOperand &SelectCopy(Operand &src, PrimType srcType, PrimType dstType) override; 97 void SelectRangeGoto(RangeGotoNode &rangeGotoNode, Operand &opnd0) override; 98 Operand &GetOrCreateRflag() override; 99 const Operand *GetRflag() const override; 100 const LabelOperand *GetLabelOperand(LabelIdx labIdx) const override; 101 LabelOperand &GetOrCreateLabelOperand(LabelIdx labIdx) override; 102 LabelOperand &GetOrCreateLabelOperand(BB &bb) override; 103 RegOperand &CreateVirtualRegisterOperand(regno_t vRegNO) override; 104 RegOperand &GetOrCreateVirtualRegisterOperand(regno_t vRegNO) override; 105 RegOperand &GetOrCreateFramePointerRegOperand() override; 106 RegOperand &GetOrCreateStackBaseRegOperand() override; 107 RegOperand &GetZeroOpnd(uint32 size) override; 108 Operand &CreateCfiRegOperand(uint32 reg, uint32 size) override; 109 Operand &CreateImmOperand(PrimType primType, int64 val) override; 110 MemOperand *GetOrCreatSpillMem(regno_t vrNum, uint32 bitSize) override; 111 MemOperand *GetPseudoRegisterSpillMemoryOperand(PregIdx idx) override; 112 113 int32 GetBaseOffset(const SymbolAlloc &symbolAlloc) override; 114 RegOperand *GetBaseReg(const SymbolAlloc &symAlloc) override; 115 AddtoCalleeSaved(regno_t reg)116 void AddtoCalleeSaved(regno_t reg) override 117 { 118 const auto &[_, flag] = calleeSavedRegs.insert(static_cast<X64reg>(reg)); 119 DEBUG_ASSERT((IsGPRegister(static_cast<X64reg>(reg)) || IsFPSIMDRegister(static_cast<X64reg>(reg))), 120 "Int or FP registers are expected"); 121 if (flag) { 122 if (IsGPRegister(static_cast<X64reg>(reg))) { 123 ++numIntregToCalleeSave; 124 } else { 125 ++numFpregToCalleeSave; 126 } 127 } 128 } 129 GetCalleeSavedRegs()130 const MapleSet<x64::X64reg> &GetCalleeSavedRegs() const 131 { 132 return calleeSavedRegs; 133 } 134 SizeOfCalleeSaved()135 uint32 SizeOfCalleeSaved() const 136 { 137 uint32 size = numIntregToCalleeSave * kX64IntregBytelen + numFpregToCalleeSave * kX64FpregBytelen; 138 return RoundUp(size, GetMemlayout()->GetStackPtrAlignment()); 139 } 140 141 void FreeSpillRegMem(regno_t vrNum); 142 143 private: 144 MapleSet<x64::X64reg> calleeSavedRegs; 145 uint32 numIntregToCalleeSave = 0; 146 uint32 numFpregToCalleeSave = 0; 147 }; 148 149 class X64OpndDumpVisitor : public OpndDumpVisitor { 150 public: X64OpndDumpVisitor(const OpndDesc & operandDesc)151 explicit X64OpndDumpVisitor(const OpndDesc &operandDesc) : OpndDumpVisitor(operandDesc) {}; 152 ~X64OpndDumpVisitor() override = default; 153 154 private: 155 void Visit(RegOperand *v) final; 156 void Visit(ImmOperand *v) final; 157 void Visit(MemOperand *v) final; 158 void Visit(ListOperand *v) final; 159 void Visit(CondOperand *v) final; 160 void Visit(CommentOperand *v) final; 161 void Visit(StImmOperand *v) final; 162 void Visit(BitShiftOperand *v) final; 163 void Visit(ExtendShiftOperand *v) final; 164 void Visit(LabelOperand *v) final; 165 void Visit(FuncNameOperand *v) final; 166 void Visit(PhiOperand *v) final; 167 void DumpRegInfo(RegOperand &v); 168 }; 169 } /* namespace maplebe */ 170 #endif /* MAPLEBE_INCLUDE_CG_X86_64_CGFUNC_H */ 171