summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--llvm/include/llvm/CodeGen/Register.h77
-rw-r--r--llvm/include/llvm/CodeGen/TargetRegisterInfo.h19
-rw-r--r--llvm/include/llvm/MC/MCRegister.h54
3 files changed, 127 insertions, 23 deletions
diff --git a/llvm/include/llvm/CodeGen/Register.h b/llvm/include/llvm/CodeGen/Register.h
index 907c1a99e56..8c06150f960 100644
--- a/llvm/include/llvm/CodeGen/Register.h
+++ b/llvm/include/llvm/CodeGen/Register.h
@@ -9,6 +9,7 @@
#ifndef LLVM_CODEGEN_REGISTER_H
#define LLVM_CODEGEN_REGISTER_H
+#include "llvm/MC/MCRegister.h"
#include <cassert>
namespace llvm {
@@ -21,29 +22,83 @@ class Register {
public:
Register(unsigned Val = 0): Reg(Val) {}
+ // Register numbers can represent physical registers, virtual registers, and
+ // sometimes stack slots. The unsigned values are divided into these ranges:
+ //
+ // 0 Not a register, can be used as a sentinel.
+ // [1;2^30) Physical registers assigned by TableGen.
+ // [2^30;2^31) Stack slots. (Rarely used.)
+ // [2^31;2^32) Virtual registers assigned by MachineRegisterInfo.
+ //
+ // Further sentinels can be allocated from the small negative integers.
+ // DenseMapInfo<unsigned> uses -1u and -2u.
+
+ /// isStackSlot - Sometimes it is useful the be able to store a non-negative
+ /// frame index in a variable that normally holds a register. isStackSlot()
+ /// returns true if Reg is in the range used for stack slots.
+ ///
+ /// Note that isVirtualRegister() and isPhysicalRegister() cannot handle stack
+ /// slots, so if a variable may contains a stack slot, always check
+ /// isStackSlot() first.
+ ///
+ static bool isStackSlot(unsigned Reg) {
+ return MCRegister::isStackSlot(Reg);
+ }
+
+ /// Compute the frame index from a register value representing a stack slot.
+ static int stackSlot2Index(unsigned Reg) {
+ assert(isStackSlot(Reg) && "Not a stack slot");
+ return int(Reg - (1u << 30));
+ }
+
+ /// Convert a non-negative frame index to a stack slot register value.
+ static unsigned index2StackSlot(int FI) {
+ assert(FI >= 0 && "Cannot hold a negative frame index.");
+ return FI + (1u << 30);
+ }
+
+ /// Return true if the specified register number is in
+ /// the physical register namespace.
+ static bool isPhysicalRegister(unsigned Reg) {
+ return MCRegister::isPhysicalRegister(Reg);
+ }
+
+ /// Return true if the specified register number is in
+ /// the virtual register namespace.
+ static bool isVirtualRegister(unsigned Reg) {
+ assert(!isStackSlot(Reg) && "Not a register! Check isStackSlot() first.");
+ return int(Reg) < 0;
+ }
+
+ /// Convert a virtual register number to a 0-based index.
+ /// The first virtual register in a function will get the index 0.
+ static unsigned virtReg2Index(unsigned Reg) {
+ assert(isVirtualRegister(Reg) && "Not a virtual register");
+ return Reg & ~(1u << 31);
+ }
+
+ /// Convert a 0-based index to a virtual register number.
+ /// This is the inverse operation of VirtReg2IndexFunctor below.
+ static unsigned index2VirtReg(unsigned Index) {
+ return Index | (1u << 31);
+ }
+
/// Return true if the specified register number is in the virtual register
/// namespace.
bool isVirtual() const {
- return int(Reg) < 0;
+ return isVirtualRegister(Reg);
}
/// Return true if the specified register number is in the physical register
/// namespace.
bool isPhysical() const {
- return int(Reg) > 0;
+ return isPhysicalRegister(Reg);
}
/// Convert a virtual register number to a 0-based index. The first virtual
/// register in a function will get the index 0.
unsigned virtRegIndex() const {
- assert(isVirtual() && "Not a virtual register");
- return Reg & ~(1u << 31);
- }
-
- /// Convert a 0-based index to a virtual register number.
- /// This is the inverse operation of VirtReg2IndexFunctor below.
- static Register index2VirtReg(unsigned Index) {
- return Register(Index | (1u << 31));
+ return virtReg2Index(Reg);
}
operator unsigned() const {
@@ -57,4 +112,4 @@ public:
}
-#endif
+#endif // ifndef LLVM_CODEGEN_REGISTER_H
diff --git a/llvm/include/llvm/CodeGen/TargetRegisterInfo.h b/llvm/include/llvm/CodeGen/TargetRegisterInfo.h
index 6843e19c9f6..72a04e6ae1c 100644
--- a/llvm/include/llvm/CodeGen/TargetRegisterInfo.h
+++ b/llvm/include/llvm/CodeGen/TargetRegisterInfo.h
@@ -267,46 +267,41 @@ public:
/// isStackSlot() first.
///
static bool isStackSlot(unsigned Reg) {
- return int(Reg) >= (1 << 30);
+ return Register::isStackSlot(Reg);
}
/// Compute the frame index from a register value representing a stack slot.
static int stackSlot2Index(unsigned Reg) {
- assert(isStackSlot(Reg) && "Not a stack slot");
- return int(Reg - (1u << 30));
+ return Register::stackSlot2Index(Reg);
}
/// Convert a non-negative frame index to a stack slot register value.
static unsigned index2StackSlot(int FI) {
- assert(FI >= 0 && "Cannot hold a negative frame index.");
- return FI + (1u << 30);
+ return Register::index2StackSlot(FI);
}
/// Return true if the specified register number is in
/// the physical register namespace.
static bool isPhysicalRegister(unsigned Reg) {
- assert(!isStackSlot(Reg) && "Not a register! Check isStackSlot() first.");
- return int(Reg) > 0;
+ return Register::isPhysicalRegister(Reg);
}
/// Return true if the specified register number is in
/// the virtual register namespace.
static bool isVirtualRegister(unsigned Reg) {
- assert(!isStackSlot(Reg) && "Not a register! Check isStackSlot() first.");
- return int(Reg) < 0;
+ return Register::isVirtualRegister(Reg);
}
/// Convert a virtual register number to a 0-based index.
/// The first virtual register in a function will get the index 0.
static unsigned virtReg2Index(unsigned Reg) {
- assert(isVirtualRegister(Reg) && "Not a virtual register");
- return Reg & ~(1u << 31);
+ return Register::virtReg2Index(Reg);
}
/// Convert a 0-based index to a virtual register number.
/// This is the inverse operation of VirtReg2IndexFunctor below.
static unsigned index2VirtReg(unsigned Index) {
- return Index | (1u << 31);
+ return Register::index2VirtReg(Index);
}
/// Return the size in bits of a register from class RC.
diff --git a/llvm/include/llvm/MC/MCRegister.h b/llvm/include/llvm/MC/MCRegister.h
new file mode 100644
index 00000000000..57a4f43d431
--- /dev/null
+++ b/llvm/include/llvm/MC/MCRegister.h
@@ -0,0 +1,54 @@
+//===-- llvm/MC/Register.h --------------------------------------*- C++ -*-===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef LLVM_MC_REGISTER_H
+#define LLVM_MC_REGISTER_H
+
+#include <cassert>
+
+namespace llvm {
+
+/// Wrapper class representing physical registers. Should be passed by value.
+/// Note that this class is not fully implemented at this time. A more complete
+/// implementation will follow.
+class MCRegister {
+public:
+ // Register numbers can represent physical registers, virtual registers, and
+ // sometimes stack slots. The unsigned values are divided into these ranges:
+ //
+ // 0 Not a register, can be used as a sentinel.
+ // [1;2^30) Physical registers assigned by TableGen.
+ // [2^30;2^31) Stack slots. (Rarely used.)
+ // [2^31;2^32) Virtual registers assigned by MachineRegisterInfo.
+ //
+ // Further sentinels can be allocated from the small negative integers.
+ // DenseMapInfo<unsigned> uses -1u and -2u.
+
+ /// This is the portion of the positive number space that is not a physical
+ /// register. StackSlot values do not exist in the MC layer, see
+ /// Register::isStackSlot() for the more information on them.
+ ///
+ /// Note that isVirtualRegister() and isPhysicalRegister() cannot handle stack
+ /// slots, so if a variable may contains a stack slot, always check
+ /// isStackSlot() first.
+ static bool isStackSlot(unsigned Reg) {
+ return int(Reg) >= (1 << 30);
+ }
+
+ /// Return true if the specified register number is in
+ /// the physical register namespace.
+ static bool isPhysicalRegister(unsigned Reg) {
+ assert(!isStackSlot(Reg) && "Not a register! Check isStackSlot() first.");
+ return int(Reg) > 0;
+ }
+};
+
+}
+
+#endif // ifndef LLVM_MC_REGISTER_H
+
OpenPOWER on IntegriCloud