mirror of
https://github.com/citra-emu/citra.git
synced 2024-11-24 11:41:04 +00:00
Module generation stubs
This commit is contained in:
parent
5c27161b23
commit
6c7551d5f3
@ -1,9 +1,11 @@
|
||||
set(SRCS
|
||||
main.cpp
|
||||
CodeGen.cpp
|
||||
ModuleGen.cpp
|
||||
)
|
||||
set(HEADERS
|
||||
CodeGen.h
|
||||
ModuleGen.h
|
||||
)
|
||||
|
||||
create_directory_groups(${SRCS} ${HEADERS})
|
||||
|
@ -1,5 +1,8 @@
|
||||
#include "CodeGen.h"
|
||||
#include "ModuleGen.h"
|
||||
|
||||
#include "core/loader/loader.h"
|
||||
|
||||
#include <llvm/Support/TargetSelect.h>
|
||||
#include <llvm/Support/Host.h>
|
||||
#include <llvm/Target/TargetSubtargetInfo.h>
|
||||
@ -61,12 +64,12 @@ void CodeGen::IntializeLLVM()
|
||||
|
||||
module = make_unique<Module>("Module", getGlobalContext());
|
||||
module->setTargetTriple(triple_string);
|
||||
ir_builder = make_unique<IRBuilder<>>(getGlobalContext());
|
||||
}
|
||||
|
||||
void CodeGen::GenerateModule()
|
||||
{
|
||||
// TODO:
|
||||
moduleGenerator = std::make_unique<ModuleGen>(module.get());
|
||||
moduleGenerator->Run();
|
||||
}
|
||||
|
||||
void CodeGen::GenerateDebugFiles()
|
||||
@ -83,6 +86,7 @@ void CodeGen::GenerateDebugFiles()
|
||||
raw_os_ostream stream(file);
|
||||
|
||||
module->print(stream, nullptr);
|
||||
stream.flush();
|
||||
file.close();
|
||||
LOG_INFO(BinaryTranslator, "Done");
|
||||
}
|
||||
@ -108,9 +112,14 @@ void CodeGen::OptimizeAndGenerate()
|
||||
PassManagerBuilder pass_manager_builder;
|
||||
|
||||
FunctionPassManager function_pass_manager(module.get());
|
||||
PassManager pass_manager;
|
||||
|
||||
module->setDataLayout(target_machine->getSubtargetImpl()->getDataLayout());
|
||||
|
||||
pass_manager.add(createVerifierPass());
|
||||
pass_manager.add(new TargetLibraryInfo(*triple));
|
||||
pass_manager.add(new DataLayoutPass());
|
||||
target_machine->addAnalysisPasses(pass_manager);
|
||||
function_pass_manager.add(new DataLayoutPass());
|
||||
target_machine->addAnalysisPasses(function_pass_manager);
|
||||
|
||||
@ -121,6 +130,7 @@ void CodeGen::OptimizeAndGenerate()
|
||||
pass_manager_builder.SLPVectorize = true;
|
||||
|
||||
pass_manager_builder.populateFunctionPassManager(function_pass_manager);
|
||||
pass_manager_builder.populateModulePassManager(pass_manager);
|
||||
|
||||
LOG_INFO(BinaryTranslator, "Optimizing functions");
|
||||
function_pass_manager.doInitialization();
|
||||
@ -129,18 +139,7 @@ void CodeGen::OptimizeAndGenerate()
|
||||
function_pass_manager.doFinalization();
|
||||
LOG_INFO(BinaryTranslator, "Done");
|
||||
|
||||
PassManager pass_manager;
|
||||
|
||||
pass_manager.add(createVerifierPass());
|
||||
pass_manager.add(new TargetLibraryInfo(*triple));
|
||||
pass_manager.add(new DataLayoutPass());
|
||||
target_machine->addAnalysisPasses(pass_manager);
|
||||
pass_manager_builder.populateModulePassManager(pass_manager);
|
||||
pass_manager.add(createVerifierPass());
|
||||
|
||||
LOG_INFO(BinaryTranslator, "Optimizing module");
|
||||
pass_manager.run(*module);
|
||||
LOG_INFO(BinaryTranslator, "Done");
|
||||
|
||||
MCContext *context;
|
||||
std::ofstream file(output_object_filename, std::ios::binary);
|
||||
@ -157,6 +156,7 @@ void CodeGen::OptimizeAndGenerate()
|
||||
}
|
||||
LOG_INFO(BinaryTranslator, "Generating code");
|
||||
pass_manager.run(*module);
|
||||
stream.flush();
|
||||
file.close();
|
||||
LOG_INFO(BinaryTranslator, "Done");
|
||||
}
|
@ -7,6 +7,8 @@ namespace llvm
|
||||
class Module;
|
||||
}
|
||||
|
||||
class ModuleGen;
|
||||
|
||||
/*
|
||||
* Holds alls the basic llvm structures
|
||||
*/
|
||||
@ -26,8 +28,9 @@ private:
|
||||
const char *output_object_filename;
|
||||
const char *output_debug_filename;
|
||||
|
||||
std::unique_ptr<ModuleGen> moduleGenerator;
|
||||
|
||||
std::unique_ptr<llvm::Triple> triple;
|
||||
std::unique_ptr<llvm::TargetMachine> target_machine;
|
||||
std::unique_ptr<llvm::Module> module;
|
||||
std::unique_ptr<llvm::IRBuilder<>> ir_builder;
|
||||
};
|
52
src/binary_translation/ModuleGen.cpp
Normal file
52
src/binary_translation/ModuleGen.cpp
Normal file
@ -0,0 +1,52 @@
|
||||
#include "ModuleGen.h"
|
||||
#include <llvm/IR/Function.h>
|
||||
#include <llvm/IR/GlobalVariable.h>
|
||||
|
||||
using namespace llvm;
|
||||
|
||||
ModuleGen::ModuleGen(llvm::Module* module)
|
||||
: module(module)
|
||||
{
|
||||
ir_builder = make_unique<IRBuilder<>>(getGlobalContext());
|
||||
}
|
||||
|
||||
ModuleGen::~ModuleGen()
|
||||
{
|
||||
}
|
||||
|
||||
void ModuleGen::Run()
|
||||
{
|
||||
GenerateGlobals();
|
||||
GenerateCanRunFunction();
|
||||
GenerateRunFunction();
|
||||
}
|
||||
|
||||
void ModuleGen::GenerateGlobals()
|
||||
{
|
||||
auto registers_global_initializer = ConstantPointerNull::get(IntegerType::getInt32PtrTy(getGlobalContext()));
|
||||
registers_global = new GlobalVariable(*module, registers_global_initializer->getType(), false, GlobalValue::ExternalLinkage, registers_global_initializer, "Registers");
|
||||
|
||||
// Flags is stored internally as i1* indexed in multiples of 4
|
||||
auto flags_global_initializer = ConstantPointerNull::get(IntegerType::getInt1PtrTy(getGlobalContext()));
|
||||
flags_global = new GlobalVariable(*module, flags_global_initializer->getType(), false, GlobalValue::ExternalLinkage, flags_global_initializer, "Flags");
|
||||
}
|
||||
|
||||
void ModuleGen::GenerateCanRunFunction()
|
||||
{
|
||||
auto can_run_function_type = FunctionType::get(ir_builder->getInt1Ty(), false);
|
||||
can_run_function = Function::Create(can_run_function_type, GlobalValue::ExternalLinkage, "CanRun", module);
|
||||
auto basic_block = BasicBlock::Create(getGlobalContext(), "Entry", can_run_function);
|
||||
|
||||
ir_builder->SetInsertPoint(basic_block);
|
||||
ir_builder->CreateRet(ir_builder->getInt1(false));
|
||||
}
|
||||
|
||||
void ModuleGen::GenerateRunFunction()
|
||||
{
|
||||
auto run_function_type = FunctionType::get(ir_builder->getVoidTy(), false);
|
||||
run_function = Function::Create(run_function_type, GlobalValue::ExternalLinkage, "Run", module);
|
||||
auto basic_block = BasicBlock::Create(getGlobalContext(), "Entry", run_function);
|
||||
|
||||
ir_builder->SetInsertPoint(basic_block);
|
||||
ir_builder->CreateRetVoid();
|
||||
}
|
43
src/binary_translation/ModuleGen.h
Normal file
43
src/binary_translation/ModuleGen.h
Normal file
@ -0,0 +1,43 @@
|
||||
#include <llvm/IR/IRBuilder.h>
|
||||
|
||||
namespace llvm
|
||||
{
|
||||
class Module;
|
||||
}
|
||||
|
||||
class ModuleGen
|
||||
{
|
||||
public:
|
||||
explicit ModuleGen(llvm::Module *module);
|
||||
~ModuleGen();
|
||||
|
||||
void Run();
|
||||
void GenerateGlobals();
|
||||
void GenerateCanRunFunction();
|
||||
void GenerateRunFunction();
|
||||
private:
|
||||
std::unique_ptr<llvm::IRBuilder<>> ir_builder;
|
||||
llvm::Module *module;
|
||||
|
||||
/*
|
||||
* u32 *Registers;
|
||||
* The registers of the cpu
|
||||
*/
|
||||
llvm::GlobalVariable *registers_global;
|
||||
/*
|
||||
* u32 *Flags;
|
||||
* The flags of the cpu
|
||||
* Orderered N, Z, C, V
|
||||
*/
|
||||
llvm::GlobalVariable *flags_global;
|
||||
/*
|
||||
* bool CanRun()
|
||||
* Returns whether there is a binary translation available for a PC
|
||||
*/
|
||||
llvm::Function *can_run_function;
|
||||
/*
|
||||
* void Run()
|
||||
* Runs binary translated opcodes
|
||||
*/
|
||||
llvm::Function *run_function;
|
||||
};
|
Loading…
Reference in New Issue
Block a user