1 //===-- HexagonSelectionDAGInfo.cpp - Hexagon SelectionDAG Info -----------===// 2 // 3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 4 // See https://llvm.org/LICENSE.txt for license information. 5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 6 // 7 //===----------------------------------------------------------------------===// 8 // 9 // This file implements the HexagonSelectionDAGInfo class. 10 // 11 //===----------------------------------------------------------------------===// 12 13 #include "HexagonTargetMachine.h" 14 #include "llvm/CodeGen/SelectionDAG.h" 15 using namespace llvm; 16 17 #define DEBUG_TYPE "hexagon-selectiondag-info" 18 19 SDValue HexagonSelectionDAGInfo::EmitTargetCodeForMemcpy( 20 SelectionDAG &DAG, const SDLoc &dl, SDValue Chain, SDValue Dst, SDValue Src, 21 SDValue Size, Align Alignment, bool isVolatile, bool AlwaysInline, 22 MachinePointerInfo DstPtrInfo, MachinePointerInfo SrcPtrInfo) const { 23 ConstantSDNode *ConstantSize = dyn_cast<ConstantSDNode>(Size); 24 if (AlwaysInline || Alignment < Align(4) || !ConstantSize) 25 return SDValue(); 26 27 uint64_t SizeVal = ConstantSize->getZExtValue(); 28 if (SizeVal < 32 || (SizeVal % 8) != 0) 29 return SDValue(); 30 31 // Special case aligned memcpys with size >= 32 bytes and a multiple of 8. 32 // 33 const TargetLowering &TLI = *DAG.getSubtarget().getTargetLowering(); 34 TargetLowering::ArgListTy Args; 35 TargetLowering::ArgListEntry Entry; 36 Entry.Ty = DAG.getDataLayout().getIntPtrType(*DAG.getContext()); 37 Entry.Node = Dst; 38 Args.push_back(Entry); 39 Entry.Node = Src; 40 Args.push_back(Entry); 41 Entry.Node = Size; 42 Args.push_back(Entry); 43 44 const char *SpecialMemcpyName = 45 "__hexagon_memcpy_likely_aligned_min32bytes_mult8bytes"; 46 const MachineFunction &MF = DAG.getMachineFunction(); 47 bool LongCalls = MF.getSubtarget<HexagonSubtarget>().useLongCalls(); 48 unsigned Flags = LongCalls ? HexagonII::HMOTF_ConstExtended : 0; 49 50 TargetLowering::CallLoweringInfo CLI(DAG); 51 CLI.setDebugLoc(dl) 52 .setChain(Chain) 53 .setLibCallee( 54 TLI.getLibcallCallingConv(RTLIB::MEMCPY), 55 Type::getVoidTy(*DAG.getContext()), 56 DAG.getTargetExternalSymbol( 57 SpecialMemcpyName, TLI.getPointerTy(DAG.getDataLayout()), Flags), 58 std::move(Args)) 59 .setDiscardResult(); 60 61 std::pair<SDValue, SDValue> CallResult = TLI.LowerCallTo(CLI); 62 return CallResult.second; 63 } 64