pineapple-src/src/core/cpu_manager.h

109 lines
2.6 KiB
C
Raw Normal View History

2022-04-23 20:49:07 +02:00
// SPDX-FileCopyrightText: Copyright 2018 yuzu Emulator Project
// SPDX-License-Identifier: GPL-2.0-or-later
2020-12-28 16:15:37 +01:00
#pragma once
#include <array>
#include <atomic>
#include <functional>
#include <memory>
#include <thread>
#include "common/fiber.h"
#include "common/thread.h"
#include "core/hardware_properties.h"
namespace Common {
class Event;
class Fiber;
} // namespace Common
namespace Core {
class System;
class CpuManager {
public:
2021-05-16 11:38:19 +02:00
explicit CpuManager(System& system_);
2020-12-28 16:15:37 +01:00
CpuManager(const CpuManager&) = delete;
CpuManager(CpuManager&&) = delete;
~CpuManager();
CpuManager& operator=(const CpuManager&) = delete;
CpuManager& operator=(CpuManager&&) = delete;
/// Sets if emulation is multicore or single core, must be set before Initialize
2021-05-05 10:10:21 +02:00
void SetMulticore(bool is_multi) {
is_multicore = is_multi;
2020-12-28 16:15:37 +01:00
}
/// Sets if emulation is using an asynchronous GPU.
2021-05-05 10:10:21 +02:00
void SetAsyncGpu(bool is_async) {
is_async_gpu = is_async;
2020-12-28 16:15:37 +01:00
}
2022-06-17 10:13:07 +02:00
void OnGpuReady() {
gpu_barrier->Sync();
}
2020-12-28 16:15:37 +01:00
void Initialize();
void Shutdown();
2022-07-11 17:46:58 +02:00
std::function<void()> GetGuestActivateFunc() {
return [this] { GuestActivate(); };
}
std::function<void()> GetGuestThreadFunc() {
2022-07-03 10:24:53 +02:00
return [this] { GuestThreadFunction(); };
}
std::function<void()> GetIdleThreadStartFunc() {
return [this] { IdleThreadFunction(); };
}
2022-07-10 14:59:48 +02:00
std::function<void()> GetShutdownThreadStartFunc() {
return [this] { ShutdownThreadFunction(); };
2022-07-03 10:24:53 +02:00
}
2020-12-28 16:15:37 +01:00
void PreemptSingleCore(bool from_running_enviroment = true);
std::size_t CurrentCore() const {
return current_core.load();
}
private:
2022-07-03 10:24:53 +02:00
void GuestThreadFunction();
void IdleThreadFunction();
2022-07-10 14:59:48 +02:00
void ShutdownThreadFunction();
2020-12-28 16:15:37 +01:00
void MultiCoreRunGuestThread();
void MultiCoreRunIdleThread();
void SingleCoreRunGuestThread();
void SingleCoreRunIdleThread();
2021-09-04 02:08:38 +02:00
static void ThreadStart(std::stop_token stop_token, CpuManager& cpu_manager, std::size_t core);
2020-12-28 16:15:37 +01:00
2022-07-11 17:46:58 +02:00
void GuestActivate();
void HandleInterrupt();
2022-07-10 14:59:48 +02:00
void ShutdownThread();
2022-06-14 03:25:44 +02:00
void RunThread(std::size_t core);
2020-12-28 16:15:37 +01:00
struct CoreData {
2021-03-06 02:58:44 +01:00
std::shared_ptr<Common::Fiber> host_context;
2021-09-04 02:08:38 +02:00
std::jthread host_thread;
2020-12-28 16:15:37 +01:00
};
2022-06-17 10:13:07 +02:00
std::unique_ptr<Common::Barrier> gpu_barrier{};
2020-12-28 16:15:37 +01:00
std::array<CoreData, Core::Hardware::NUM_CPU_CORES> core_data{};
bool is_async_gpu{};
bool is_multicore{};
std::atomic<std::size_t> current_core{};
std::size_t idle_count{};
2022-06-14 03:25:44 +02:00
std::size_t num_cores{};
2020-12-28 16:15:37 +01:00
static constexpr std::size_t max_cycle_runs = 5;
System& system;
};
} // namespace Core