blob: 52f6ea4a6e2f2e609c47d520c23400f7c3d25872 [file] [log] [blame]
Eugene Zelenko076468c2017-09-20 21:35:51 +00001//===- ARMTargetTransformInfo.h - ARM specific TTI --------------*- C++ -*-===//
Chandler Carruth93dcdc42015-01-31 11:17:59 +00002//
Chandler Carruth2946cd72019-01-19 08:50:56 +00003// 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
Chandler Carruth93dcdc42015-01-31 11:17:59 +00006//
7//===----------------------------------------------------------------------===//
Eugene Zelenko076468c2017-09-20 21:35:51 +00008//
Chandler Carruth93dcdc42015-01-31 11:17:59 +00009/// \file
10/// This file a TargetTransformInfo::Concept conforming object specific to the
11/// ARM target machine. It uses the target's detailed information to
12/// provide more precise answers to certain TTI queries, while letting the
13/// target independent and default TTI implementations handle the rest.
Eugene Zelenko076468c2017-09-20 21:35:51 +000014//
Chandler Carruth93dcdc42015-01-31 11:17:59 +000015//===----------------------------------------------------------------------===//
16
17#ifndef LLVM_LIB_TARGET_ARM_ARMTARGETTRANSFORMINFO_H
18#define LLVM_LIB_TARGET_ARM_ARMTARGETTRANSFORMINFO_H
19
20#include "ARM.h"
Eugene Zelenko076468c2017-09-20 21:35:51 +000021#include "ARMSubtarget.h"
Chandler Carruth93dcdc42015-01-31 11:17:59 +000022#include "ARMTargetMachine.h"
Eugene Zelenko076468c2017-09-20 21:35:51 +000023#include "llvm/ADT/ArrayRef.h"
Chandler Carruth93dcdc42015-01-31 11:17:59 +000024#include "llvm/Analysis/TargetTransformInfo.h"
25#include "llvm/CodeGen/BasicTTIImpl.h"
Eugene Zelenko076468c2017-09-20 21:35:51 +000026#include "llvm/IR/Constant.h"
27#include "llvm/IR/Function.h"
28#include "llvm/MC/SubtargetFeature.h"
Chandler Carruth93dcdc42015-01-31 11:17:59 +000029
30namespace llvm {
31
Eugene Zelenko076468c2017-09-20 21:35:51 +000032class APInt;
33class ARMTargetLowering;
34class Instruction;
35class Loop;
36class SCEV;
37class ScalarEvolution;
38class Type;
39class Value;
40
Chandler Carruth93dcdc42015-01-31 11:17:59 +000041class ARMTTIImpl : public BasicTTIImplBase<ARMTTIImpl> {
Eugene Zelenko076468c2017-09-20 21:35:51 +000042 using BaseT = BasicTTIImplBase<ARMTTIImpl>;
43 using TTI = TargetTransformInfo;
44
Chandler Carruthc340ca82015-02-01 14:01:15 +000045 friend BaseT;
Chandler Carruth93dcdc42015-01-31 11:17:59 +000046
47 const ARMSubtarget *ST;
48 const ARMTargetLowering *TLI;
49
Florian Hahn4adcfcf2017-07-13 08:26:17 +000050 // Currently the following features are excluded from InlineFeatureWhitelist.
Simon Tatham760df472019-05-28 16:13:20 +000051 // ModeThumb, FeatureNoARM, ModeSoftFloat, FeatureFP64, FeatureD32
Florian Hahn4adcfcf2017-07-13 08:26:17 +000052 // Depending on whether they are set or unset, different
53 // instructions/registers are available. For example, inlining a callee with
54 // -thumb-mode in a caller with +thumb-mode, may cause the assembler to
55 // fail if the callee uses ARM only instructions, e.g. in inline asm.
56 const FeatureBitset InlineFeatureWhitelist = {
57 ARM::FeatureVFP2, ARM::FeatureVFP3, ARM::FeatureNEON, ARM::FeatureThumb2,
58 ARM::FeatureFP16, ARM::FeatureVFP4, ARM::FeatureFPARMv8,
Bernard Ogdenb828bb22018-08-17 11:29:49 +000059 ARM::FeatureFullFP16, ARM::FeatureFP16FML, ARM::FeatureHWDivThumb,
Florian Hahn4adcfcf2017-07-13 08:26:17 +000060 ARM::FeatureHWDivARM, ARM::FeatureDB, ARM::FeatureV7Clrex,
61 ARM::FeatureAcquireRelease, ARM::FeatureSlowFPBrcc,
62 ARM::FeaturePerfMon, ARM::FeatureTrustZone, ARM::Feature8MSecExt,
63 ARM::FeatureCrypto, ARM::FeatureCRC, ARM::FeatureRAS,
64 ARM::FeatureFPAO, ARM::FeatureFuseAES, ARM::FeatureZCZeroing,
65 ARM::FeatureProfUnpredicate, ARM::FeatureSlowVGETLNi32,
66 ARM::FeatureSlowVDUP32, ARM::FeaturePreferVMOVSR,
67 ARM::FeaturePrefISHSTBarrier, ARM::FeatureMuxedUnits,
68 ARM::FeatureSlowOddRegister, ARM::FeatureSlowLoadDSubreg,
69 ARM::FeatureDontWidenVMOVS, ARM::FeatureExpandMLx,
70 ARM::FeatureHasVMLxHazards, ARM::FeatureNEONForFPMovs,
71 ARM::FeatureNEONForFP, ARM::FeatureCheckVLDnAlign,
72 ARM::FeatureHasSlowFPVMLx, ARM::FeatureVMLxForwarding,
73 ARM::FeaturePref32BitThumb, ARM::FeatureAvoidPartialCPSR,
74 ARM::FeatureCheapPredicableCPSR, ARM::FeatureAvoidMOVsShOp,
75 ARM::FeatureHasRetAddrStack, ARM::FeatureHasNoBranchPredictor,
76 ARM::FeatureDSP, ARM::FeatureMP, ARM::FeatureVirtualization,
77 ARM::FeatureMClass, ARM::FeatureRClass, ARM::FeatureAClass,
78 ARM::FeatureNaClTrap, ARM::FeatureStrictAlign, ARM::FeatureLongCalls,
79 ARM::FeatureExecuteOnly, ARM::FeatureReserveR9, ARM::FeatureNoMovt,
80 ARM::FeatureNoNegativeImmediates
81 };
82
Chandler Carruthc956ab662015-02-01 14:22:17 +000083 const ARMSubtarget *getST() const { return ST; }
Chandler Carruthc340ca82015-02-01 14:01:15 +000084 const ARMTargetLowering *getTLI() const { return TLI; }
85
Chandler Carruth93dcdc42015-01-31 11:17:59 +000086public:
Eric Christophera4e5d3c2015-09-16 23:38:13 +000087 explicit ARMTTIImpl(const ARMBaseTargetMachine *TM, const Function &F)
Mehdi Amini5010ebf2015-07-09 02:08:42 +000088 : BaseT(TM, F.getParent()->getDataLayout()), ST(TM->getSubtargetImpl(F)),
89 TLI(ST->getTargetLowering()) {}
Chandler Carruth93dcdc42015-01-31 11:17:59 +000090
Florian Hahn4adcfcf2017-07-13 08:26:17 +000091 bool areInlineCompatible(const Function *Caller,
92 const Function *Callee) const;
93
Silviu Barangae748c9e2015-09-01 11:19:15 +000094 bool enableInterleavedAccessVectorization() { return true; }
95
Sam Parker67756c02019-02-07 13:32:54 +000096 bool shouldFavorBackedgeIndex(const Loop *L) const {
Evandro Menezes85bd3972019-04-04 22:40:06 +000097 if (L->getHeader()->getParent()->hasOptSize())
Sam Parker67756c02019-02-07 13:32:54 +000098 return false;
99 return ST->isMClass() && ST->isThumb2() && L->getNumBlocks() == 1;
100 }
101
Renato Golin4b18a512016-04-18 12:06:47 +0000102 /// Floating-point computation using ARMv8 AArch32 Advanced
103 /// SIMD instructions remains unchanged from ARMv7. Only AArch64 SIMD
104 /// is IEEE-754 compliant, but it's not covered in this target.
Renato Golin5cb666a2016-04-14 20:42:18 +0000105 bool isFPVectorizationPotentiallyUnsafe() {
Renato Golin4b18a512016-04-18 12:06:47 +0000106 return !ST->isTargetDarwin();
Renato Golin5cb666a2016-04-14 20:42:18 +0000107 }
108
Chandler Carruth93dcdc42015-01-31 11:17:59 +0000109 /// \name Scalar TTI Implementations
110 /// @{
111
Sjoerd Meijer38c2cd02016-07-14 07:44:20 +0000112 int getIntImmCodeSizeCost(unsigned Opcode, unsigned Idx, const APInt &Imm,
113 Type *Ty);
114
Chandler Carruth93dcdc42015-01-31 11:17:59 +0000115 using BaseT::getIntImmCost;
Chandler Carruth93205eb2015-08-05 18:08:10 +0000116 int getIntImmCost(const APInt &Imm, Type *Ty);
Chandler Carruth93dcdc42015-01-31 11:17:59 +0000117
Tim Northover903f81b2016-04-15 18:17:18 +0000118 int getIntImmCost(unsigned Opcode, unsigned Idx, const APInt &Imm, Type *Ty);
Tim Northover5c02f9a2016-04-13 23:08:27 +0000119
Chandler Carruth93dcdc42015-01-31 11:17:59 +0000120 /// @}
121
122 /// \name Vector TTI Implementations
123 /// @{
124
125 unsigned getNumberOfRegisters(bool Vector) {
126 if (Vector) {
127 if (ST->hasNEON())
128 return 16;
129 return 0;
130 }
131
132 if (ST->isThumb1Only())
133 return 8;
134 return 13;
135 }
136
Daniel Neilsonc0112ae2017-06-12 14:22:21 +0000137 unsigned getRegisterBitWidth(bool Vector) const {
Chandler Carruth93dcdc42015-01-31 11:17:59 +0000138 if (Vector) {
139 if (ST->hasNEON())
140 return 128;
141 return 0;
142 }
143
144 return 32;
145 }
146
Wei Mi062c7442015-05-06 17:12:25 +0000147 unsigned getMaxInterleaveFactor(unsigned VF) {
Diana Picus92423ce2016-06-27 09:08:23 +0000148 return ST->getMaxInterleaveFactor();
Chandler Carruth93dcdc42015-01-31 11:17:59 +0000149 }
150
Sjoerd Meijerea31ddb2019-04-30 10:28:50 +0000151 int getMemcpyCost(const Instruction *I);
152
Chandler Carruth93205eb2015-08-05 18:08:10 +0000153 int getShuffleCost(TTI::ShuffleKind Kind, Type *Tp, int Index, Type *SubTp);
Chandler Carruth93dcdc42015-01-31 11:17:59 +0000154
Jonas Paulssonfccc7d62017-04-12 11:49:08 +0000155 int getCastInstrCost(unsigned Opcode, Type *Dst, Type *Src,
156 const Instruction *I = nullptr);
Chandler Carruth93dcdc42015-01-31 11:17:59 +0000157
Jonas Paulssonfccc7d62017-04-12 11:49:08 +0000158 int getCmpSelInstrCost(unsigned Opcode, Type *ValTy, Type *CondTy,
159 const Instruction *I = nullptr);
Chandler Carruth93dcdc42015-01-31 11:17:59 +0000160
Chandler Carruth93205eb2015-08-05 18:08:10 +0000161 int getVectorInstrCost(unsigned Opcode, Type *Val, unsigned Index);
Chandler Carruth93dcdc42015-01-31 11:17:59 +0000162
Fangrui Songf78650a2018-07-30 19:41:25 +0000163 int getAddressComputationCost(Type *Val, ScalarEvolution *SE,
Mohammed Agabaria23599ba2017-01-05 14:03:41 +0000164 const SCEV *Ptr);
Chandler Carruth93dcdc42015-01-31 11:17:59 +0000165
Chandler Carruth93205eb2015-08-05 18:08:10 +0000166 int getArithmeticInstrCost(
Chandler Carruth93dcdc42015-01-31 11:17:59 +0000167 unsigned Opcode, Type *Ty,
168 TTI::OperandValueKind Op1Info = TTI::OK_AnyValue,
169 TTI::OperandValueKind Op2Info = TTI::OK_AnyValue,
170 TTI::OperandValueProperties Opd1PropInfo = TTI::OP_None,
Mohammed Agabaria2c96c432017-01-11 08:23:37 +0000171 TTI::OperandValueProperties Opd2PropInfo = TTI::OP_None,
172 ArrayRef<const Value *> Args = ArrayRef<const Value *>());
Chandler Carruth93dcdc42015-01-31 11:17:59 +0000173
Chandler Carruth93205eb2015-08-05 18:08:10 +0000174 int getMemoryOpCost(unsigned Opcode, Type *Src, unsigned Alignment,
Jonas Paulssonfccc7d62017-04-12 11:49:08 +0000175 unsigned AddressSpace, const Instruction *I = nullptr);
Chandler Carruth93dcdc42015-01-31 11:17:59 +0000176
Chandler Carruth93205eb2015-08-05 18:08:10 +0000177 int getInterleavedMemoryOpCost(unsigned Opcode, Type *VecTy, unsigned Factor,
178 ArrayRef<unsigned> Indices, unsigned Alignment,
Dorit Nuzman34da6dd2018-10-31 09:57:56 +0000179 unsigned AddressSpace,
180 bool UseMaskForCond = false,
181 bool UseMaskForGaps = false);
Oliver Stannard4df1cc02016-10-07 08:48:24 +0000182
Sam Parker757ac022019-06-12 12:00:42 +0000183 bool isLoweredToCall(const Function *F);
184 bool isHardwareLoopProfitable(Loop *L, ScalarEvolution &SE,
185 AssumptionCache &AC,
186 TargetLibraryInfo *LibInfo,
Chen Zhengc5b918d2019-06-19 01:26:31 +0000187 HardwareLoopInfo &HWLoopInfo);
Sam Parker757ac022019-06-12 12:00:42 +0000188
Sam Parker19a08e42017-07-25 08:51:30 +0000189 void getUnrollingPreferences(Loop *L, ScalarEvolution &SE,
190 TTI::UnrollingPreferences &UP);
191
Oliver Stannard4df1cc02016-10-07 08:48:24 +0000192 bool shouldBuildLookupTablesForConstant(Constant *C) const {
193 // In the ROPI and RWPI relocation models we can't have pointers to global
194 // variables or functions in constant data, so don't convert switches to
195 // lookup tables if any of the values would need relocation.
196 if (ST->isROPI() || ST->isRWPI())
197 return !C->needsRelocation();
198
199 return true;
200 }
Chandler Carruth93dcdc42015-01-31 11:17:59 +0000201 /// @}
202};
203
204} // end namespace llvm
205
Eugene Zelenko076468c2017-09-20 21:35:51 +0000206#endif // LLVM_LIB_TARGET_ARM_ARMTARGETTRANSFORMINFO_H