diff --git a/src/cache/cache.sv b/src/cache/cache.sv index ae4415dbd..4701fc4c7 100644 --- a/src/cache/cache.sv +++ b/src/cache/cache.sv @@ -88,7 +88,7 @@ module cache import cvw::*; #(parameter cvw_t P, logic FlushAdrFlag, FlushWayFlag; logic [NUMWAYS-1:0] FlushWay, NextFlushWay; logic FlushWayCntEn; - logic SelBothWriteback; + logic SelWriteback; logic LRUWriteEn; logic SelFlush; logic ResetOrFlushCntRst; @@ -156,7 +156,7 @@ module cache import cvw::*; #(parameter cvw_t P, mux3 #(PA_BITS) CacheBusAdrMux(.d0({PAdr[PA_BITS-1:OFFSETLEN], {OFFSETLEN{1'b0}}}), .d1({Tag, PAdr[SETTOP-1:OFFSETLEN], {OFFSETLEN{1'b0}}}), .d2({Tag, FlushAdr, {OFFSETLEN{1'b0}}}), - .s({SelFlush, SelBothWriteback}), .y(CacheBusAdr)); + .s({SelFlush, SelWriteback}), .y(CacheBusAdr)); ///////////////////////////////////////////////////////////////////////////////////////////// // Write Path @@ -227,7 +227,7 @@ module cache import cvw::*; #(parameter cvw_t P, .FlushStage, .CacheRW, .Stall, .CacheHit, .LineDirty, .CacheStall, .CacheCommitted, .CacheMiss, .CacheAccess, .SelAdr, .SelWay, - .ClearDirty, .SetDirty, .SetValid, .ClearValid, .ZeroCacheLine, .SelBothWriteback, .SelFlush, + .ClearDirty, .SetDirty, .SetValid, .ClearValid, .ZeroCacheLine, .SelWriteback, .SelFlush, .FlushAdrCntEn, .FlushWayCntEn, .FlushCntRst, .FlushAdrFlag, .FlushWayFlag, .FlushCache, .SelFetchBuffer, .InvalidateCache, .CMOp, .CacheEn, .LRUWriteEn); diff --git a/src/cache/cachefsm.sv b/src/cache/cachefsm.sv index 392bcdf03..8a11dd735 100644 --- a/src/cache/cachefsm.sv +++ b/src/cache/cachefsm.sv @@ -59,7 +59,7 @@ module cachefsm import cvw::*; #(parameter cvw_t P, output logic SetDirty, // Set the dirty bit in the selected way and set output logic ClearDirty, // Clear the dirty bit in the selected way and set output logic ZeroCacheLine, // Write zeros to all bytes of cacheline - output logic SelBothWriteback, // Overrides cached tag check to select a specific way and set for writeback + output logic SelWriteback, // Overrides cached tag check to select a specific way and set for writeback output logic LRUWriteEn, // Update the LRU state output logic SelFlush, // [0] Use SelAdr, [1] SRAM reads/writes from FlushAdr output logic SelWay, // Controls which way to select a way data and tag, 00 = hitway, 10 = victimway, 11 = flushway @@ -75,10 +75,9 @@ module cachefsm import cvw::*; #(parameter cvw_t P, logic AnyMiss; logic FlushFlag; logic CMOWritebackHit; + logic CMOWriteback; logic CMOZeroNoEviction; logic CMOZeroEviction; - logic SelWriteback; // Overrides cached tag check to select a specific way and set for writeback - logic SelCMOWriteback; // Overrides cached tag check to select a specific way and set for writeback for both data and tag typedef enum logic [3:0]{STATE_READY, // hit states // miss states @@ -88,10 +87,7 @@ module cachefsm import cvw::*; #(parameter cvw_t P, STATE_READ_HOLD, // required for back to back reads. structural hazard on writting SRAM // flush cache STATE_FLUSH, - STATE_FLUSH_WRITEBACK, - // CMO states - STATE_CMO_WRITEBACK, - STATE_CMO_DONE + STATE_FLUSH_WRITEBACK } statetype; statetype CurrState, NextState; @@ -102,6 +98,7 @@ module cachefsm import cvw::*; #(parameter cvw_t P, assign CMOWritebackHit = (CMOp[1] | CMOp[2]) & CacheHit; assign CMOZeroNoEviction = CMOp[3] & ~LineDirty; // (hit or miss) with no writeback store zeros now assign CMOZeroEviction = CMOp[3] & LineDirty; // (hit or miss) with writeback dirty line + assign CMOWriteback = CMOWritebackHit | CMOZeroEviction; assign FlushFlag = FlushAdrFlag & FlushWayFlag; @@ -124,8 +121,7 @@ module cachefsm import cvw::*; #(parameter cvw_t P, STATE_READY: if(InvalidateCache) NextState = STATE_READY; // exclusion-tag: dcache InvalidateCheck else if(FlushCache & ~READ_ONLY_CACHE) NextState = STATE_FLUSH; else if(AnyMiss & (READ_ONLY_CACHE | ~LineDirty)) NextState = STATE_FETCH; // exclusion-tag: icache FETCHStatement - else if(AnyMiss | CMOZeroEviction) NextState = STATE_WRITEBACK; // exclusion-tag: icache WRITEBACKStatement - else if(CMOWritebackHit) NextState = STATE_CMO_WRITEBACK; + else if(AnyMiss | CMOWriteback) NextState = STATE_WRITEBACK; // exclusion-tag: icache WRITEBACKStatement else NextState = STATE_READY; STATE_FETCH: if(CacheBusAck) NextState = STATE_WRITE_LINE; else if(CacheBusAck) NextState = STATE_READY; @@ -134,8 +130,9 @@ module cachefsm import cvw::*; #(parameter cvw_t P, STATE_READ_HOLD: if(Stall) NextState = STATE_READ_HOLD; else NextState = STATE_READY; // exclusion-tag-start: icache case - STATE_WRITEBACK: if(CacheBusAck & ~CMOp[3]) NextState = STATE_FETCH; - else if(CacheBusAck) NextState = STATE_CMO_DONE; + STATE_WRITEBACK: if (CacheBusAck & (CMOp[1] | CMOp[2])) NextState = STATE_READ_HOLD; + else if(CacheBusAck & ~CMOp[3]) NextState = STATE_FETCH; + else if(CacheBusAck) NextState = STATE_READ_HOLD; else NextState = STATE_WRITEBACK; // eviction needs a delay as the bus fsm does not correctly handle sending the write command at the same time as getting back the bus ack. STATE_FLUSH: if(LineDirty) NextState = STATE_FLUSH_WRITEBACK; @@ -144,31 +141,25 @@ module cachefsm import cvw::*; #(parameter cvw_t P, STATE_FLUSH_WRITEBACK: if(CacheBusAck & ~FlushFlag) NextState = STATE_FLUSH; else if(CacheBusAck) NextState = STATE_READ_HOLD; else NextState = STATE_FLUSH_WRITEBACK; - - STATE_CMO_WRITEBACK: if(CacheBusAck & (CMOp[1] | CMOp[2])) NextState = STATE_CMO_DONE; - else NextState = STATE_CMO_WRITEBACK; - STATE_CMO_DONE: if(Stall) NextState = STATE_CMO_DONE; - else NextState = STATE_READY; // exclusion-tag-end: icache case default: NextState = STATE_READY; endcase end // com back to CPU - assign CacheCommitted = (CurrState != STATE_READY) & ~(READ_ONLY_CACHE & (CurrState == STATE_READ_HOLD | CurrState == STATE_CMO_DONE)); - assign CacheStall = (CurrState == STATE_READY & (FlushCache | AnyMiss | CMOWritebackHit | CMOZeroEviction)) | // exclusion-tag: icache StallStates + assign CacheCommitted = (CurrState != STATE_READY) & ~(READ_ONLY_CACHE & (CurrState == STATE_READ_HOLD)); + assign CacheStall = (CurrState == STATE_READY & (FlushCache | AnyMiss | CMOWriteback)) | // exclusion-tag: icache StallStates (CurrState == STATE_FETCH) | (CurrState == STATE_WRITEBACK) | (CurrState == STATE_WRITE_LINE) | // this cycle writes the sram, must keep stalling so the next cycle can read the next hit/miss unless its a write. (CurrState == STATE_FLUSH) | - (CurrState == STATE_FLUSH_WRITEBACK) | - (CurrState == STATE_CMO_WRITEBACK); + (CurrState == STATE_FLUSH_WRITEBACK); // write enables internal to cache assign SetValid = CurrState == STATE_WRITE_LINE | (P.ZICBOZ_SUPPORTED & CurrState == STATE_READY & CMOZeroNoEviction) | (P.ZICBOZ_SUPPORTED & CurrState == STATE_WRITEBACK & CacheBusAck & CMOp[3]); assign ClearValid = P.ZICBOM_SUPPORTED & ((CurrState == STATE_READY & CMOp[0] & CacheHit) | - (CurrState == STATE_CMO_WRITEBACK & CMOp[2] & CacheBusAck)); + (CurrState == STATE_WRITEBACK & CMOp[2] & CacheBusAck)); // coverage off -item e 1 -fecexprrow 8 assign LRUWriteEn = (((CurrState == STATE_READY & (AnyHit | CMOZeroNoEviction)) | (CurrState == STATE_WRITE_LINE)) & ~FlushStage) | @@ -180,19 +171,14 @@ module cachefsm import cvw::*; #(parameter cvw_t P, assign ClearDirty = (CurrState == STATE_WRITE_LINE & ~(CacheRW[0])) | // exclusion-tag: icache ClearDirty (CurrState == STATE_FLUSH & LineDirty) | // This is wrong in a multicore snoop cache protocal. Dirty must be cleared concurrently and atomically with writeback. For single core cannot clear after writeback on bus ack and change flushadr. Clears the wrong set. // Flush and eviction controls - (P.ZICBOM_SUPPORTED & CurrState == STATE_CMO_WRITEBACK & (CMOp[1] | CMOp[2]) & CacheBusAck); - assign SelWay = SelWriteback | (CurrState == STATE_WRITE_LINE) | - // This is almost the same as setvalid, but on cachehit we don't want to select - // the nonhit way, but instead want to force this to zero - (P.ZICBOZ_SUPPORTED & CurrState == STATE_READY & CMOZeroNoEviction & ~CacheHit) | - (P.ZICBOZ_SUPPORTED & CurrState == STATE_WRITEBACK & CacheBusAck & CMOp[3]); + (P.ZICBOM_SUPPORTED & CurrState == STATE_WRITEBACK & (CMOp[1] | CMOp[2]) & CacheBusAck); + assign SelWay = (CurrState == STATE_WRITEBACK & ((~CacheBusAck & ~(CMOp[1] | CMOp[2])) | (P.ZICBOZ_SUPPORTED & CacheBusAck & CMOp[3]))) | + (CurrState == STATE_READY & ((AnyMiss & LineDirty) | (P.ZICBOZ_SUPPORTED & CMOZeroNoEviction & ~CacheHit))) | + (CurrState == STATE_WRITE_LINE); assign ZeroCacheLine = P.ZICBOZ_SUPPORTED & ((CurrState == STATE_READY & CMOZeroNoEviction) | (CurrState == STATE_WRITEBACK & (CMOp[3] & CacheBusAck))); - assign SelWriteback = (CurrState == STATE_WRITEBACK & ~CacheBusAck) | - (CurrState == STATE_READY & AnyMiss & LineDirty); - assign SelCMOWriteback = CurrState == STATE_CMO_WRITEBACK; - assign SelBothWriteback = SelWriteback | SelCMOWriteback; - + assign SelWriteback = (CurrState == STATE_WRITEBACK & (CMOp[1] | CMOp[2] | ~CacheBusAck)) | + (CurrState == STATE_READY & AnyMiss & LineDirty); assign SelFlush = (CurrState == STATE_READY & FlushCache) | (CurrState == STATE_FLUSH) | (CurrState == STATE_FLUSH_WRITEBACK); @@ -208,17 +194,16 @@ module cachefsm import cvw::*; #(parameter cvw_t P, // Bus interface controls assign CacheBusRW[1] = (CurrState == STATE_READY & AnyMiss & ~LineDirty) | // exclusion-tag: icache CacheBusRCauses (CurrState == STATE_FETCH & ~CacheBusAck) | - (CurrState == STATE_WRITEBACK & CacheBusAck & ~CMOp[3]); + (CurrState == STATE_WRITEBACK & CacheBusAck & ~(|CMOp)); assign CacheBusRW[0] = (CurrState == STATE_READY & AnyMiss & LineDirty) | // exclusion-tag: icache CacheBusW (CurrState == STATE_WRITEBACK & ~CacheBusAck) | (CurrState == STATE_FLUSH_WRITEBACK & ~CacheBusAck) | - (P.ZICBOM_SUPPORTED & CurrState == STATE_CMO_WRITEBACK & (CMOp[1] | CMOp[2]) & ~CacheBusAck); + (P.ZICBOM_SUPPORTED & CurrState == STATE_WRITEBACK & (CMOp[1] | CMOp[2]) & ~CacheBusAck); assign SelAdr = (CurrState == STATE_READY & (CacheRW[0] | AnyMiss | (|CMOp))) | // exclusion-tag: icache SelAdrCauses // changes if store delay hazard removed (CurrState == STATE_FETCH) | (CurrState == STATE_WRITEBACK) | (CurrState == STATE_WRITE_LINE) | - (CurrState == STATE_CMO_WRITEBACK) | resetDelay; assign SelFetchBuffer = CurrState == STATE_WRITE_LINE | CurrState == STATE_READ_HOLD; assign CacheEn = (~Stall | FlushCache | AnyMiss) | (CurrState != STATE_READY) | reset | InvalidateCache; // exclusion-tag: dcache CacheEn