summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/cpu/inorder/thread_context.cc10
-rwxr-xr-xsrc/cpu/o3/thread_context_impl.hh30
-rw-r--r--src/cpu/simple_thread.cc44
-rw-r--r--src/cpu/simple_thread.hh2
-rw-r--r--src/cpu/thread_context.cc37
-rw-r--r--src/cpu/thread_context.hh13
6 files changed, 57 insertions, 79 deletions
diff --git a/src/cpu/inorder/thread_context.cc b/src/cpu/inorder/thread_context.cc
index 2990430e1..aab8c226a 100644
--- a/src/cpu/inorder/thread_context.cc
+++ b/src/cpu/inorder/thread_context.cc
@@ -93,18 +93,10 @@ InOrderThreadContext::profileSample()
void
InOrderThreadContext::takeOverFrom(ThreadContext *old_context)
{
- // some things should already be set up
- assert(getSystemPtr() == old_context->getSystemPtr());
- assert(getProcessPtr() == old_context->getProcessPtr());
-
- // copy over functional state
- setStatus(old_context->status());
- copyArchRegs(old_context);
+ ::takeOverFrom(*this, *old_context);
thread->funcExeInst = old_context->readFuncExeInst();
- old_context->setStatus(ThreadContext::Halted);
-
thread->noSquashFromTC = false;
thread->trapPending = false;
}
diff --git a/src/cpu/o3/thread_context_impl.hh b/src/cpu/o3/thread_context_impl.hh
index 0a8dfeb3e..6de5c5731 100755
--- a/src/cpu/o3/thread_context_impl.hh
+++ b/src/cpu/o3/thread_context_impl.hh
@@ -66,34 +66,10 @@ template <class Impl>
void
O3ThreadContext<Impl>::takeOverFrom(ThreadContext *old_context)
{
- // some things should already be set up
- assert(getSystemPtr() == old_context->getSystemPtr());
- assert(getProcessPtr() == old_context->getProcessPtr());
+ ::takeOverFrom(*this, *old_context);
- // copy over functional state
- setStatus(old_context->status());
- copyArchRegs(old_context);
- setContextId(old_context->contextId());
- setThreadId(old_context->threadId());
-
- if (FullSystem) {
- EndQuiesceEvent *other_quiesce = old_context->getQuiesceEvent();
- if (other_quiesce) {
- // Point the quiesce event's TC at this TC so that it wakes up
- // the proper CPU.
- other_quiesce->tc = this;
- }
- if (thread->quiesceEvent) {
- thread->quiesceEvent->tc = this;
- }
-
- // Transfer kernel stats from one CPU to the other.
- thread->kernelStats = old_context->getKernelStats();
- } else {
- thread->funcExeInst = old_context->readFuncExeInst();
- }
-
- old_context->setStatus(ThreadContext::Halted);
+ thread->kernelStats = old_context->getKernelStats();
+ thread->funcExeInst = old_context->readFuncExeInst();
thread->noSquashFromTC = false;
thread->trapPending = false;
diff --git a/src/cpu/simple_thread.cc b/src/cpu/simple_thread.cc
index 787680224..9cf8da7b4 100644
--- a/src/cpu/simple_thread.cc
+++ b/src/cpu/simple_thread.cc
@@ -107,49 +107,11 @@ SimpleThread::~SimpleThread()
void
SimpleThread::takeOverFrom(ThreadContext *oldContext)
{
- // some things should already be set up
- if (FullSystem)
- assert(system == oldContext->getSystemPtr());
- assert(process == oldContext->getProcessPtr());
-
- copyState(oldContext);
- if (FullSystem) {
- EndQuiesceEvent *quiesce = oldContext->getQuiesceEvent();
- if (quiesce) {
- // Point the quiesce event's TC at this TC so that it wakes up
- // the proper CPU.
- quiesce->tc = tc;
- }
- if (quiesceEvent) {
- quiesceEvent->tc = tc;
- }
-
- TheISA::Kernel::Statistics *stats = oldContext->getKernelStats();
- if (stats) {
- kernelStats = stats;
- }
- }
+ ::takeOverFrom(*tc, *oldContext);
+ kernelStats = oldContext->getKernelStats();
+ funcExeInst = oldContext->readFuncExeInst();
storeCondFailures = 0;
-
- oldContext->setStatus(ThreadContext::Halted);
-}
-
-void
-SimpleThread::copyTC(ThreadContext *context)
-{
- copyState(context);
-
- if (FullSystem) {
- EndQuiesceEvent *quiesce = context->getQuiesceEvent();
- if (quiesce) {
- quiesceEvent = quiesce;
- }
- TheISA::Kernel::Statistics *stats = context->getKernelStats();
- if (stats) {
- kernelStats = stats;
- }
- }
}
void
diff --git a/src/cpu/simple_thread.hh b/src/cpu/simple_thread.hh
index ee54850ae..6f1173b7f 100644
--- a/src/cpu/simple_thread.hh
+++ b/src/cpu/simple_thread.hh
@@ -146,8 +146,6 @@ class SimpleThread : public ThreadState
void regStats(const std::string &name);
- void copyTC(ThreadContext *context);
-
void copyState(ThreadContext *oldContext);
void serialize(std::ostream &os);
diff --git a/src/cpu/thread_context.cc b/src/cpu/thread_context.cc
index 4a4038297..a5a05a264 100644
--- a/src/cpu/thread_context.cc
+++ b/src/cpu/thread_context.cc
@@ -43,8 +43,11 @@
#include "base/misc.hh"
#include "base/trace.hh"
#include "config/the_isa.hh"
+#include "cpu/base.hh"
+#include "cpu/quiesce_event.hh"
#include "cpu/thread_context.hh"
#include "debug/Context.hh"
+#include "sim/full_system.hh"
void
ThreadContext::compare(ThreadContext *one, ThreadContext *two)
@@ -136,3 +139,37 @@ unserialize(ThreadContext &tc, Checkpoint *cp, const std::string &section)
// thread_num and cpu_id are deterministic from the config
}
+
+void
+takeOverFrom(ThreadContext &ntc, ThreadContext &otc)
+{
+ assert(ntc.getProcessPtr() == otc.getProcessPtr());
+
+ ntc.setStatus(otc.status());
+ ntc.copyArchRegs(&otc);
+ ntc.setContextId(otc.contextId());
+ ntc.setThreadId(otc.threadId());
+
+ if (FullSystem) {
+ assert(ntc.getSystemPtr() == otc.getSystemPtr());
+
+ BaseCPU *ncpu(ntc.getCpuPtr());
+ assert(ncpu);
+ EndQuiesceEvent *oqe(otc.getQuiesceEvent());
+ assert(oqe);
+ assert(oqe->tc == &otc);
+
+ BaseCPU *ocpu(otc.getCpuPtr());
+ assert(ocpu);
+ EndQuiesceEvent *nqe(ntc.getQuiesceEvent());
+ assert(nqe);
+ assert(nqe->tc == &ntc);
+
+ if (oqe->scheduled()) {
+ ncpu->schedule(nqe, oqe->when());
+ ocpu->deschedule(oqe);
+ }
+ }
+
+ otc.setStatus(ThreadContext::Halted);
+}
diff --git a/src/cpu/thread_context.hh b/src/cpu/thread_context.hh
index c54076c8a..dbe3c0ce8 100644
--- a/src/cpu/thread_context.hh
+++ b/src/cpu/thread_context.hh
@@ -481,4 +481,17 @@ void unserialize(ThreadContext &tc, Checkpoint *cp, const std::string &section);
/** @} */
+
+/**
+ * Copy state between thread contexts in preparation for CPU handover.
+ *
+ * @note This method modifies the old thread contexts as well as the
+ * new thread context. The old thread context will have its quiesce
+ * event descheduled if it is scheduled and its status set to halted.
+ *
+ * @param new_tc Destination ThreadContext.
+ * @param old_tc Source ThreadContext.
+ */
+void takeOverFrom(ThreadContext &new_tc, ThreadContext &old_tc);
+
#endif