[llvm-exegesis] Provide a way to handle memory instructions.
Summary:
And implement memory instructions on X86.
This fixes PR36906.
Reviewers: gchatelet
Reviewed By: gchatelet
Subscribers: lebedev.ri, filcab, mgorny, tschuett, RKSimon, llvm-commits
Differential Revision: https://reviews.llvm.org/D48935
llvm-svn: 338567
diff --git a/llvm/tools/llvm-exegesis/lib/Assembler.cpp b/llvm/tools/llvm-exegesis/lib/Assembler.cpp
index d2be7f4..3b8b1d6 100644
--- a/llvm/tools/llvm-exegesis/lib/Assembler.cpp
+++ b/llvm/tools/llvm-exegesis/lib/Assembler.cpp
@@ -66,12 +66,16 @@
return false;
}
-// Creates a void MachineFunction with no argument.
+// Creates a void(int8*) MachineFunction.
static llvm::MachineFunction &
-createVoidVoidMachineFunction(llvm::StringRef FunctionID, llvm::Module *Module,
- llvm::MachineModuleInfo *MMI) {
+createVoidVoidPtrMachineFunction(llvm::StringRef FunctionID,
+ llvm::Module *Module,
+ llvm::MachineModuleInfo *MMI) {
llvm::Type *const ReturnType = llvm::Type::getInt32Ty(Module->getContext());
- llvm::FunctionType *FunctionType = llvm::FunctionType::get(ReturnType, false);
+ llvm::Type *const MemParamType = llvm::PointerType::get(
+ llvm::Type::getInt8Ty(Module->getContext()), 0 /*default address space*/);
+ llvm::FunctionType *FunctionType =
+ llvm::FunctionType::get(ReturnType, {MemParamType}, false);
llvm::Function *const F = llvm::Function::Create(
FunctionType, llvm::GlobalValue::InternalLinkage, FunctionID, Module);
// Making sure we can create a MachineFunction out of this Function even if it
@@ -81,9 +85,12 @@
}
static void fillMachineFunction(llvm::MachineFunction &MF,
+ llvm::ArrayRef<unsigned> LiveIns,
llvm::ArrayRef<llvm::MCInst> Instructions) {
llvm::MachineBasicBlock *MBB = MF.CreateMachineBasicBlock();
MF.push_back(MBB);
+ for (const unsigned Reg : LiveIns)
+ MBB->addLiveIn(Reg);
const llvm::MCInstrInfo *MCII = MF.getTarget().getMCInstrInfo();
llvm::DebugLoc DL;
for (const llvm::MCInst &Inst : Instructions) {
@@ -134,13 +141,14 @@
std::unique_ptr<llvm::MachineModuleInfo> MMI =
llvm::make_unique<llvm::MachineModuleInfo>(&TM);
llvm::MachineFunction &MF =
- createVoidVoidMachineFunction(FunctionID, Module.get(), MMI.get());
+ createVoidVoidPtrMachineFunction(FunctionID, Module.get(), MMI.get());
// Saving reserved registers for client.
return MF.getSubtarget().getRegisterInfo()->getReservedRegs(MF);
}
void assembleToStream(const ExegesisTarget &ET,
std::unique_ptr<llvm::LLVMTargetMachine> TM,
+ llvm::ArrayRef<unsigned> LiveIns,
llvm::ArrayRef<unsigned> RegsToDef,
llvm::ArrayRef<llvm::MCInst> Instructions,
llvm::raw_pwrite_stream &AsmStream) {
@@ -151,13 +159,17 @@
std::unique_ptr<llvm::MachineModuleInfo> MMI =
llvm::make_unique<llvm::MachineModuleInfo>(TM.get());
llvm::MachineFunction &MF =
- createVoidVoidMachineFunction(FunctionID, Module.get(), MMI.get());
+ createVoidVoidPtrMachineFunction(FunctionID, Module.get(), MMI.get());
// We need to instruct the passes that we're done with SSA and virtual
// registers.
auto &Properties = MF.getProperties();
Properties.set(llvm::MachineFunctionProperties::Property::NoVRegs);
Properties.reset(llvm::MachineFunctionProperties::Property::IsSSA);
+
+ for (const unsigned Reg : LiveIns)
+ MF.getRegInfo().addLiveIn(Reg);
+
bool IsSnippetSetupComplete = false;
std::vector<llvm::MCInst> SnippetWithSetup =
generateSnippetSetupCode(RegsToDef, ET, *TM, IsSnippetSetupComplete);
@@ -176,7 +188,7 @@
MF.getRegInfo().freezeReservedRegs(MF);
// Fill the MachineFunction from the instructions.
- fillMachineFunction(MF, Instructions);
+ fillMachineFunction(MF, LiveIns, Instructions);
// We create the pass manager, run the passes to populate AsmBuffer.
llvm::MCContext &MCContext = MMI->getContext();