diff --git a/src_Core/RISCY_OOO/procs/lib/Map.bsv b/src_Core/RISCY_OOO/procs/lib/Map.bsv index 388dcb9..9bf3600 100644 --- a/src_Core/RISCY_OOO/procs/lib/Map.bsv +++ b/src_Core/RISCY_OOO/procs/lib/Map.bsv @@ -55,7 +55,7 @@ typedef struct { // the value stored in the map, and the associativity of the storage. interface Map#(type ky, type ix, type vl, numeric type as); method Action update(MapKeyIndex#(ky,ix) key, vl value); - method Action updateWithFunc(MapKeyIndex#(ky,ix) ki, vl value, function vl up(vl old_v, vl new_v)); + method Action updateWithFunc(MapKeyIndex#(ky,ix) ki, vl value, function vl up(vl old_v, vl new_v), Bool insert); method Maybe#(vl) lookup(MapKeyIndex#(ky,ix) lookup_key); method Action clear; method Bool clearDone; @@ -79,29 +79,31 @@ Bitwise#(ix), Eq#(ix), Arith#(ix)); if (clearCount == ~0) clearReg <= False; endrule - function Action doUpdate(MapKeyIndex#(ky,ix) ki, vl value, function vl up(vl old_v, vl new_v)); + function Action doUpdate(MapKeyIndex#(ky,ix) ki, vl value, function vl up(vl old_v, vl new_v), Bool insert); action + Bool found = False; Bit#(TLog#(as)) way = wayNext; MapKeyValue#(ky,vl) old = unpack(0); if (a > 1) begin for (Integer i = 0; i < a; i = i + 1) begin MapKeyValue#(ky,vl) entry = mem[i].sub(ki.index); if (entry.key == ki.key) begin + found = True; way = fromInteger(i); old = entry; end end end - mem[way].upd(ki.index, MapKeyValue{key: ki.key, value: up(old.value, value)}); + if (found || insert) mem[way].upd(ki.index, MapKeyValue{key: ki.key, value: up(old.value, value)}); wayNext <= (wayNext == fromInteger(a-1)) ? 0: wayNext + 1; didUpdate.send; endaction endfunction function vl returnNew(vl old_v, vl new_v) = new_v; - method Action update(MapKeyIndex#(ky,ix) ki, vl value) = doUpdate(ki, value, returnNew); - method Action updateWithFunc(MapKeyIndex#(ky,ix) ki, vl value, function vl up(vl old_v, vl new_v)) = - doUpdate(ki, value, up); + method Action update(MapKeyIndex#(ky,ix) ki, vl value) = doUpdate(ki, value, returnNew, True); + method Action updateWithFunc(MapKeyIndex#(ky,ix) ki, vl value, function vl up(vl old_v, vl new_v), Bool insert) = + doUpdate(ki, value, up, insert); method Maybe#(vl) lookup(MapKeyIndex#(ky,ix) lu); Maybe#(vl) ret = Invalid; diff --git a/src_Core/RISCY_OOO/procs/lib/SplitLSQ.bsv b/src_Core/RISCY_OOO/procs/lib/SplitLSQ.bsv index 3a11112..6b95eed 100644 --- a/src_Core/RISCY_OOO/procs/lib/SplitLSQ.bsv +++ b/src_Core/RISCY_OOO/procs/lib/SplitLSQ.bsv @@ -2119,7 +2119,8 @@ module mkSplitLSQ(SplitLSQ); doAssert(ld_specBits_deqLd[deqP] == 0, "at commit means zero spec bits"); end - if(isValid(ld_killed_deqLd[deqP])) begin + Bool killedLd = isValid(ld_killed_deqLd[deqP]); + if(killedLd) begin doAssert(ld_memFunc[deqP] == Ld && !ld_isMMIO_deqLd[deqP], "must be non-MMIO Ld"); doAssert(!isValid(ld_fault_deqLd[deqP]), "cannot have fault"); @@ -2127,11 +2128,15 @@ module mkSplitLSQ(SplitLSQ); "must be done"); doAssert(!ld_waitWPResp_deqLd[deqP], "cannot wait for wrong path resp"); - ldKillMap.updateWithFunc(unpack(ld_pc_hash[deqP]), 1, boundedPlus); // Update predictor. - end else if ((rand_count & (512-1)) == 0) begin - // "randomly" evict trained entries in the store-to-load aliasing predictor. - ldKillMap.update(unpack(ld_pc_hash[deqP]), minBound); end + Bool rand_inv = (rand_count & (512-1)) == 0; + Bool waited = ld_waitForOlderSt[deqP]; // Don't negative train if we waited for older stores. + // Update predictor. + ldKillMap.updateWithFunc(unpack(ld_pc_hash[deqP]), // Key + waited ? 0:1, // value; don't train if we waited. + killedLd ? boundedPlus:boundedMinus, // function to combine this value with existing + killedLd || rand_inv // insert if doesn't exist + ); // remove the entry ld_valid_deqLd[deqP] <= False;