core: Add a configuration setting for use_multi_core.
This commit is contained in:
parent
cba69fdcd4
commit
9bf2a428f9
10 changed files with 56 additions and 17 deletions
|
@ -126,6 +126,21 @@ PerfStats::Results System::GetAndResetPerfStats() {
|
|||
return perf_stats.GetAndResetStats(CoreTiming::GetGlobalTimeUs());
|
||||
}
|
||||
|
||||
const std::shared_ptr<Kernel::Scheduler>& System::Scheduler(size_t core_index) {
|
||||
if (!Settings::values.use_multi_core) {
|
||||
// Always use Core 0 scheduler when multicore is disabled
|
||||
return cpu_cores[0]->Scheduler();
|
||||
}
|
||||
|
||||
ASSERT(core_index < NUM_CPU_CORES);
|
||||
return cpu_cores[core_index]->Scheduler();
|
||||
}
|
||||
|
||||
ARM_Interface& System::ArmInterface(size_t core_index) {
|
||||
ASSERT(core_index < NUM_CPU_CORES);
|
||||
return cpu_cores[core_index]->ArmInterface();
|
||||
}
|
||||
|
||||
System::ResultStatus System::Init(EmuWindow* emu_window, u32 system_mode) {
|
||||
NGLOG_DEBUG(HW_Memory, "initialized OK");
|
||||
|
||||
|
@ -154,10 +169,13 @@ System::ResultStatus System::Init(EmuWindow* emu_window, u32 system_mode) {
|
|||
// Create threads for CPU cores 1-3, and build thread_to_cpu map
|
||||
// CPU core 0 is run on the main thread
|
||||
thread_to_cpu[std::this_thread::get_id()] = cpu_cores[0];
|
||||
if (Settings::values.use_multi_core) {
|
||||
for (size_t index = 0; index < cpu_core_threads.size(); ++index) {
|
||||
cpu_core_threads[index] = std::make_unique<std::thread>(RunCpuCore, cpu_cores[index + 1]);
|
||||
cpu_core_threads[index] =
|
||||
std::make_unique<std::thread>(RunCpuCore, cpu_cores[index + 1]);
|
||||
thread_to_cpu[cpu_core_threads[index]->get_id()] = cpu_cores[index + 1];
|
||||
}
|
||||
}
|
||||
|
||||
NGLOG_DEBUG(Core, "Initialized OK");
|
||||
|
||||
|
@ -190,10 +208,12 @@ void System::Shutdown() {
|
|||
|
||||
// Close all CPU/threading state
|
||||
cpu_barrier->NotifyEnd();
|
||||
if (Settings::values.use_multi_core) {
|
||||
for (auto& thread : cpu_core_threads) {
|
||||
thread->join();
|
||||
thread.reset();
|
||||
}
|
||||
}
|
||||
thread_to_cpu.clear();
|
||||
for (auto& cpu_core : cpu_cores) {
|
||||
cpu_core.reset();
|
||||
|
|
|
@ -112,10 +112,7 @@ public:
|
|||
return CurrentCpuCore().ArmInterface();
|
||||
}
|
||||
|
||||
ARM_Interface& ArmInterface(size_t core_index) {
|
||||
ASSERT(core_index < NUM_CPU_CORES);
|
||||
return cpu_cores[core_index]->ArmInterface();
|
||||
}
|
||||
ARM_Interface& ArmInterface(size_t core_index);
|
||||
|
||||
Tegra::GPU& GPU() {
|
||||
return *gpu_core;
|
||||
|
@ -125,10 +122,7 @@ public:
|
|||
return *CurrentCpuCore().Scheduler();
|
||||
}
|
||||
|
||||
const std::shared_ptr<Kernel::Scheduler>& Scheduler(size_t core_index) {
|
||||
ASSERT(core_index < NUM_CPU_CORES);
|
||||
return cpu_cores[core_index]->Scheduler();
|
||||
}
|
||||
const std::shared_ptr<Kernel::Scheduler>& Scheduler(size_t core_index);
|
||||
|
||||
Kernel::SharedPtr<Kernel::Process>& CurrentProcess() {
|
||||
return current_process;
|
||||
|
|
|
@ -26,9 +26,12 @@ void CpuBarrier::NotifyEnd() {
|
|||
}
|
||||
|
||||
bool CpuBarrier::Rendezvous() {
|
||||
if (end) {
|
||||
return false;
|
||||
} else {
|
||||
if (!Settings::values.use_multi_core) {
|
||||
// Meaningless when running in single-core mode
|
||||
return true;
|
||||
}
|
||||
|
||||
if (!end) {
|
||||
std::unique_lock<std::mutex> lock(mutex);
|
||||
|
||||
--cores_waiting;
|
||||
|
@ -41,6 +44,8 @@ bool CpuBarrier::Rendezvous() {
|
|||
condition.wait(lock);
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
Cpu::Cpu(std::shared_ptr<CpuBarrier> cpu_barrier, size_t core_index)
|
||||
|
|
|
@ -121,6 +121,7 @@ struct Values {
|
|||
|
||||
// Core
|
||||
bool use_cpu_jit;
|
||||
bool use_multi_core;
|
||||
|
||||
// Data Storage
|
||||
bool use_virtual_sd;
|
||||
|
|
|
@ -155,6 +155,8 @@ TelemetrySession::TelemetrySession() {
|
|||
|
||||
// Log user configuration information
|
||||
AddField(Telemetry::FieldType::UserConfig, "Core_UseCpuJit", Settings::values.use_cpu_jit);
|
||||
AddField(Telemetry::FieldType::UserConfig, "Core_UseMultiCore",
|
||||
Settings::values.use_multi_core);
|
||||
AddField(Telemetry::FieldType::UserConfig, "Renderer_ResolutionFactor",
|
||||
Settings::values.resolution_factor);
|
||||
AddField(Telemetry::FieldType::UserConfig, "Renderer_ToggleFramelimit",
|
||||
|
|
|
@ -78,6 +78,7 @@ void Config::ReadValues() {
|
|||
|
||||
qt_config->beginGroup("Core");
|
||||
Settings::values.use_cpu_jit = qt_config->value("use_cpu_jit", true).toBool();
|
||||
Settings::values.use_multi_core = qt_config->value("use_multi_core", false).toBool();
|
||||
qt_config->endGroup();
|
||||
|
||||
qt_config->beginGroup("Renderer");
|
||||
|
@ -177,6 +178,7 @@ void Config::SaveValues() {
|
|||
|
||||
qt_config->beginGroup("Core");
|
||||
qt_config->setValue("use_cpu_jit", Settings::values.use_cpu_jit);
|
||||
qt_config->setValue("use_multi_core", Settings::values.use_multi_core);
|
||||
qt_config->endGroup();
|
||||
|
||||
qt_config->beginGroup("Renderer");
|
||||
|
|
|
@ -20,6 +20,7 @@ ConfigureGeneral::ConfigureGeneral(QWidget* parent)
|
|||
this->setConfiguration();
|
||||
|
||||
ui->use_cpu_jit->setEnabled(!Core::System::GetInstance().IsPoweredOn());
|
||||
ui->use_multi_core->setEnabled(!Core::System::GetInstance().IsPoweredOn());
|
||||
ui->use_docked_mode->setEnabled(!Core::System::GetInstance().IsPoweredOn());
|
||||
}
|
||||
|
||||
|
@ -30,6 +31,7 @@ void ConfigureGeneral::setConfiguration() {
|
|||
ui->toggle_check_exit->setChecked(UISettings::values.confirm_before_closing);
|
||||
ui->theme_combobox->setCurrentIndex(ui->theme_combobox->findData(UISettings::values.theme));
|
||||
ui->use_cpu_jit->setChecked(Settings::values.use_cpu_jit);
|
||||
ui->use_multi_core->setChecked(Settings::values.use_multi_core);
|
||||
ui->use_docked_mode->setChecked(Settings::values.use_docked_mode);
|
||||
}
|
||||
|
||||
|
@ -40,6 +42,7 @@ void ConfigureGeneral::applyConfiguration() {
|
|||
ui->theme_combobox->itemData(ui->theme_combobox->currentIndex()).toString();
|
||||
|
||||
Settings::values.use_cpu_jit = ui->use_cpu_jit->isChecked();
|
||||
Settings::values.use_multi_core = ui->use_multi_core->isChecked();
|
||||
Settings::values.use_docked_mode = ui->use_docked_mode->isChecked();
|
||||
Settings::Apply();
|
||||
}
|
||||
|
|
|
@ -58,6 +58,13 @@
|
|||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="QCheckBox" name="use_multi_core">
|
||||
<property name="text">
|
||||
<string>Enable multi-core</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
</layout>
|
||||
</item>
|
||||
</layout>
|
||||
|
|
|
@ -91,6 +91,7 @@ void Config::ReadValues() {
|
|||
|
||||
// Core
|
||||
Settings::values.use_cpu_jit = sdl2_config->GetBoolean("Core", "use_cpu_jit", true);
|
||||
Settings::values.use_multi_core = sdl2_config->GetBoolean("Core", "use_multi_core", false);
|
||||
|
||||
// Renderer
|
||||
Settings::values.resolution_factor =
|
||||
|
|
|
@ -80,6 +80,10 @@ touch_device=
|
|||
# 0: Interpreter (slow), 1 (default): JIT (fast)
|
||||
use_cpu_jit =
|
||||
|
||||
# Whether to use multi-core for CPU emulation
|
||||
# 0 (default): Disabled, 1: Enabled
|
||||
use_multi_core=
|
||||
|
||||
[Renderer]
|
||||
# Whether to use software or hardware rendering.
|
||||
# 0: Software, 1 (default): Hardware
|
||||
|
|
Loading…
Reference in a new issue