Locking around some JIT stuff.

Excessive for now, but safer.
This commit is contained in:
Ben Vanik 2013-10-16 21:32:20 -07:00
parent 8e37fb8502
commit c53db98517
4 changed files with 18 additions and 1 deletions

View File

@ -50,6 +50,7 @@ Processor::Processor(xe_memory_ref memory, shared_ptr<Backend> backend) :
interrupt_thread_lock_(NULL), interrupt_thread_state_(NULL) {
memory_ = xe_memory_retain(memory);
backend_ = backend;
sym_lock_ = xe_mutex_alloc(10000);
InitializeIfNeeded();
}
@ -71,6 +72,7 @@ Processor::~Processor() {
delete jit_;
delete sym_table_;
xe_mutex_free(sym_lock_);
graphics_system_.reset();
export_resolver_.reset();
@ -158,7 +160,9 @@ int Processor::LoadRawBinary(const xechar_t* path, uint32_t start_address) {
// Initialize the module and prepare it for execution.
XEEXPECTZERO(jit_->InitModule(exec_module));
xe_mutex_lock(sym_lock_);
modules_.push_back(exec_module);
xe_mutex_unlock(sym_lock_);
result_code = 0;
XECLEANUP:
@ -183,7 +187,9 @@ int Processor::LoadXexModule(const char* name, const char* path,
// Initialize the module and prepare it for execution.
XEEXPECTZERO(jit_->InitModule(exec_module));
xe_mutex_lock(sym_lock_);
modules_.push_back(exec_module);
xe_mutex_unlock(sym_lock_);
result_code = 0;
XECLEANUP:
@ -264,6 +270,7 @@ uint64_t Processor::ExecuteInterrupt(uint32_t address,
FunctionSymbol* Processor::GetFunction(uint32_t address) {
// Attempt to grab the function symbol from the global lookup table.
// The symbol table takes a lock so it should be safe.
FunctionSymbol* fn_symbol = sym_table_->GetFunction(address);
if (fn_symbol) {
return fn_symbol;
@ -274,13 +281,16 @@ FunctionSymbol* Processor::GetFunction(uint32_t address) {
// symbol is not found (likely) it will do analysis on it.
// TODO(benvanik): make this more efficient. Could use a binary search or
// something more clever.
xe_mutex_lock(sym_lock_);
for (std::vector<ExecModule*>::iterator it = modules_.begin();
it != modules_.end(); ++it) {
fn_symbol = (*it)->FindFunctionSymbol(address);
if (fn_symbol) {
xe_mutex_unlock(sym_lock_);
return fn_symbol;
}
}
xe_mutex_unlock(sym_lock_);
// Not found at all? That seems wrong...
XEASSERTALWAYS();

View File

@ -76,6 +76,7 @@ private:
sdb::SymbolTable* sym_table_;
JIT* jit_;
std::vector<ExecModule*> modules_;
xe_mutex_t* sym_lock_;
xe_mutex_t* interrupt_thread_lock_;
ThreadState* interrupt_thread_state_;

View File

@ -27,10 +27,12 @@ using namespace AsmJit;
X64JIT::X64JIT(xe_memory_ref memory, SymbolTable* sym_table) :
JIT(memory, sym_table),
emitter_(NULL) {
jit_lock_ = xe_mutex_alloc(10000);
}
X64JIT::~X64JIT() {
delete emitter_;
xe_mutex_free(jit_lock_);
}
int X64JIT::Setup() {
@ -160,17 +162,20 @@ int X64JIT::UninitModule(ExecModule* module) {
void* X64JIT::GetFunctionPointer(sdb::FunctionSymbol* fn_symbol) {
// Check function.
// TODO(benvanik): make this lock-free (or spin).
xe_mutex_lock(jit_lock_);
x64_function_t fn_ptr = (x64_function_t)fn_symbol->impl_value;
if (!fn_ptr) {
// Function hasn't been prepped yet - make it now inline.
// The emitter will lock and do other fancy things, if required.
if (emitter_->PrepareFunction(fn_symbol)) {
xe_mutex_unlock(jit_lock_);
return NULL;
}
fn_ptr = (x64_function_t)fn_symbol->impl_value;
XEASSERTNOTNULL(fn_ptr);
}
xe_mutex_unlock(jit_lock_);
return fn_ptr;
}

View File

@ -43,6 +43,7 @@ protected:
int CheckProcessor();
void DumpCPUInfo();
xe_mutex_t* jit_lock_;
X64Emitter* emitter_;
};