Merge pull request #9398 from liamwhite/fail
general: improve handling of system startup failure
This commit is contained in:
		@@ -389,7 +389,9 @@ struct System::Impl {
 | 
			
		||||
        kernel.ShutdownCores();
 | 
			
		||||
        cpu_manager.Shutdown();
 | 
			
		||||
        debugger.reset();
 | 
			
		||||
        services->KillNVNFlinger();
 | 
			
		||||
        if (services) {
 | 
			
		||||
            services->KillNVNFlinger();
 | 
			
		||||
        }
 | 
			
		||||
        kernel.CloseServices();
 | 
			
		||||
        services.reset();
 | 
			
		||||
        service_manager.reset();
 | 
			
		||||
 
 | 
			
		||||
@@ -20,23 +20,20 @@ namespace Core {
 | 
			
		||||
CpuManager::CpuManager(System& system_) : system{system_} {}
 | 
			
		||||
CpuManager::~CpuManager() = default;
 | 
			
		||||
 | 
			
		||||
void CpuManager::ThreadStart(std::stop_token stop_token, CpuManager& cpu_manager,
 | 
			
		||||
                             std::size_t core) {
 | 
			
		||||
    cpu_manager.RunThread(core);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void CpuManager::Initialize() {
 | 
			
		||||
    num_cores = is_multicore ? Core::Hardware::NUM_CPU_CORES : 1;
 | 
			
		||||
    gpu_barrier = std::make_unique<Common::Barrier>(num_cores + 1);
 | 
			
		||||
 | 
			
		||||
    for (std::size_t core = 0; core < num_cores; core++) {
 | 
			
		||||
        core_data[core].host_thread = std::jthread(ThreadStart, std::ref(*this), core);
 | 
			
		||||
        core_data[core].host_thread =
 | 
			
		||||
            std::jthread([this, core](std::stop_token token) { RunThread(token, core); });
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void CpuManager::Shutdown() {
 | 
			
		||||
    for (std::size_t core = 0; core < num_cores; core++) {
 | 
			
		||||
        if (core_data[core].host_thread.joinable()) {
 | 
			
		||||
            core_data[core].host_thread.request_stop();
 | 
			
		||||
            core_data[core].host_thread.join();
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
@@ -184,7 +181,7 @@ void CpuManager::ShutdownThread() {
 | 
			
		||||
    UNREACHABLE();
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void CpuManager::RunThread(std::size_t core) {
 | 
			
		||||
void CpuManager::RunThread(std::stop_token token, std::size_t core) {
 | 
			
		||||
    /// Initialization
 | 
			
		||||
    system.RegisterCoreThread(core);
 | 
			
		||||
    std::string name;
 | 
			
		||||
@@ -206,7 +203,9 @@ void CpuManager::RunThread(std::size_t core) {
 | 
			
		||||
    });
 | 
			
		||||
 | 
			
		||||
    // Running
 | 
			
		||||
    gpu_barrier->Sync();
 | 
			
		||||
    if (!gpu_barrier->Sync(token)) {
 | 
			
		||||
        return;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    if (!is_async_gpu && !is_multicore) {
 | 
			
		||||
        system.GPU().ObtainContext();
 | 
			
		||||
 
 | 
			
		||||
@@ -81,12 +81,10 @@ private:
 | 
			
		||||
    void SingleCoreRunGuestThread();
 | 
			
		||||
    void SingleCoreRunIdleThread();
 | 
			
		||||
 | 
			
		||||
    static void ThreadStart(std::stop_token stop_token, CpuManager& cpu_manager, std::size_t core);
 | 
			
		||||
 | 
			
		||||
    void GuestActivate();
 | 
			
		||||
    void HandleInterrupt();
 | 
			
		||||
    void ShutdownThread();
 | 
			
		||||
    void RunThread(std::size_t core);
 | 
			
		||||
    void RunThread(std::stop_token stop_token, std::size_t core);
 | 
			
		||||
 | 
			
		||||
    struct CoreData {
 | 
			
		||||
        std::shared_ptr<Common::Fiber> host_context;
 | 
			
		||||
 
 | 
			
		||||
@@ -104,12 +104,16 @@ struct KernelCore::Impl {
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    void CloseCurrentProcess() {
 | 
			
		||||
        (*current_process).Finalize();
 | 
			
		||||
        // current_process->Close();
 | 
			
		||||
        // TODO: The current process should be destroyed based on accurate ref counting after
 | 
			
		||||
        KProcess* old_process = current_process.exchange(nullptr);
 | 
			
		||||
        if (old_process == nullptr) {
 | 
			
		||||
            return;
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        // old_process->Close();
 | 
			
		||||
        // TODO: The process should be destroyed based on accurate ref counting after
 | 
			
		||||
        // calling Close(). Adding a manual Destroy() call instead to avoid a memory leak.
 | 
			
		||||
        (*current_process).Destroy();
 | 
			
		||||
        current_process = nullptr;
 | 
			
		||||
        old_process->Finalize();
 | 
			
		||||
        old_process->Destroy();
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    void Shutdown() {
 | 
			
		||||
 
 | 
			
		||||
		Reference in New Issue
	
	Block a user