summaryrefslogtreecommitdiff
path: root/lib/Target/ARM/ARMConstantIslandPass.cpp
diff options
context:
space:
mode:
authorJakob Stoklund Olesen <stoklund@2pi.dk>2011-12-07 04:17:35 +0000
committerJakob Stoklund Olesen <stoklund@2pi.dk>2011-12-07 04:17:35 +0000
commita26811ec83d00344a739d84f4b8584e5548b94ce (patch)
tree1d6ebf6655ed04f2b6c95ce76b5b1e78c90df5be /lib/Target/ARM/ARMConstantIslandPass.cpp
parent1c663fee566546fc5622ffb4f169438bbd495fbf (diff)
downloadllvm-a26811ec83d00344a739d84f4b8584e5548b94ce.tar.gz
llvm-a26811ec83d00344a739d84f4b8584e5548b94ce.tar.bz2
llvm-a26811ec83d00344a739d84f4b8584e5548b94ce.tar.xz
Compute some alignment information for each basic block.
These fields are not used for anything yet. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@146017 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'lib/Target/ARM/ARMConstantIslandPass.cpp')
-rw-r--r--lib/Target/ARM/ARMConstantIslandPass.cpp62
1 files changed, 48 insertions, 14 deletions
diff --git a/lib/Target/ARM/ARMConstantIslandPass.cpp b/lib/Target/ARM/ARMConstantIslandPass.cpp
index b9d7b31ed2..443c4b9d5d 100644
--- a/lib/Target/ARM/ARMConstantIslandPass.cpp
+++ b/lib/Target/ARM/ARMConstantIslandPass.cpp
@@ -82,8 +82,17 @@ namespace {
/// will both be ==2 mod 4).
unsigned Size;
- BasicBlockInfo() : Offset(0), Size(0) {}
- BasicBlockInfo(unsigned o, unsigned s) : Offset(o), Size(s) {}
+ /// Unalign - When non-zero, the block contains instructions (inline asm)
+ /// of unknown size. The real size may be smaller than Size bytes by a
+ /// multiple of 1 << Unalign.
+ uint8_t Unalign;
+
+ /// PostAlign - When non-zero, the block terminator contains a .align
+ /// directive, so the end of the block is aligned to 1 << PostAlign
+ /// bytes.
+ uint8_t PostAlign;
+
+ BasicBlockInfo() : Offset(0), Size(0), Unalign(0), PostAlign(0) {}
/// Compute the offset immediately following this block.
unsigned postOffset() const { return Offset + Size; }
@@ -234,6 +243,7 @@ namespace {
MachineBasicBlock *AdjustJTTargetBlockForward(MachineBasicBlock *BB,
MachineBasicBlock *JTBB);
+ void ComputeBlockSize(const MachineBasicBlock *MBB);
unsigned GetOffsetOf(MachineInstr *MI) const;
void dumpBBs();
void verify(MachineFunction &MF);
@@ -507,11 +517,16 @@ void ARMConstantIslands::InitialFunctionScan(MachineFunction &MF,
HasInlineAsm = true;
}
+ BBInfo.clear();
+ BBInfo.resize(MF.getNumBlockIDs());
+
// Now go back through the instructions and build up our data structures.
unsigned Offset = 0;
for (MachineFunction::iterator MBBI = MF.begin(), E = MF.end();
MBBI != E; ++MBBI) {
MachineBasicBlock &MBB = *MBBI;
+ BasicBlockInfo &BBI = BBInfo[MBB.getNumber()];
+ BBI.Offset = Offset;
// If this block doesn't fall through into the next MBB, then this is
// 'water' that a constant pool island could be placed.
@@ -526,6 +541,11 @@ void ARMConstantIslands::InitialFunctionScan(MachineFunction &MF,
// Add instruction size to MBBSize.
MBBSize += TII->GetInstSizeInBytes(I);
+ // For inline asm, GetInstSizeInBytes returns a conservative estimate.
+ // The actual size may be smaller, but still a multiple of the instr size.
+ if (I->isInlineAsm())
+ BBI.Unalign = isThumb ? 1 : 2;
+
int Opc = I->getOpcode();
if (I->getDesc().isBranch()) {
bool isCond = false;
@@ -543,6 +563,7 @@ void ARMConstantIslands::InitialFunctionScan(MachineFunction &MF,
// is aligned. That is held in Offset+MBBSize, which already has
// 2 added in for the size of the mov pc instruction.
MF.EnsureAlignment(2U);
+ BBI.PostAlign = 2;
if ((Offset+MBBSize)%4 != 0 || HasInlineAsm)
// FIXME: Add a pseudo ALIGN instruction instead.
MBBSize += 2; // padding
@@ -673,11 +694,33 @@ void ARMConstantIslands::InitialFunctionScan(MachineFunction &MF,
((Offset%4) != 0 || HasInlineAsm))
MBBSize += 2;
- BBInfo.push_back(BasicBlockInfo(Offset, MBBSize));
+ BBI.Size = MBBSize;
Offset += MBBSize;
}
}
+/// ComputeBlockSize - Compute the size and some alignment information for MBB.
+/// This function updates BBInfo directly.
+void ARMConstantIslands::ComputeBlockSize(const MachineBasicBlock *MBB) {
+ BasicBlockInfo &BBI = BBInfo[MBB->getNumber()];
+ BBI.Size = 0;
+ BBI.Unalign = 0;
+ BBI.PostAlign = 0;
+
+ for (MachineBasicBlock::const_iterator I = MBB->begin(), E = MBB->end();
+ I != E; ++I) {
+ BBI.Size += TII->GetInstSizeInBytes(I);
+ // For inline asm, GetInstSizeInBytes returns a conservative estimate.
+ // The actual size may be smaller, but still a multiple of the instr size.
+ if (I->isInlineAsm())
+ BBI.Unalign = isThumb ? 1 : 2;
+ }
+
+ // tBR_JTr contains a .align 2 directive.
+ if (!MBB->empty() && MBB->back().getOpcode() == ARM::tBR_JTr)
+ BBI.PostAlign = 2;
+}
+
/// GetOffsetOf - Return the current offset of the specified machine instruction
/// from the start of the function. This offset changes as stuff is moved
/// around inside the function.
@@ -798,23 +841,14 @@ MachineBasicBlock *ARMConstantIslands::SplitBlockBeforeInstr(MachineInstr *MI) {
// the new jump we added. (It should be possible to do this without
// recounting everything, but it's very confusing, and this is rarely
// executed.)
- unsigned OrigBBSize = 0;
- for (MachineBasicBlock::iterator I = OrigBB->begin(), E = OrigBB->end();
- I != E; ++I)
- OrigBBSize += TII->GetInstSizeInBytes(I);
- BBInfo[OrigBBI].Size = OrigBBSize;
+ ComputeBlockSize(OrigBB);
// ...and adjust BBOffsets for NewBB accordingly.
BBInfo[NewBBI].Offset = BBInfo[OrigBBI].postOffset();
// Figure out how large the NewMBB is. As the second half of the original
// block, it may contain a tablejump.
- unsigned NewBBSize = 0;
- for (MachineBasicBlock::iterator I = NewBB->begin(), E = NewBB->end();
- I != E; ++I)
- NewBBSize += TII->GetInstSizeInBytes(I);
- // Set the size of NewBB in BBSizes. It does not include any padding now.
- BBInfo[NewBBI].Size = NewBBSize;
+ ComputeBlockSize(NewBB);
MachineInstr* ThumbJTMI = prior(NewBB->end());
if (ThumbJTMI->getOpcode() == ARM::tBR_JTr) {