forked from OSchip/llvm-project
MIR Serialization: Serialize the list of machine basic blocks with simple attributes.
This commit implements the initial serialization of machine basic blocks in a machine function. Only the simple, scalar MBB attributes are serialized. The reference to LLVM IR's basic block is preserved when that basic block has a name. Reviewers: Duncan P. N. Exon Smith Differential Revision: http://reviews.llvm.org/D10465 llvm-svn: 240145
This commit is contained in:
parent
4d8ffa082c
commit
4f093bf1ce
|
@ -20,6 +20,34 @@
|
|||
|
||||
#include "llvm/ADT/StringRef.h"
|
||||
#include "llvm/Support/YAMLTraits.h"
|
||||
#include <vector>
|
||||
|
||||
namespace llvm {
|
||||
namespace yaml {
|
||||
|
||||
struct MachineBasicBlock {
|
||||
std::string Name;
|
||||
unsigned Alignment = 0;
|
||||
bool IsLandingPad = false;
|
||||
bool AddressTaken = false;
|
||||
// TODO: Serialize the successors and liveins.
|
||||
// TODO: Serialize machine instructions.
|
||||
};
|
||||
|
||||
template <> struct MappingTraits<MachineBasicBlock> {
|
||||
static void mapping(IO &YamlIO, MachineBasicBlock &MBB) {
|
||||
YamlIO.mapOptional("name", MBB.Name,
|
||||
std::string()); // Don't print out an empty name.
|
||||
YamlIO.mapOptional("alignment", MBB.Alignment);
|
||||
YamlIO.mapOptional("isLandingPad", MBB.IsLandingPad);
|
||||
YamlIO.mapOptional("addressTaken", MBB.AddressTaken);
|
||||
}
|
||||
};
|
||||
|
||||
} // end namespace yaml
|
||||
} // end namespace llvm
|
||||
|
||||
LLVM_YAML_IS_SEQUENCE_VECTOR(llvm::yaml::MachineBasicBlock)
|
||||
|
||||
namespace llvm {
|
||||
namespace yaml {
|
||||
|
@ -29,6 +57,8 @@ struct MachineFunction {
|
|||
unsigned Alignment = 0;
|
||||
bool ExposesReturnsTwice = false;
|
||||
bool HasInlineAsm = false;
|
||||
|
||||
std::vector<MachineBasicBlock> BasicBlocks;
|
||||
};
|
||||
|
||||
template <> struct MappingTraits<MachineFunction> {
|
||||
|
@ -37,6 +67,7 @@ template <> struct MappingTraits<MachineFunction> {
|
|||
YamlIO.mapOptional("alignment", MF.Alignment);
|
||||
YamlIO.mapOptional("exposesReturnsTwice", MF.ExposesReturnsTwice);
|
||||
YamlIO.mapOptional("hasInlineAsm", MF.HasInlineAsm);
|
||||
YamlIO.mapOptional("body", MF.BasicBlocks);
|
||||
}
|
||||
};
|
||||
|
||||
|
|
|
@ -19,10 +19,12 @@
|
|||
#include "llvm/AsmParser/Parser.h"
|
||||
#include "llvm/CodeGen/MachineFunction.h"
|
||||
#include "llvm/CodeGen/MIRYamlMapping.h"
|
||||
#include "llvm/IR/BasicBlock.h"
|
||||
#include "llvm/IR/DiagnosticInfo.h"
|
||||
#include "llvm/IR/Instructions.h"
|
||||
#include "llvm/IR/LLVMContext.h"
|
||||
#include "llvm/IR/Module.h"
|
||||
#include "llvm/IR/ValueSymbolTable.h"
|
||||
#include "llvm/Support/LineIterator.h"
|
||||
#include "llvm/Support/SMLoc.h"
|
||||
#include "llvm/Support/SourceMgr.h"
|
||||
|
@ -74,6 +76,12 @@ public:
|
|||
/// Return true if error occurred.
|
||||
bool initializeMachineFunction(MachineFunction &MF);
|
||||
|
||||
/// Initialize the machine basic block using it's YAML representation.
|
||||
///
|
||||
/// Return true if an error occurred.
|
||||
bool initializeMachineBasicBlock(MachineBasicBlock &MBB,
|
||||
const yaml::MachineBasicBlock &YamlMBB);
|
||||
|
||||
private:
|
||||
/// Return a MIR diagnostic converted from an LLVM assembly diagnostic.
|
||||
SMDiagnostic diagFromLLVMAssemblyDiag(const SMDiagnostic &Error,
|
||||
|
@ -198,6 +206,28 @@ bool MIRParserImpl::initializeMachineFunction(MachineFunction &MF) {
|
|||
MF.setAlignment(YamlMF.Alignment);
|
||||
MF.setExposesReturnsTwice(YamlMF.ExposesReturnsTwice);
|
||||
MF.setHasInlineAsm(YamlMF.HasInlineAsm);
|
||||
const auto &F = *MF.getFunction();
|
||||
for (const auto &YamlMBB : YamlMF.BasicBlocks) {
|
||||
const BasicBlock *BB = nullptr;
|
||||
if (!YamlMBB.Name.empty()) {
|
||||
BB = dyn_cast_or_null<BasicBlock>(
|
||||
F.getValueSymbolTable().lookup(YamlMBB.Name));
|
||||
// TODO: Report an error if a basic block isn't found.
|
||||
}
|
||||
auto *MBB = MF.CreateMachineBasicBlock(BB);
|
||||
MF.insert(MF.end(), MBB);
|
||||
if (initializeMachineBasicBlock(*MBB, YamlMBB))
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
bool MIRParserImpl::initializeMachineBasicBlock(
|
||||
MachineBasicBlock &MBB, const yaml::MachineBasicBlock &YamlMBB) {
|
||||
MBB.setAlignment(YamlMBB.Alignment);
|
||||
if (YamlMBB.AddressTaken)
|
||||
MBB.setHasAddressTaken();
|
||||
MBB.setIsLandingPad(YamlMBB.IsLandingPad);
|
||||
return false;
|
||||
}
|
||||
|
||||
|
|
|
@ -16,6 +16,7 @@
|
|||
#include "llvm/ADT/STLExtras.h"
|
||||
#include "llvm/CodeGen/MachineFunction.h"
|
||||
#include "llvm/CodeGen/MIRYamlMapping.h"
|
||||
#include "llvm/IR/BasicBlock.h"
|
||||
#include "llvm/IR/Module.h"
|
||||
#include "llvm/Support/MemoryBuffer.h"
|
||||
#include "llvm/Support/raw_ostream.h"
|
||||
|
@ -34,6 +35,8 @@ public:
|
|||
MIRPrinter(raw_ostream &OS) : OS(OS) {}
|
||||
|
||||
void print(const MachineFunction &MF);
|
||||
|
||||
void convert(yaml::MachineBasicBlock &YamlMBB, const MachineBasicBlock &MBB);
|
||||
};
|
||||
|
||||
} // end anonymous namespace
|
||||
|
@ -61,10 +64,27 @@ void MIRPrinter::print(const MachineFunction &MF) {
|
|||
YamlMF.Alignment = MF.getAlignment();
|
||||
YamlMF.ExposesReturnsTwice = MF.exposesReturnsTwice();
|
||||
YamlMF.HasInlineAsm = MF.hasInlineAsm();
|
||||
for (const auto &MBB : MF) {
|
||||
yaml::MachineBasicBlock YamlMBB;
|
||||
convert(YamlMBB, MBB);
|
||||
YamlMF.BasicBlocks.push_back(YamlMBB);
|
||||
}
|
||||
yaml::Output Out(OS);
|
||||
Out << YamlMF;
|
||||
}
|
||||
|
||||
void MIRPrinter::convert(yaml::MachineBasicBlock &YamlMBB,
|
||||
const MachineBasicBlock &MBB) {
|
||||
// TODO: Serialize unnamed BB references.
|
||||
if (const auto *BB = MBB.getBasicBlock())
|
||||
YamlMBB.Name = BB->hasName() ? BB->getName() : "<unnamed bb>";
|
||||
else
|
||||
YamlMBB.Name = "";
|
||||
YamlMBB.Alignment = MBB.getAlignment();
|
||||
YamlMBB.AddressTaken = MBB.hasAddressTaken();
|
||||
YamlMBB.IsLandingPad = MBB.isLandingPad();
|
||||
}
|
||||
|
||||
void llvm::printMIR(raw_ostream &OS, const Module &M) {
|
||||
yaml::Output Out(OS);
|
||||
Out << const_cast<Module &>(M);
|
||||
|
|
|
@ -0,0 +1,43 @@
|
|||
# RUN: llc -start-after branch-folder -stop-after branch-folder -o /dev/null %s | FileCheck %s
|
||||
# This test ensures that the MIR parser parses machine functions correctly.
|
||||
|
||||
--- |
|
||||
|
||||
define i32 @foo() {
|
||||
entry:
|
||||
ret i32 0
|
||||
}
|
||||
|
||||
define i32 @bar() {
|
||||
start:
|
||||
ret i32 0
|
||||
}
|
||||
|
||||
...
|
||||
---
|
||||
# CHECK: name: foo
|
||||
# CHECK: body:
|
||||
# CHECK-NEXT: - name: entry
|
||||
# CHECK-NEXT: alignment: 0
|
||||
# CHECK-NEXT: isLandingPad: false
|
||||
# CHECK-NEXT: addressTaken: false
|
||||
name: foo
|
||||
body:
|
||||
- name: entry
|
||||
...
|
||||
---
|
||||
# CHECK: name: bar
|
||||
# CHECK: body:
|
||||
# CHECK-NEXT: - name: start
|
||||
# CHECK-NEXT: alignment: 4
|
||||
# CHECK-NEXT: isLandingPad: false
|
||||
# CHECK-NEXT: addressTaken: false
|
||||
# CHECK-NEXT: - alignment: 0
|
||||
# CHECK-NEXT: isLandingPad: false
|
||||
# CHECK-NEXT: addressTaken: true
|
||||
name: bar
|
||||
body:
|
||||
- name: start
|
||||
alignment: 4
|
||||
- addressTaken: true
|
||||
...
|
Loading…
Reference in New Issue