Target.cpp 2.3 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576
  1. //===-- Target.cpp ----------------------------------------------*- C++ -*-===//
  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. #include "../Target.h"
  9. #include "AArch64.h"
  10. #include "AArch64RegisterInfo.h"
  11. namespace llvm {
  12. namespace exegesis {
  13. static unsigned getLoadImmediateOpcode(unsigned RegBitWidth) {
  14. switch (RegBitWidth) {
  15. case 32:
  16. return AArch64::MOVi32imm;
  17. case 64:
  18. return AArch64::MOVi64imm;
  19. }
  20. llvm_unreachable("Invalid Value Width");
  21. }
  22. // Generates instruction to load an immediate value into a register.
  23. static MCInst loadImmediate(unsigned Reg, unsigned RegBitWidth,
  24. const APInt &Value) {
  25. if (Value.getBitWidth() > RegBitWidth)
  26. llvm_unreachable("Value must fit in the Register");
  27. return MCInstBuilder(getLoadImmediateOpcode(RegBitWidth))
  28. .addReg(Reg)
  29. .addImm(Value.getZExtValue());
  30. }
  31. #include "AArch64GenExegesis.inc"
  32. namespace {
  33. class ExegesisAArch64Target : public ExegesisTarget {
  34. public:
  35. ExegesisAArch64Target() : ExegesisTarget(AArch64CpuPfmCounters) {}
  36. private:
  37. std::vector<MCInst> setRegTo(const MCSubtargetInfo &STI, unsigned Reg,
  38. const APInt &Value) const override {
  39. if (AArch64::GPR32RegClass.contains(Reg))
  40. return {loadImmediate(Reg, 32, Value)};
  41. if (AArch64::GPR64RegClass.contains(Reg))
  42. return {loadImmediate(Reg, 64, Value)};
  43. errs() << "setRegTo is not implemented, results will be unreliable\n";
  44. return {};
  45. }
  46. bool matchesArch(Triple::ArchType Arch) const override {
  47. return Arch == Triple::aarch64 || Arch == Triple::aarch64_be;
  48. }
  49. void addTargetSpecificPasses(PassManagerBase &PM) const override {
  50. // Function return is a pseudo-instruction that needs to be expanded
  51. PM.add(createAArch64ExpandPseudoPass());
  52. }
  53. };
  54. } // namespace
  55. static ExegesisTarget *getTheExegesisAArch64Target() {
  56. static ExegesisAArch64Target Target;
  57. return &Target;
  58. }
  59. void InitializeAArch64ExegesisTarget() {
  60. ExegesisTarget::registerTarget(getTheExegesisAArch64Target());
  61. }
  62. } // namespace exegesis
  63. } // namespace llvm