From 156fada616f38f893408067a0a098ed15a45e5d0 Mon Sep 17 00:00:00 2001 From: Alex Forencich Date: Sun, 21 Mar 2021 12:04:30 -0700 Subject: [PATCH] Store commands currently being processed so they can be released when the processing coroutines are killed --- cocotbext/axi/axi_master.py | 44 ++++++++++++++++++++++++++++++++++++ cocotbext/axi/axil_master.py | 44 ++++++++++++++++++++++++++++++++++++ 2 files changed, 88 insertions(+) diff --git a/cocotbext/axi/axi_master.py b/cocotbext/axi/axi_master.py index 8efe918..b7f7c73 100644 --- a/cocotbext/axi/axi_master.py +++ b/cocotbext/axi/axi_master.py @@ -63,6 +63,7 @@ class AxiMasterWrite(Reset): self.b_channel = AxiBSink(bus.b, clock, reset, reset_active_level) self.write_command_queue = Queue() + self.current_write_command = None self.write_resp_queue = Queue() self.id_count = 2**len(self.aw_channel.bus.awid) @@ -70,6 +71,7 @@ class AxiMasterWrite(Reset): self.active_id = Counter() self.int_write_resp_command_queue = Queue() + self.current_write_resp_command = None self.int_write_resp_queue_list = [Queue() for k in range(self.id_count)] self.in_flight_operations = 0 @@ -223,12 +225,26 @@ class AxiMasterWrite(Reset): if cmd.event: cmd.event.set(None) + if self.current_write_command: + cmd = self.current_write_command + self.current_write_command = None + self.log.warning("Flushed write operation during reset: %s", cmd) + if cmd.event: + cmd.event.set(None) + while not self.int_write_resp_command_queue.empty(): cmd = self.int_write_resp_command_queue.get_nowait() self.log.warning("Flushed write operation during reset: %s", cmd) if cmd.event: cmd.event.set(None) + if self.current_write_resp_command: + cmd = self.current_write_resp_command + self.current_write_resp_command = None + self.log.warning("Flushed write operation during reset: %s", cmd) + if cmd.event: + cmd.event.set(None) + while not self.write_resp_queue.empty(): resp = self.write_resp_queue.get_nowait() self.log.warning("Flushed write response during reset: %s", resp) @@ -239,6 +255,7 @@ class AxiMasterWrite(Reset): async def _process_write(self): while True: cmd = await self.write_command_queue.get() + self.current_write_command = cmd num_bytes = 2**cmd.size @@ -339,9 +356,12 @@ class AxiMasterWrite(Reset): resp_cmd = AxiWriteRespCmd(cmd.address, len(cmd.data), cmd.size, cycles, cmd.prot, burst_list, cmd.event) await self.int_write_resp_command_queue.put(resp_cmd) + self.current_write_command = None + async def _process_write_resp(self): while True: cmd = await self.int_write_resp_command_queue.get() + self.current_write_resp_command = cmd resp = AxiResp.OKAY user = [] @@ -386,6 +406,8 @@ class AxiMasterWrite(Reset): else: self.write_resp_queue.put_nowait(write_resp) + self.current_write_resp_command = None + self.in_flight_operations -= 1 if self.in_flight_operations == 0: @@ -405,6 +427,7 @@ class AxiMasterRead(Reset): self.r_channel = AxiRSink(bus.r, clock, reset, reset_active_level) self.read_command_queue = Queue() + self.current_read_command = None self.read_data_queue = Queue() self.id_count = 2**len(self.ar_channel.bus.arid) @@ -412,6 +435,7 @@ class AxiMasterRead(Reset): self.active_id = Counter() self.int_read_resp_command_queue = Queue() + self.current_read_resp_command = None self.int_read_resp_queue_list = [Queue() for k in range(self.id_count)] self.in_flight_operations = 0 @@ -557,12 +581,26 @@ class AxiMasterRead(Reset): if cmd.event: cmd.event.set(None) + if self.current_read_command: + cmd = self.current_read_command + self.current_read_command = None + self.log.warning("Flushed read operation during reset: %s", cmd) + if cmd.event: + cmd.event.set(None) + while not self.int_read_resp_command_queue.empty(): cmd = self.int_read_resp_command_queue.get_nowait() self.log.warning("Flushed read operation during reset: %s", cmd) if cmd.event: cmd.event.set(None) + if self.current_read_resp_command: + cmd = self.current_read_resp_command + self.current_read_resp_command = None + self.log.warning("Flushed read operation during reset: %s", cmd) + if cmd.event: + cmd.event.set(None) + while not self.read_data_queue.empty(): resp = self.read_data_queue.get_nowait() self.log.warning("Flushed read response during reset: %s", resp) @@ -573,6 +611,7 @@ class AxiMasterRead(Reset): async def _process_read(self): while True: cmd = await self.read_command_queue.get() + self.current_read_command = cmd num_bytes = 2**cmd.size @@ -632,9 +671,12 @@ class AxiMasterRead(Reset): resp_cmd = AxiReadRespCmd(cmd.address, cmd.length, cmd.size, cycles, cmd.prot, burst_list, cmd.event) await self.int_read_resp_command_queue.put(resp_cmd) + self.current_read_command = None + async def _process_read_resp(self): while True: cmd = await self.int_read_resp_command_queue.get() + self.current_read_resp_command = cmd num_bytes = 2**cmd.size @@ -711,6 +753,8 @@ class AxiMasterRead(Reset): else: self.read_data_queue.put_nowait(read_resp) + self.current_read_resp_command = None + self.in_flight_operations -= 1 if self.in_flight_operations == 0: diff --git a/cocotbext/axi/axil_master.py b/cocotbext/axi/axil_master.py index 0558cca..d305a5c 100644 --- a/cocotbext/axi/axil_master.py +++ b/cocotbext/axi/axil_master.py @@ -59,9 +59,11 @@ class AxiLiteMasterWrite(Reset): self.b_channel = AxiLiteBSink(bus.b, clock, reset, reset_active_level) self.write_command_queue = Queue() + self.current_write_command = None self.write_resp_queue = Queue() self.int_write_resp_command_queue = Queue() + self.current_write_resp_command = None self.in_flight_operations = 0 self._idle = Event() @@ -166,12 +168,26 @@ class AxiLiteMasterWrite(Reset): if cmd.event: cmd.event.set(None) + if self.current_write_command: + cmd = self.current_write_command + self.current_write_command = None + self.log.warning("Flushed write operation during reset: %s", cmd) + if cmd.event: + cmd.event.set(None) + while not self.int_write_resp_command_queue.empty(): cmd = self.int_write_resp_command_queue.get_nowait() self.log.warning("Flushed write operation during reset: %s", cmd) if cmd.event: cmd.event.set(None) + if self.current_write_resp_command: + cmd = self.current_write_resp_command + self.current_write_resp_command = None + self.log.warning("Flushed write operation during reset: %s", cmd) + if cmd.event: + cmd.event.set(None) + while not self.write_resp_queue.empty(): resp = self.write_resp_queue.get_nowait() self.log.warning("Flushed write response during reset: %s", resp) @@ -182,6 +198,7 @@ class AxiLiteMasterWrite(Reset): async def _process_write(self): while True: cmd = await self.write_command_queue.get() + self.current_write_command = cmd word_addr = (cmd.address // self.byte_width) * self.byte_width @@ -229,9 +246,12 @@ class AxiLiteMasterWrite(Reset): await self.aw_channel.send(aw) await self.w_channel.send(w) + self.current_write_command = None + async def _process_write_resp(self): while True: cmd = await self.int_write_resp_command_queue.get() + self.current_write_resp_command = cmd resp = AxiResp.OKAY @@ -253,6 +273,8 @@ class AxiLiteMasterWrite(Reset): else: self.write_resp_queue.put_nowait(write_resp) + self.current_write_resp_command = None + self.in_flight_operations -= 1 if self.in_flight_operations == 0: @@ -272,9 +294,11 @@ class AxiLiteMasterRead(Reset): self.r_channel = AxiLiteRSink(bus.r, clock, reset, reset_active_level) self.read_command_queue = Queue() + self.current_read_command = None self.read_data_queue = Queue() self.int_read_resp_command_queue = Queue() + self.current_read_resp_command = None self.in_flight_operations = 0 self._idle = Event() @@ -376,12 +400,26 @@ class AxiLiteMasterRead(Reset): if cmd.event: cmd.event.set(None) + if self.current_read_command: + cmd = self.current_read_command + self.current_read_command = None + self.log.warning("Flushed read operation during reset: %s", cmd) + if cmd.event: + cmd.event.set(None) + while not self.int_read_resp_command_queue.empty(): cmd = self.int_read_resp_command_queue.get_nowait() self.log.warning("Flushed read operation during reset: %s", cmd) if cmd.event: cmd.event.set(None) + if self.current_read_resp_command: + cmd = self.current_read_resp_command + self.current_read_resp_command = None + self.log.warning("Flushed read operation during reset: %s", cmd) + if cmd.event: + cmd.event.set(None) + while not self.read_data_queue.empty(): resp = self.read_data_queue.get_nowait() self.log.warning("Flushed read response during reset: %s", resp) @@ -392,6 +430,7 @@ class AxiLiteMasterRead(Reset): async def _process_read(self): while True: cmd = await self.read_command_queue.get() + self.current_read_command = cmd word_addr = (cmd.address // self.byte_width) * self.byte_width @@ -410,9 +449,12 @@ class AxiLiteMasterRead(Reset): await self.ar_channel.send(ar) + self.current_read_command = None + async def _process_read_resp(self): while True: cmd = await self.int_read_resp_command_queue.get() + self.current_read_resp_command = cmd start_offset = cmd.address % self.byte_width end_offset = ((cmd.address + cmd.length - 1) % self.byte_width) + 1 @@ -451,6 +493,8 @@ class AxiLiteMasterRead(Reset): else: self.read_data_queue.put_nowait(read_resp) + self.current_read_resp_command = None + self.in_flight_operations -= 1 if self.in_flight_operations == 0: