gem5 O3CPU 后端文档更新


关于 gem5 O3CPU 的文档有点抽象,与代码没有密切关联。因此,本文提取关键函数链以显示指令如何由后端处理,并提供一些基本描述以降低 O3CPU 后端(IEW 和 Commit 阶段)的学习曲线。

希望这能帮助更多人。读者应该已经熟悉 gem5。本文也已添加到文档中。

计算指令

计算指令更简单,因为它们不访问内存,也不与 LSQ 交互。下面包含一个高级调用链(仅重要函数)以及每个函数功能的描述。

Rename::tick()->Rename::RenameInsts()
IEW::tick()->IEW::dispatchInsts()
IEW::tick()->InstructionQueue::scheduleReadyInsts()
IEW::tick()->IEW::executeInsts()
IEW::tick()->IEW::writebackInsts()
Commit::tick()->Commit::commitInsts()->Commit::commitHead()

加载指令

加载指令与计算指令共享相同的路径,直到执行。

IEW::tick()->IEW::executeInsts()
  ->LSQUnit::executeLoad()
    ->StaticInst::initiateAcc()
      ->LSQ::pushRequest()
        ->LSQUnit::read()
          ->LSQRequest::buildPackets()
          ->LSQRequest::sendPacketToCache()
    ->LSQUnit::checkViolation()
DcachePort::recvTimingResp()->LSQRequest::recvTimingResp()
  ->LSQUnit::completeDataAccess()
    ->LSQUnit::writeback()
      ->StaticInst::completeAcc()
      ->IEW::instToCommit()
IEW::tick()->IEW::writebackInsts()

存储指令

存储指令类似于加载指令,但仅在提交后写回到缓存。

IEW::tick()->IEW::executeInsts()
  ->LSQUnit::executeStore()
    ->StaticInst::initiateAcc()
      ->LSQ::pushRequest()
        ->LSQUnit::write()
    ->LSQUnit::checkViolation()
Commit::tick()->Commit::commitInsts()->Commit::commitHead()
IEW::tick()->LSQUnit::commitStores()
IEW::tick()->LSQUnit::writebackStores()
  ->LSQRequest::buildPackets()
  ->LSQRequest::sendPacketToCache()
  ->LSQUnit::storePostSend()
DcachePort::recvTimingResp()->LSQRequest::recvTimingResp()
  ->LSQUnit::completeDataAccess()
    ->LSQUnit::completeStore()

分支错误预测

分支错误预测在 IEW::executeInsts() 中处理。它将通知提交阶段开始压缩错误预测分支上 ROB 中的所有指令。

IEW::tick()->IEW::executeInsts()->IEW::squashDueToBranch()

内存顺序错误预测

InstructionQueue 有一个 MemDepUnit 来跟踪内存顺序依赖性。 如果 MemDepUnit 声明存在依赖性,IQ 将不会调度指令。

LSQUnit::read() 中,LSQ 将搜索可能的别名存储并在可能时转发。否则,加载被阻塞,并通过通知 MemDepUnit 在阻塞存储完成时重新调度。

LSQUnit::executeLoad/Store() 都将调用 LSQUnit::checkViolation() 来搜索 LQ 中可能的错误预测。如果找到,它将设置 LSQUnit::memDepViolatorIEW::executeInsts() 将稍后开始压缩错误预测的指令。

IEW::tick()->IEW::executeInsts()
  ->LSQUnit::executeLoad()
    ->StaticInst::initiateAcc()
    ->LSQUnit::checkViolation()
  ->IEW::squashDueToMemOrder()