diff options
| author | bunnei <bunneidev@gmail.com> | 2021-02-27 11:56:04 -0800 | 
|---|---|---|
| committer | bunnei <bunneidev@gmail.com> | 2021-02-27 11:56:04 -0800 | 
| commit | 51fb0a6f9647ba199da10fe4f018ee36e44e65ba (patch) | |
| tree | 89cd2ad6dfb310587aa546bb7b9847762795f08f /src/core/hle | |
| parent | 09f7c355c6d7e3c7845ba96d9704489d2d5853f4 (diff) | |
core: Switch to unique_ptr for usage of Common::Fiber.
- With using unique_ptr instead of shared_ptr, we have more explicit ownership of the context.
- Fixes a memory leak due to circular reference of the shared pointer.
Diffstat (limited to 'src/core/hle')
| -rw-r--r-- | src/core/hle/kernel/k_scheduler.cpp | 18 | ||||
| -rw-r--r-- | src/core/hle/kernel/k_scheduler.h | 10 | ||||
| -rw-r--r-- | src/core/hle/kernel/k_thread.cpp | 6 | ||||
| -rw-r--r-- | src/core/hle/kernel/k_thread.h | 10 | ||||
| -rw-r--r-- | src/core/hle/kernel/svc.cpp | 3 | 
5 files changed, 24 insertions, 23 deletions
| diff --git a/src/core/hle/kernel/k_scheduler.cpp b/src/core/hle/kernel/k_scheduler.cpp index bb5f43b53..465036f3d 100644 --- a/src/core/hle/kernel/k_scheduler.cpp +++ b/src/core/hle/kernel/k_scheduler.cpp @@ -608,7 +608,7 @@ void KScheduler::YieldToAnyThread(KernelCore& kernel) {  }  KScheduler::KScheduler(Core::System& system, s32 core_id) : system(system), core_id(core_id) { -    switch_fiber = std::make_shared<Common::Fiber>(OnSwitch, this); +    switch_fiber = std::make_unique<Common::Fiber>(OnSwitch, this);      state.needs_scheduling.store(true);      state.interrupt_task_thread_runnable = false;      state.should_count_idle = false; @@ -726,15 +726,15 @@ void KScheduler::ScheduleImpl() {      // Save context for previous thread      Unload(previous_thread); -    std::shared_ptr<Common::Fiber>* old_context; +    Common::Fiber* old_context;      if (previous_thread != nullptr) { -        old_context = &previous_thread->GetHostContext(); +        old_context = previous_thread->GetHostContext();      } else { -        old_context = &idle_thread->GetHostContext(); +        old_context = idle_thread->GetHostContext();      }      guard.unlock(); -    Common::Fiber::YieldTo(*old_context, switch_fiber); +    Common::Fiber::YieldTo(old_context, switch_fiber.get());      /// When a thread wakes up, the scheduler may have changed to other in another core.      auto& next_scheduler = *system.Kernel().CurrentScheduler();      next_scheduler.SwitchContextStep2(); @@ -769,13 +769,13 @@ void KScheduler::SwitchToCurrent() {                      break;                  }              } -            std::shared_ptr<Common::Fiber>* next_context; +            Common::Fiber* next_context;              if (next_thread != nullptr) { -                next_context = &next_thread->GetHostContext(); +                next_context = next_thread->GetHostContext();              } else { -                next_context = &idle_thread->GetHostContext(); +                next_context = idle_thread->GetHostContext();              } -            Common::Fiber::YieldTo(switch_fiber, *next_context); +            Common::Fiber::YieldTo(switch_fiber.get(), next_context);          } while (!is_switch_pending());      }  } diff --git a/src/core/hle/kernel/k_scheduler.h b/src/core/hle/kernel/k_scheduler.h index f595b9a5c..a4285c595 100644 --- a/src/core/hle/kernel/k_scheduler.h +++ b/src/core/hle/kernel/k_scheduler.h @@ -68,12 +68,12 @@ public:      void OnThreadStart(); -    [[nodiscard]] std::shared_ptr<Common::Fiber>& ControlContext() { -        return switch_fiber; +    [[nodiscard]] Common::Fiber* ControlContext() { +        return switch_fiber.get();      } -    [[nodiscard]] const std::shared_ptr<Common::Fiber>& ControlContext() const { -        return switch_fiber; +    [[nodiscard]] const Common::Fiber* ControlContext() const { +        return switch_fiber.get();      }      [[nodiscard]] u64 UpdateHighestPriorityThread(KThread* highest_thread); @@ -178,7 +178,7 @@ private:      KThread* idle_thread; -    std::shared_ptr<Common::Fiber> switch_fiber{}; +    std::unique_ptr<Common::Fiber> switch_fiber{};      struct SchedulingState {          std::atomic<bool> needs_scheduling; diff --git a/src/core/hle/kernel/k_thread.cpp b/src/core/hle/kernel/k_thread.cpp index 1661afbd9..f49e31b72 100644 --- a/src/core/hle/kernel/k_thread.cpp +++ b/src/core/hle/kernel/k_thread.cpp @@ -991,10 +991,6 @@ void KThread::SetState(ThreadState state) {      }  } -std::shared_ptr<Common::Fiber>& KThread::GetHostContext() { -    return host_context; -} -  ResultVal<std::shared_ptr<KThread>> KThread::Create(Core::System& system, ThreadType type_flags,                                                      std::string name, VAddr entry_point,                                                      u32 priority, u64 arg, s32 processor_id, @@ -1028,7 +1024,7 @@ ResultVal<std::shared_ptr<KThread>> KThread::Create(Core::System& system, Thread      scheduler.AddThread(thread);      thread->host_context = -        std::make_shared<Common::Fiber>(std::move(thread_start_func), thread_start_parameter); +        std::make_unique<Common::Fiber>(std::move(thread_start_func), thread_start_parameter);      return MakeResult<std::shared_ptr<KThread>>(std::move(thread));  } diff --git a/src/core/hle/kernel/k_thread.h b/src/core/hle/kernel/k_thread.h index c8ac656a4..a2893d939 100644 --- a/src/core/hle/kernel/k_thread.h +++ b/src/core/hle/kernel/k_thread.h @@ -293,7 +293,13 @@ public:          return thread_context_64;      } -    [[nodiscard]] std::shared_ptr<Common::Fiber>& GetHostContext(); +    [[nodiscard]] Common::Fiber* GetHostContext() { +        return host_context.get(); +    } + +    [[nodiscard]] const Common::Fiber* GetHostContext() const { +        return host_context.get(); +    }      [[nodiscard]] ThreadState GetState() const {          return thread_state & ThreadState::Mask; @@ -719,7 +725,7 @@ private:      Common::SpinLock context_guard{};      // For emulation -    std::shared_ptr<Common::Fiber> host_context{}; +    std::unique_ptr<Common::Fiber> host_context{};      // For debugging      std::vector<KSynchronizationObject*> wait_objects_for_debugging; diff --git a/src/core/hle/kernel/svc.cpp b/src/core/hle/kernel/svc.cpp index cc8fa6576..d04116115 100644 --- a/src/core/hle/kernel/svc.cpp +++ b/src/core/hle/kernel/svc.cpp @@ -2626,8 +2626,7 @@ void Call(Core::System& system, u32 immediate) {      kernel.ExitSVCProfile();      if (!thread->IsCallingSvc()) { -        auto* host_context = thread->GetHostContext().get(); -        host_context->Rewind(); +        thread->GetHostContext()->Rewind();      }      system.EnterDynarmicProfile(); | 
