From 2c8b7bfe5251d201bdfbd2720d3da3b593139a4e Mon Sep 17 00:00:00 2001 From: Timothy Hayes Date: Fri, 18 Oct 2019 17:19:03 +0100 Subject: [PATCH] mem-ruby: MESI_Three_Level discriminate L0 invalidation reason The L0 cache can now know whether a line is being invalidated due to this cache/core's own requirements, e.g. a load from the core causing a line eviction, or due to another cache/core's requirements, e.g. a remote cache requesting a present line in exclusive state. Change-Id: If57bfb92b6c8f575ca47d984606be7c859dcff9a Reviewed-on: https://gem5-review.googlesource.com/c/public/gem5/+/24259 Tested-by: Gem5 Cloud Project GCB service account <345032938727@cloudbuild.gserviceaccount.com> Tested-by: kokoro Reviewed-by: Giacomo Travaglini Maintainer: Giacomo Travaglini --- .../ruby/protocol/MESI_Three_Level-L0cache.sm | 20 ++++++---- .../ruby/protocol/MESI_Three_Level-L1cache.sm | 40 ++++++++++++++----- src/mem/ruby/protocol/MESI_Three_Level-msg.sm | 15 ++++++- 3 files changed, 57 insertions(+), 18 deletions(-) diff --git a/src/mem/ruby/protocol/MESI_Three_Level-L0cache.sm b/src/mem/ruby/protocol/MESI_Three_Level-L0cache.sm index c6697c368..b74a7276a 100644 --- a/src/mem/ruby/protocol/MESI_Three_Level-L0cache.sm +++ b/src/mem/ruby/protocol/MESI_Three_Level-L0cache.sm @@ -101,7 +101,9 @@ machine(MachineType:L0Cache, "MESI Directory L0 Cache") Ifetch, desc="I-fetch request from the home processor"; Store, desc="Store request from the home processor"; - Inv, desc="Invalidate request from L2 bank"; + // invalidations from L1 (due to self or other core) + InvOwn, desc="Invalidate request from L1 (own)"; + InvElse, desc="Invalidate request from L1 (else)"; // internal generated request L0_Replacement, desc="L0 Replacement", format="!r"; @@ -287,8 +289,10 @@ machine(MachineType:L0Cache, "MESI Directory L0 Cache") trigger(Event:Ack, in_msg.addr, cache_entry, tbe); } else if (in_msg.Class == CoherenceClass:WB_ACK) { trigger(Event:WB_Ack, in_msg.addr, cache_entry, tbe); - } else if (in_msg.Class == CoherenceClass:INV) { - trigger(Event:Inv, in_msg.addr, cache_entry, tbe); + } else if (in_msg.Class == CoherenceClass:INV_OWN) { + trigger(Event:InvOwn, in_msg.addr, cache_entry, tbe); + } else if (in_msg.Class == CoherenceClass:INV_ELSE) { + trigger(Event:InvElse, in_msg.addr, cache_entry, tbe); } else if (in_msg.Class == CoherenceClass:GETX || in_msg.Class == CoherenceClass:UPGRADE) { // upgrade transforms to GETX due to race @@ -659,12 +663,12 @@ machine(MachineType:L0Cache, "MESI Directory L0 Cache") k_popMandatoryQueue; } - transition({I, IS, IM, Inst_IS}, Inv) { + transition({I, IS, IM, Inst_IS}, {InvOwn, InvElse}) { fi_sendInvAck; l_popRequestQueue; } - transition(SM, Inv, IM) { + transition(SM, {InvOwn, InvElse}, IM) { fi_sendInvAck; l_popRequestQueue; } @@ -694,7 +698,7 @@ machine(MachineType:L0Cache, "MESI Directory L0 Cache") ff_deallocateCacheBlock; } - transition(S, Inv, I) { + transition(S, {InvOwn, InvElse}, I) { forward_eviction_to_cpu; fi_sendInvAck; ff_deallocateCacheBlock; @@ -714,7 +718,7 @@ machine(MachineType:L0Cache, "MESI Directory L0 Cache") ff_deallocateCacheBlock; } - transition(E, {Inv, Fwd_GETX}, I) { + transition(E, {InvOwn, InvElse, Fwd_GETX}, I) { // don't send data forward_eviction_to_cpu; fi_sendInvAck; @@ -734,7 +738,7 @@ machine(MachineType:L0Cache, "MESI Directory L0 Cache") ff_deallocateCacheBlock; } - transition(M, {Inv, Fwd_GETX}, I) { + transition(M, {InvOwn, InvElse, Fwd_GETX}, I) { forward_eviction_to_cpu; f_sendDataToL1; ff_deallocateCacheBlock; diff --git a/src/mem/ruby/protocol/MESI_Three_Level-L1cache.sm b/src/mem/ruby/protocol/MESI_Three_Level-L1cache.sm index eec07ca31..00d897a81 100644 --- a/src/mem/ruby/protocol/MESI_Three_Level-L1cache.sm +++ b/src/mem/ruby/protocol/MESI_Three_Level-L1cache.sm @@ -553,10 +553,20 @@ machine(MachineType:L1Cache, "MESI Directory L1 Cache CMP") } } - action(forward_eviction_to_L0, "\cc", desc="sends eviction information to the processor") { + action(forward_eviction_to_L0_own, "\cc", desc="sends (own) eviction information to the processor") { enqueue(bufferToL0_out, CoherenceMsg, l1_request_latency) { out_msg.addr := address; - out_msg.Class := CoherenceClass:INV; + out_msg.Class := CoherenceClass:INV_OWN; + out_msg.Sender := machineID; + out_msg.Dest := createMachineID(MachineType:L0Cache, version); + out_msg.MessageSize := MessageSizeType:Control; + } + } + + action(forward_eviction_to_L0_else, "\cce", desc="sends (else) eviction information to the processor") { + enqueue(bufferToL0_out, CoherenceMsg, l1_request_latency) { + out_msg.addr := address; + out_msg.Class := CoherenceClass:INV_ELSE; out_msg.Sender := machineID; out_msg.Dest := createMachineID(MachineType:L0Cache, version); out_msg.MessageSize := MessageSizeType:Control; @@ -816,8 +826,12 @@ machine(MachineType:L1Cache, "MESI Directory L1 Cache CMP") ff_deallocateCacheBlock; } - transition(S, {L0_Invalidate_Own, L0_Invalidate_Else}, S_IL0) { - forward_eviction_to_L0; + transition(S, L0_Invalidate_Own, S_IL0) { + forward_eviction_to_L0_own; + } + + transition(S, L0_Invalidate_Else, S_IL0) { + forward_eviction_to_L0_else; } transition(SS, Inv, I) { @@ -860,8 +874,12 @@ machine(MachineType:L1Cache, "MESI Directory L1 Cache CMP") l_popL2RequestQueue; } - transition(E, {L0_Invalidate_Own, L0_Invalidate_Else}, E_IL0) { - forward_eviction_to_L0; + transition(E, L0_Invalidate_Own, E_IL0) { + forward_eviction_to_L0_own; + } + + transition(E, L0_Invalidate_Else, E_IL0) { + forward_eviction_to_L0_else; } // Transitions from Modified @@ -906,8 +924,12 @@ machine(MachineType:L1Cache, "MESI Directory L1 Cache CMP") l_popL2RequestQueue; } - transition(M, {L0_Invalidate_Own, L0_Invalidate_Else}, M_IL0) { - forward_eviction_to_L0; + transition(M, L0_Invalidate_Own, M_IL0) { + forward_eviction_to_L0_own; + } + + transition(M, L0_Invalidate_Else, M_IL0) { + forward_eviction_to_L0_else; } transition(M_I, Fwd_GETX, SINK_WB_ACK) { @@ -1008,7 +1030,7 @@ machine(MachineType:L1Cache, "MESI Directory L1 Cache CMP") } transition(SM, L0_Invalidate_Else, SM_IL0) { - forward_eviction_to_L0; + forward_eviction_to_L0_else; } transition(SINK_WB_ACK, Inv){ diff --git a/src/mem/ruby/protocol/MESI_Three_Level-msg.sm b/src/mem/ruby/protocol/MESI_Three_Level-msg.sm index 2a5ecc8e8..fa583e0cc 100644 --- a/src/mem/ruby/protocol/MESI_Three_Level-msg.sm +++ b/src/mem/ruby/protocol/MESI_Three_Level-msg.sm @@ -1,4 +1,16 @@ /* + * Copyright (c) 2020 ARM Limited + * All rights reserved + * + * The license below extends only to copyright in the software and shall + * not be construed as granting a license to any other intellectual + * property including but not limited to intellectual property relating + * to a hardware implementation of the functionality of the software + * licensed hereunder. You may use the software subject to the license + * terms below provided that you ensure that this notice is replicated + * unmodified and in its entirety in all distributions of the software, + * modified or unmodified, in source code or in binary form. + * * Copyright (c) 2013 Mark D. Hill and David A. Wood * All rights reserved. * @@ -33,7 +45,8 @@ enumeration(CoherenceClass, desc="...") { UPGRADE, desc="UPGRADE to exclusive"; GETS, desc="Get Shared"; GET_INSTR, desc="Get Instruction"; - INV, desc="INValidate"; + INV_OWN, desc="Invalidate (own)"; + INV_ELSE, desc="Invalidate (else)"; PUTX, desc="Replacement message"; WB_ACK, desc="Writeback ack"; -- 2.30.2