Changeset View
Changeset View
Standalone View
Standalone View
llvm/lib/Target/ARM/ARMTargetTransformInfo.cpp
//===- ARMTargetTransformInfo.cpp - ARM specific TTI ----------------------===// | //===- ARMTargetTransformInfo.cpp - ARM specific TTI ----------------------===// | ||||
// | // | ||||
// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. | // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. | ||||
// See https://llvm.org/LICENSE.txt for license information. | // See https://llvm.org/LICENSE.txt for license information. | ||||
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception | // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception | ||||
// | // | ||||
//===----------------------------------------------------------------------===// | //===----------------------------------------------------------------------===// | ||||
#include "ARMTargetTransformInfo.h" | #include "ARMTargetTransformInfo.h" | ||||
#include "ARMSubtarget.h" | #include "ARMSubtarget.h" | ||||
#include "MCTargetDesc/ARMAddressingModes.h" | #include "MCTargetDesc/ARMAddressingModes.h" | ||||
#include "llvm/ADT/APInt.h" | #include "llvm/ADT/APInt.h" | ||||
#include "llvm/ADT/SmallVector.h" | #include "llvm/ADT/SmallVector.h" | ||||
#include "llvm/Analysis/LoopInfo.h" | #include "llvm/Analysis/LoopInfo.h" | ||||
#include "llvm/CodeGen/ComplexArithmeticPass.h" | |||||
#include "llvm/CodeGen/CostTable.h" | #include "llvm/CodeGen/CostTable.h" | ||||
#include "llvm/CodeGen/ISDOpcodes.h" | #include "llvm/CodeGen/ISDOpcodes.h" | ||||
#include "llvm/CodeGen/ValueTypes.h" | #include "llvm/CodeGen/ValueTypes.h" | ||||
#include "llvm/IR/BasicBlock.h" | #include "llvm/IR/BasicBlock.h" | ||||
dnsampaio: nit. Add new line? | |||||
#include "llvm/IR/DataLayout.h" | #include "llvm/IR/DataLayout.h" | ||||
#include "llvm/IR/DerivedTypes.h" | #include "llvm/IR/DerivedTypes.h" | ||||
#include "llvm/IR/Instruction.h" | #include "llvm/IR/Instruction.h" | ||||
#include "llvm/IR/Instructions.h" | #include "llvm/IR/Instructions.h" | ||||
#include "llvm/IR/Intrinsics.h" | |||||
#include "llvm/IR/IntrinsicInst.h" | #include "llvm/IR/IntrinsicInst.h" | ||||
#include "llvm/IR/Intrinsics.h" | |||||
#include "llvm/IR/IntrinsicsARM.h" | #include "llvm/IR/IntrinsicsARM.h" | ||||
#include "llvm/IR/PatternMatch.h" | #include "llvm/IR/PatternMatch.h" | ||||
#include "llvm/IR/Type.h" | #include "llvm/IR/Type.h" | ||||
#include "llvm/MC/SubtargetFeature.h" | #include "llvm/MC/SubtargetFeature.h" | ||||
#include "llvm/Support/Casting.h" | #include "llvm/Support/Casting.h" | ||||
#include "llvm/Support/KnownBits.h" | #include "llvm/Support/KnownBits.h" | ||||
#include "llvm/Support/MachineValueType.h" | #include "llvm/Support/MachineValueType.h" | ||||
#include "llvm/Target/TargetMachine.h" | #include "llvm/Target/TargetMachine.h" | ||||
Show All 13 Lines | static cl::opt<bool> EnableMaskedLoadStores( | ||||
"enable-arm-maskedldst", cl::Hidden, cl::init(true), | "enable-arm-maskedldst", cl::Hidden, cl::init(true), | ||||
cl::desc("Enable the generation of masked loads and stores")); | cl::desc("Enable the generation of masked loads and stores")); | ||||
static cl::opt<bool> DisableLowOverheadLoops( | static cl::opt<bool> DisableLowOverheadLoops( | ||||
"disable-arm-loloops", cl::Hidden, cl::init(false), | "disable-arm-loloops", cl::Hidden, cl::init(false), | ||||
cl::desc("Disable the generation of low-overhead loops")); | cl::desc("Disable the generation of low-overhead loops")); | ||||
static cl::opt<bool> | static cl::opt<bool> | ||||
AllowWLSLoops("allow-arm-wlsloops", cl::Hidden, cl::init(true), | AllowWLSLoops("allow-arm-wlsloops", cl::Hidden, cl::init(true), | ||||
These are probably unneeded? dmgreen: These are probably unneeded? | |||||
cl::desc("Enable the generation of WLS loops")); | cl::desc("Enable the generation of WLS loops")); | ||||
extern cl::opt<TailPredication::Mode> EnableTailPredication; | extern cl::opt<TailPredication::Mode> EnableTailPredication; | ||||
extern cl::opt<bool> EnableMaskedGatherScatters; | extern cl::opt<bool> EnableMaskedGatherScatters; | ||||
extern cl::opt<unsigned> MVEMaxSupportedInterleaveFactor; | extern cl::opt<unsigned> MVEMaxSupportedInterleaveFactor; | ||||
Show All 39 Lines | |||||
TTI::AddressingModeKind | TTI::AddressingModeKind | ||||
ARMTTIImpl::getPreferredAddressingMode(const Loop *L, | ARMTTIImpl::getPreferredAddressingMode(const Loop *L, | ||||
ScalarEvolution *SE) const { | ScalarEvolution *SE) const { | ||||
if (ST->hasMVEIntegerOps()) | if (ST->hasMVEIntegerOps()) | ||||
return TTI::AMK_PostIndexed; | return TTI::AMK_PostIndexed; | ||||
if (L->getHeader()->getParent()->hasOptSize()) | if (L->getHeader()->getParent()->hasOptSize()) | ||||
return TTI::AMK_None; | return TTI::AMK_None; | ||||
Not Done ReplyInline Actionsnit. extra space. dnsampaio: nit. extra space. | |||||
if (ST->isMClass() && ST->isThumb2() && | if (ST->isMClass() && ST->isThumb2() && | ||||
L->getNumBlocks() == 1) | L->getNumBlocks() == 1) | ||||
return TTI::AMK_PreIndexed; | return TTI::AMK_PreIndexed; | ||||
return TTI::AMK_None; | return TTI::AMK_None; | ||||
} | } | ||||
▲ Show 20 Lines • Show All 2,213 Lines • ▼ Show 20 Lines | |||||
} | } | ||||
bool ARMTTIImpl::preferPredicatedReductionSelect( | bool ARMTTIImpl::preferPredicatedReductionSelect( | ||||
unsigned Opcode, Type *Ty, TTI::ReductionFlags Flags) const { | unsigned Opcode, Type *Ty, TTI::ReductionFlags Flags) const { | ||||
if (!ST->hasMVEIntegerOps()) | if (!ST->hasMVEIntegerOps()) | ||||
return false; | return false; | ||||
return true; | return true; | ||||
} | } | ||||
Intrinsic::ID | |||||
ARMTTIImpl::getComplexArithmeticIntrinsic(ComplexArithmeticCandidate *C, | |||||
unsigned &IntArgCount) const { | |||||
if (C->getDataType()->isDoubleTy() || | |||||
(C->getDataType()->isVectorTy() && | |||||
cast<VectorType>(C->getDataType())->getElementType()->isDoubleTy())) | |||||
return Intrinsic::not_intrinsic; | |||||
unsigned Rotation = C->getRotation(); | |||||
if (ST->hasMVEFloatOps()) { | |||||
Value *RotVal = ConstantInt::get(Type::getInt32Ty(C->getContext()), | |||||
(Rotation == 90 ? 0 : 1)); | |||||
if (C->Type == ComplexArithmeticCandidate::Complex_Add) { | |||||
Value *Halving = ConstantInt::get(Type::getInt32Ty(C->getContext()), 1); | |||||
C->ExtraOperandsPre.push_back(Halving); | |||||
C->ExtraOperandsPre.push_back(RotVal); | |||||
IntArgCount = 4; | |||||
return Intrinsic::arm_mve_vcaddq; | |||||
} | |||||
RotVal = | |||||
ConstantInt::get(Type::getInt32Ty(C->getContext()), (Rotation / 90)); | |||||
if (C->Type == ComplexArithmeticCandidate::Complex_Mla || | |||||
(C->Type == ComplexArithmeticCandidate::Complex_Mul && | |||||
C->isTerminalInPair())) { | |||||
C->ExtraOperandsPre.push_back(RotVal); | |||||
C->Type = ComplexArithmeticCandidate::Complex_Mla; | |||||
IntArgCount = 4; | |||||
return Intrinsic::arm_mve_vcmlaq; | |||||
} | |||||
if (C->Type == ComplexArithmeticCandidate::Complex_Mul) { | |||||
C->ExtraOperandsPre.push_back(RotVal); | |||||
IntArgCount = 3; | |||||
return Intrinsic::arm_mve_vcmulq; | |||||
} | |||||
} | |||||
if (ST->hasNEON()) { | |||||
if (C->Type == ComplexArithmeticCandidate::Complex_Add) { | |||||
IntArgCount = 2; | |||||
if (Rotation == 90) | |||||
return Intrinsic::arm_neon_vcadd_rot90; | |||||
if (Rotation == 270) | |||||
return Intrinsic::arm_neon_vcadd_rot270; | |||||
} | |||||
} | |||||
return Intrinsic::not_intrinsic; | |||||
} | |||||
No newline at end of file |
nit. Add new line?