From a76af876a13347456304df4ab8142c7b33f7286a Mon Sep 17 00:00:00 2001 From: Jessica Clarke Date: Wed, 15 Apr 2020 16:45:28 +0100 Subject: [PATCH] MMIOPlatform.bsv: Discard write response for uncached AMOs Otherwise, the next MMIO access will see the 0 from the write response instead of its response, and every subsequent access will see the previous's response, further accumulating if more uncached AMOs are performed. --- src_Core/CPU/MMIOPlatform.bsv | 14 ++++++++++++-- 1 file changed, 12 insertions(+), 2 deletions(-) diff --git a/src_Core/CPU/MMIOPlatform.bsv b/src_Core/CPU/MMIOPlatform.bsv index 8273326..ded8dbe 100644 --- a/src_Core/CPU/MMIOPlatform.bsv +++ b/src_Core/CPU/MMIOPlatform.bsv @@ -282,6 +282,10 @@ module mkMMIOPlatform #(Vector#(CoreNum, MMIOCoreToPlatform) cores, // CRs, we record the AMO resp at processing time Reg#(Data) amoResp <- mkRegU; + // For AMOs to the fabric, we end up with read and write responses, and need + // to discard the latter. This tracks which of the two we're waiting for. + Reg#(Bool) amoWaitWriteResp <- mkRegU; + // we increment mtime periodically Reg#(Bit#(TLog#(CyclesPerTimeInc))) cycle <- mkReg(0); @@ -928,6 +932,7 @@ module mkMMIOPlatform #(Vector#(CoreNum, MMIOCoreToPlatform) cores, let req = MMIOCRq {addr:addr, func:tagged Ld, byteEn:?, data:?}; mmio_fabric_adapter_core_side.request.put (req); state <= WaitResp; + amoWaitWriteResp <= False; if (verbosity > 0) begin $display ("MMIOPlatform.rl_mmio_to_fabric_amo_req: addr 0x%0h", addr); @@ -941,7 +946,11 @@ module mkMMIOPlatform #(Vector#(CoreNum, MMIOCoreToPlatform) cores, &&& isAmo); MMIODataPRs dprs <- mmio_fabric_adapter_core_side.response.get; - if (! dprs.valid) begin + if (amoWaitWriteResp) begin + // Discard the write response; we're now ready for another request + state <= SelectReq; + end + else if (! dprs.valid) begin // Access fault let prs = tagged DataAccess dprs; cores[reqCore].pRs.enq (prs); @@ -958,7 +967,8 @@ module mkMMIOPlatform #(Vector#(CoreNum, MMIOCoreToPlatform) cores, let prs = tagged DataAccess (MMIODataPRs { valid: True, data: ld_val }); cores[reqCore].pRs.enq (prs); - state <= SelectReq; + // Stay in WaitResp but wait to discard the write response + amoWaitWriteResp <= True; if (verbosity > 1) begin $display ("MMIO_Platform.rl_mmio_from_fabric_amo_rsp: addr 0x%0h, size %0d, amofunc %0d",