Author: Alessandro Decina Date: 2021-05-16T11:01:47-07:00 New Revision: 833e9b2ea7a7290f8833d524c8f8865558c1016a
URL: https://github.com/llvm/llvm-project/commit/833e9b2ea7a7290f8833d524c8f8865558c1016a DIFF: https://github.com/llvm/llvm-project/commit/833e9b2ea7a7290f8833d524c8f8865558c1016a.diff LOG: [BPF] add support for 32 bit registers in inline asm Add "w" constraint type which allows selecting 32 bit registers. 32 bit registers were added in https://reviews.llvm.org/rGca31c3bb3ff149850b664838fbbc7d40ce571879. Differential Revision: https://reviews.llvm.org/D102118 Added: clang/test/CodeGen/bpf-inline-asm.c llvm/test/CodeGen/BPF/inlineasm-wreg.ll Modified: clang/lib/Basic/Targets/BPF.cpp clang/lib/Basic/Targets/BPF.h llvm/lib/Target/BPF/BPFISelLowering.cpp llvm/lib/Target/BPF/BPFISelLowering.h Removed: ################################################################################ diff --git a/clang/lib/Basic/Targets/BPF.cpp b/clang/lib/Basic/Targets/BPF.cpp index 2fe2450b9a654..0b0298df30a57 100644 --- a/clang/lib/Basic/Targets/BPF.cpp +++ b/clang/lib/Basic/Targets/BPF.cpp @@ -46,3 +46,14 @@ ArrayRef<Builtin::Info> BPFTargetInfo::getTargetBuiltins() const { return llvm::makeArrayRef(BuiltinInfo, clang::BPF::LastTSBuiltin - Builtin::FirstTSBuiltin); } + +bool BPFTargetInfo::handleTargetFeatures(std::vector<std::string> &Features, + DiagnosticsEngine &Diags) { + for (const auto &Feature : Features) { + if (Feature == "+alu32") { + HasAlu32 = true; + } + } + + return true; +} diff --git a/clang/lib/Basic/Targets/BPF.h b/clang/lib/Basic/Targets/BPF.h index 06b451db189af..393a91ff53a51 100644 --- a/clang/lib/Basic/Targets/BPF.h +++ b/clang/lib/Basic/Targets/BPF.h @@ -23,6 +23,7 @@ namespace targets { class LLVM_LIBRARY_VISIBILITY BPFTargetInfo : public TargetInfo { static const Builtin::Info BuiltinInfo[]; + bool HasAlu32 = false; public: BPFTargetInfo(const llvm::Triple &Triple, const TargetOptions &) @@ -55,6 +56,8 @@ class LLVM_LIBRARY_VISIBILITY BPFTargetInfo : public TargetInfo { bool Enabled) const override { Features[Name] = Enabled; } + bool handleTargetFeatures(std::vector<std::string> &Features, + DiagnosticsEngine &Diags) override; ArrayRef<Builtin::Info> getTargetBuiltins() const override; @@ -68,7 +71,16 @@ class LLVM_LIBRARY_VISIBILITY BPFTargetInfo : public TargetInfo { ArrayRef<const char *> getGCCRegNames() const override { return None; } bool validateAsmConstraint(const char *&Name, - TargetInfo::ConstraintInfo &info) const override { + TargetInfo::ConstraintInfo &Info) const override { + switch (*Name) { + default: + break; + case 'w': + if (HasAlu32) { + Info.setAllowsRegister(); + } + break; + } return true; } @@ -93,6 +105,10 @@ class LLVM_LIBRARY_VISIBILITY BPFTargetInfo : public TargetInfo { void fillValidCPUList(SmallVectorImpl<StringRef> &Values) const override; bool setCPU(const std::string &Name) override { + if (Name == "v3") { + HasAlu32 = true; + } + StringRef CPUName(Name); return isValidCPUName(CPUName); } diff --git a/clang/test/CodeGen/bpf-inline-asm.c b/clang/test/CodeGen/bpf-inline-asm.c new file mode 100644 index 0000000000000..d85bcbe02bc3f --- /dev/null +++ b/clang/test/CodeGen/bpf-inline-asm.c @@ -0,0 +1,31 @@ +// REQUIRES: bpf-registered-target +// RUN: %clang -target bpf -emit-llvm -S -Xclang -target-feature -Xclang +alu32 %s -o - | FileCheck %s +// RUN: %clang -target bpf -emit-llvm -S -mcpu=v3 %s -o - | FileCheck %s + +void test_generic_constraints(int var32, long var64) { + asm("%0 = %1" + : "=r"(var32) + : "0"(var32)); + // CHECK: [[R32_ARG:%[a-zA-Z0-9]+]] = load i32, i32* + // CHECK: call i32 asm "$0 = $1", "=r,0"(i32 [[R32_ARG]]) + + asm("%0 = %1" + : "=r"(var64) + : "0"(var64)); + // CHECK: [[R64_ARG:%[a-zA-Z0-9]+]] = load i64, i64* + // CHECK: call i64 asm "$0 = $1", "=r,0"(i64 [[R64_ARG]]) + + asm("%0 = %1" + : "=r"(var64) + : "r"(var64)); + // CHECK: [[R64_ARG:%[a-zA-Z0-9]+]] = load i64, i64* + // CHECK: call i64 asm "$0 = $1", "=r,r"(i64 [[R64_ARG]]) +} + +void test_constraint_w(int a) { + asm("%0 = %1" + : "=w"(a) + : "w"(a)); + // CHECK: [[R32_ARG:%[a-zA-Z0-9]+]] = load i32, i32* + // CHECK: call i32 asm "$0 = $1", "=w,w"(i32 [[R32_ARG]]) +} diff --git a/llvm/lib/Target/BPF/BPFISelLowering.cpp b/llvm/lib/Target/BPF/BPFISelLowering.cpp index 8b16e0d3a23d0..c543dfcfca953 100644 --- a/llvm/lib/Target/BPF/BPFISelLowering.cpp +++ b/llvm/lib/Target/BPF/BPFISelLowering.cpp @@ -220,6 +220,20 @@ bool BPFTargetLowering::isZExtFree(EVT VT1, EVT VT2) const { return NumBits1 == 32 && NumBits2 == 64; } +BPFTargetLowering::ConstraintType +BPFTargetLowering::getConstraintType(StringRef Constraint) const { + if (Constraint.size() == 1) { + switch (Constraint[0]) { + default: + break; + case 'w': + return C_RegisterClass; + } + } + + return TargetLowering::getConstraintType(Constraint); +} + std::pair<unsigned, const TargetRegisterClass *> BPFTargetLowering::getRegForInlineAsmConstraint(const TargetRegisterInfo *TRI, StringRef Constraint, @@ -229,6 +243,10 @@ BPFTargetLowering::getRegForInlineAsmConstraint(const TargetRegisterInfo *TRI, switch (Constraint[0]) { case 'r': // GENERAL_REGS return std::make_pair(0U, &BPF::GPRRegClass); + case 'w': + if (HasAlu32) + return std::make_pair(0U, &BPF::GPR32RegClass); + break; default: break; } diff --git a/llvm/lib/Target/BPF/BPFISelLowering.h b/llvm/lib/Target/BPF/BPFISelLowering.h index 51e59f39036ca..d5007425a7f8d 100644 --- a/llvm/lib/Target/BPF/BPFISelLowering.h +++ b/llvm/lib/Target/BPF/BPFISelLowering.h @@ -46,6 +46,9 @@ class BPFTargetLowering : public TargetLowering { // with the given GlobalAddress is legal. bool isOffsetFoldingLegal(const GlobalAddressSDNode *GA) const override; + BPFTargetLowering::ConstraintType + getConstraintType(StringRef Constraint) const override; + std::pair<unsigned, const TargetRegisterClass *> getRegForInlineAsmConstraint(const TargetRegisterInfo *TRI, StringRef Constraint, MVT VT) const override; diff --git a/llvm/test/CodeGen/BPF/inlineasm-wreg.ll b/llvm/test/CodeGen/BPF/inlineasm-wreg.ll new file mode 100644 index 0000000000000..3c4144e60d51e --- /dev/null +++ b/llvm/test/CodeGen/BPF/inlineasm-wreg.ll @@ -0,0 +1,18 @@ +; RUN: llc < %s -march=bpfel -mattr=+alu32 -verify-machineinstrs | FileCheck %s +; RUN: llc < %s -march=bpfeb -mattr=+alu32 -verify-machineinstrs | FileCheck %s + +; Test that %w works as input constraint +; CHECK-LABEL: test_inlineasm_w_input_constraint +define dso_local i32 @test_inlineasm_w_input_constraint() { + tail call void asm sideeffect "w0 = $0", "w"(i32 42) +; CHECK: w0 = w1 + ret i32 42 +} + +; Test that %w works as output constraint +; CHECK-LABEL: test_inlineasm_w_output_constraint +define dso_local i32 @test_inlineasm_w_output_constraint() { + %1 = tail call i32 asm sideeffect "$0 = $1", "=w,i"(i32 42) +; CHECK: w0 = 42 + ret i32 %1 +} _______________________________________________ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits