diff options
author | Gabe Black <gabeblack@google.com> | 2014-12-05 01:47:35 -0800 |
---|---|---|
committer | Gabe Black <gabeblack@google.com> | 2014-12-05 01:47:35 -0800 |
commit | bacbb8ecbcee2b4c5c3fe71f415abc5852ae4a8f (patch) | |
tree | 79e771d5209f85f6d3ecf5cafcb5d9e254fa7be0 /src/cpu/o3 | |
parent | fe48c0a32bf749358eeb95e748f9fc2247cc5480 (diff) | |
download | gem5-bacbb8ecbcee2b4c5c3fe71f415abc5852ae4a8f.tar.xz |
cpu: Only check for PC events on instruction boundaries.
Only the instruction address is actually checked, so there's no need to check
repeatedly while we're working through the microops of a macroop and that's
not changing.
Diffstat (limited to 'src/cpu/o3')
-rw-r--r-- | src/cpu/o3/commit_impl.hh | 41 |
1 files changed, 24 insertions, 17 deletions
diff --git a/src/cpu/o3/commit_impl.hh b/src/cpu/o3/commit_impl.hh index f0566233c..bb2b17209 100644 --- a/src/cpu/o3/commit_impl.hh +++ b/src/cpu/o3/commit_impl.hh @@ -1,4 +1,5 @@ /* + * Copyright 2014 Google, Inc. * Copyright (c) 2010-2014 ARM Limited * All rights reserved * @@ -1105,20 +1106,27 @@ DefaultCommit<Impl>::commitInsts() } } - int count = 0; - Addr oldpc; - // Debug statement. Checks to make sure we're not - // currently updating state while handling PC events. - assert(!thread[tid]->noSquashFromTC && !thread[tid]->trapPending); - do { - oldpc = pc[tid].instAddr(); - cpu->system->pcEventQueue.service(thread[tid]->getTC()); - count++; - } while (oldpc != pc[tid].instAddr()); - if (count > 1) { - DPRINTF(Commit, - "PC skip function event, stopping commit\n"); - break; + bool onInstBoundary = !head_inst->isMicroop() || + head_inst->isLastMicroop() || + !head_inst->isDelayedCommit(); + + if (onInstBoundary) { + int count = 0; + Addr oldpc; + // Make sure we're not currently updating state while + // handling PC events. + assert(!thread[tid]->noSquashFromTC && + !thread[tid]->trapPending); + do { + oldpc = pc[tid].instAddr(); + cpu->system->pcEventQueue.service(thread[tid]->getTC()); + count++; + } while (oldpc != pc[tid].instAddr()); + if (count > 1) { + DPRINTF(Commit, + "PC skip function event, stopping commit\n"); + break; + } } // Check if an instruction just enabled interrupts and we've @@ -1128,9 +1136,8 @@ DefaultCommit<Impl>::commitInsts() // case squash now to make sure the interrupt is handled. // // If we don't do this, we might end up in a live lock situation - if (!interrupt && avoidQuiesceLiveLock && - (!head_inst->isMicroop() || head_inst->isLastMicroop()) && - cpu->checkInterrupts(cpu->tcBase(0))) + if (!interrupt && avoidQuiesceLiveLock && + onInstBoundary && cpu->checkInterrupts(cpu->tcBase(0))) squashAfter(tid, head_inst); } else { DPRINTF(Commit, "Unable to commit head instruction PC:%s " |