Fix byte-enable merging tag logic in the cache (with help from

Alexandre).
Also adjust priority in CCall exceptions.
This commit is contained in:
jon
2020-05-12 12:24:15 +01:00
parent 26919154db
commit 854151978e
5 changed files with 15 additions and 18 deletions

View File

@@ -118,20 +118,10 @@ function LineInstOffset getLineInstOffset(Addr a);
endfunction
function Line getUpdatedLine(Line curLine, LineByteEn wrBE, Line wrLine);
// handle data merge
Vector#(LineSzBytes, Bit#(8)) newDataVec = mergeDataBE(curLine.data, wrLine.data, wrBE);
// handle tag merge
Vector#(CLineNumMemTaggedData, MemTag) curTagVec = curLine.tag;
Vector#(CLineNumMemTaggedData, MemTag) wrTagVec = wrLine.tag;
function MemTag getNewTag(Integer i);
let res = curTagVec[i];
if (pack(wrBE[i]) == ~0) res = wrTagVec[i];
return res;
endfunction
Vector#(CLineNumMemTaggedData, MemTag) newTagVec = genWith(getNewTag);
// compose updated line
return CLine { tag: newTagVec
, data: unpack(pack(newDataVec)) };
let curLineMem = clineToMemTaggedDataVector(curLine);
let wrLineMem = clineToMemTaggedDataVector(wrLine);
let newLineMem = zipWith3(mergeMemTaggedDataBE, curLineMem, wrLineMem, wrBE);
return memTaggedDataVectorToCline(newLineMem);
endfunction
// calculate tag

View File

@@ -476,7 +476,7 @@ module mkMemExePipeline#(MemExeInput inIfc)(MemExePipeline);
Addr addr, MemDataByteEn be, MemTaggedData d);
Bit#(TLog#(MemDataBytes)) byteOffset = truncate(addr);
return tuple2(unpack(pack(be) << byteOffset), MemTaggedData {
tag: (byteOffset == 0) ? d.tag : False
tag: (byteOffset == 0 && be == replicate(True)) ? d.tag : False
, data: unpack(pack(d.data) << {byteOffset, 3'b0})});
endfunction
let {shiftBE, shiftData} = getShiftedBEData(getAddr(vaddr), origBE, toMemData);

View File

@@ -52,6 +52,12 @@ typedef struct {
Vector#(CLineNumMemTaggedData, MemTag) tag;
Vector#(CLineNumMemTaggedData, MemData) data;
} CLine deriving (Bits, Eq, FShow);
function Vector#(CLineNumMemTaggedData, MemTaggedData) clineToMemTaggedDataVector(CLine line);
function f(x,y) = MemTaggedData{tag: x, data: y};
return zipWith(f, line.tag, line.data);
endfunction
function CLine memTaggedDataVectorToCline(Vector#(CLineNumMemTaggedData, MemTaggedData) line) =
CLine{tag: map(getTag, line), data: map(getData, line)};
function Data getDataAt(CLine line, CLineDataSel sel);
Vector#(CLineNumData, Data) data = unpack(pack(line.data));
return data[sel];
@@ -184,4 +190,3 @@ instance Connectable#(FifoDeq#(t), FifoEnq#(t));
mkConnection(toGet(deq), toPut(enq));
endmodule
endinstance

View File

@@ -53,6 +53,8 @@ function Maybe#(CSR_XCapCause) capChecks(CapPipe a, CapPipe b, CapPipe ddc, CapC
result = e1(SealViolation);
else if (toCheck.src2_sealed && isValidCap(b) && !isSealed(b))
result = e2(SealViolation);
else if (toCheck.src1_type_not_reserved && !validAsType(a, zeroExtend(getType(a))))
result = e1(TypeViolation);
else if (toCheck.src1_src2_types_match && getType(a) != getType(b))
result = e1(TypeViolation);
else if (toCheck.src1_permit_ccall && !getHardPerms(a).permitCCall)
@@ -71,8 +73,6 @@ function Maybe#(CSR_XCapCause) capChecks(CapPipe a, CapPipe b, CapPipe ddc, CapC
result = e2(TypeViolation);
else if (toCheck.src2_addr_valid_type && !validAsType(b, truncate(getAddr(b))))
result = e2(LengthViolation);
else if (toCheck.src1_type_not_reserved && !validAsType(a, zeroExtend(getType(a))))
result = e1(TypeViolation);
else if (toCheck.src1_perm_subset_src2 && (getPerms(a) & getPerms(b)) != getPerms(a))
result = e2(SoftwarePermViolation);
else if (toCheck.src1_derivable && !isDerivable(a))

View File

@@ -43,6 +43,8 @@ typedef struct {
tag_t tag;
data_t data;
} TaggedData#(type tag_t, type data_t) deriving (Bits, FShow, Eq);
function tag_t getTag(TaggedData#(tag_t, data_t) td) = td.tag;
function data_t getData(TaggedData#(tag_t, data_t) td) = td.data;
typedef Vector#(2, Data) MemData;
typedef Bool MemTag;
typedef SizeOf#(MemData) MemDataSz;