Skip to content

Commit 5683774

Browse files
committed
Eliminate read access latency of rv_timer
Make the read access latency timer of the rv_timer configurable by the parent module; support either same cycle (0) or a single-cycle delay (as before). Switch to AccessLatency of 0. Since the tlul_adapter_reg always introduces a cycle delay from accepting a transaction (a_valid & a_ready) and sending the data (d_valid), there is already a register delay (storage) on the read data path. This change should therefore reduce the resource requirements slightly.
1 parent 2dacd2c commit 5683774

File tree

2 files changed

+39
-24
lines changed

2 files changed

+39
-24
lines changed

rtl/system/rv_timer.sv

Lines changed: 33 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,9 @@ module rv_timer #(
1010
// Bus data width (must be 32)
1111
parameter int unsigned DataWidth = 32,
1212
// Bus address width
13-
parameter int unsigned AddressWidth = 32
13+
parameter int unsigned AddressWidth = 32,
14+
// Number of cycles by which the read data lags the request (must be 0 or 1)
15+
parameter int unsigned AccessLatency = 1
1416
) (
1517
input logic clk_i,
1618
input logic rst_ni,
@@ -45,9 +47,8 @@ module rv_timer #(
4547
logic [TW-1:0] mtime_q, mtime_d, mtime_inc;
4648
logic [TW-1:0] mtimecmp_q, mtimecmp_d;
4749
logic interrupt_q, interrupt_d;
48-
logic error_q, error_d;
49-
logic [DataWidth-1:0] rdata_q, rdata_d;
50-
logic rvalid_q;
50+
logic error_d;
51+
logic [DataWidth-1:0] rdata_d;
5152

5253
// Global write enable for all registers
5354
assign timer_we = timer_req_i & timer_we_i;
@@ -121,31 +122,43 @@ module rv_timer #(
121122
endcase
122123
end
123124

124-
// error_q and rdata_q are only valid when rvalid_q is high
125-
always_ff @(posedge clk_i) begin
126-
if (timer_req_i) begin
127-
rdata_q <= rdata_d;
128-
error_q <= error_d;
125+
if (AccessLatency == 1) begin : gen_access_latency1
126+
logic [DataWidth-1:0] rdata_q;
127+
logic error_q;
128+
logic rvalid_q;
129+
130+
// error_q and rdata_q are only valid when rvalid_q is high
131+
always_ff @(posedge clk_i) begin
132+
if (timer_req_i) begin
133+
rdata_q <= rdata_d;
134+
error_q <= error_d;
135+
end
129136
end
130-
end
131137

132-
assign timer_rdata_o = rdata_q;
138+
assign timer_rdata_o = rdata_q;
133139

134-
// Read data is always valid one cycle after a request
135-
always_ff @(posedge clk_i or negedge rst_ni) begin
136-
if (!rst_ni) begin
137-
rvalid_q <= 1'b0;
138-
end else begin
139-
rvalid_q <= timer_req_i;
140+
// Read data is always valid one cycle after a request
141+
always_ff @(posedge clk_i or negedge rst_ni) begin
142+
if (!rst_ni) begin
143+
rvalid_q <= 1'b0;
144+
end else begin
145+
rvalid_q <= timer_req_i;
146+
end
140147
end
141-
end
142148

143-
assign timer_rvalid_o = rvalid_q;
144-
assign timer_err_o = error_q;
149+
assign timer_rvalid_o = rvalid_q;
150+
assign timer_err_o = error_q;
151+
end else begin : gen_access_latency0
152+
// Zero cycle latency; other cases caught by assertion below.
153+
assign timer_rdata_o = rdata_d;
154+
assign timer_rvalid_o = timer_req_i;
155+
assign timer_err_o = error_d;
156+
end
145157

146158
bit [DataWidth-ADDR_OFFSET:0] unused_timer_addr;
147159
assign unused_timer_addr = timer_addr_i[DataWidth-1:ADDR_OFFSET-1];
148160

149161
// Assertions
150162
`ASSERT_INIT(param_legal, DataWidth == 32)
163+
`ASSERT_INIT(AllowedLatency_A, AccessLatency inside {0, 1})
151164
endmodule : rv_timer

rtl/system/sonata_system.sv

Lines changed: 6 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -130,6 +130,7 @@ module sonata_system
130130
localparam int unsigned TotalSpiNum = SPI_NUM + FixedSpiNum; // The total number of SPI devices
131131
localparam int unsigned FixedGpioNum = 1; // Number of GPIO instances that don't pass through the pinmux
132132
localparam int unsigned TotalGpioNum = GPIO_NUM + FixedGpioNum; // The total number of GPIO instances
133+
localparam int unsigned TAccessLatency = 0; // Cycles of read data latency.
133134

134135
// The number of data bits controlled by each mask bit; since the CPU requires
135136
// only byte level access, explicitly grouping the data bits makes the inferred
@@ -618,8 +619,8 @@ module sonata_system
618619
assign device_addr[DbgDev][BusAddrWidth-1:DRegAddrWidth] = tl_ifetch_pkg::ADDR_SPACE_DBG_DEV[BusAddrWidth-1:DRegAddrWidth];
619620

620621
tlul_adapter_reg #(
621-
.RegAw ( TRegAddrWidth ),
622-
.AccessLatency ( 1 )
622+
.RegAw ( TRegAddrWidth ),
623+
.AccessLatency ( TAccessLatency )
623624
) timer_device_adapter (
624625
.clk_i (clk_sys_i),
625626
.rst_ni (rst_sys_ni),
@@ -1151,8 +1152,9 @@ module sonata_system
11511152

11521153
// RISC-V timer.
11531154
rv_timer #(
1154-
.DataWidth ( BusDataWidth ),
1155-
.AddressWidth ( BusAddrWidth )
1155+
.DataWidth ( BusDataWidth ),
1156+
.AddressWidth ( BusAddrWidth ),
1157+
.AccessLatency( TAccessLatency )
11561158
) u_rv_timer (
11571159
.clk_i (clk_sys_i),
11581160
.rst_ni (rst_sys_ni),

0 commit comments

Comments
 (0)