summaryrefslogtreecommitdiff
path: root/rtl
diff options
context:
space:
mode:
authorAlejandro Soto <alejandro@34project.org>2023-11-18 20:16:26 -0600
committerAlejandro Soto <alejandro@34project.org>2023-11-18 20:16:26 -0600
commitbc56985a67d2cec759cbad8a0de2c6f54b6818cd (patch)
tree1f78c174a16c4ca836dcbf2e46b1a113b61fa76e /rtl
parente573ddb5814ac1c9cafd6376c3052ca01dddeae8 (diff)
rtl/gfx: fix scanout off-by-ones
Diffstat (limited to '')
-rw-r--r--rtl/gfx/gfx_scanout.sv29
-rw-r--r--rtl/gfx/gfx_scanout_dac.sv2
2 files changed, 19 insertions, 12 deletions
diff --git a/rtl/gfx/gfx_scanout.sv b/rtl/gfx/gfx_scanout.sv
index 074a75a..a7aa71a 100644
--- a/rtl/gfx/gfx_scanout.sv
+++ b/rtl/gfx/gfx_scanout.sv
@@ -27,22 +27,25 @@ module gfx_scanout
);
logic commit, effective_mask, flush, mask_fifo_out, dac_ready,
- fb_ready, mask_fifo_ready, fb_fifo_valid, mask_fifo_valid, pop, put, put_mask;
+ fb_ready, mask_fifo_ready, fb_fifo_valid, mask_fifo_valid,
+ pop, put, put_mask, next_vsync, start_vsync, wait_vsync;
mem_word fb_fifo_out;
- half_coord mask_in_addr, mask_hold_addr, mask_out_addr, max_addr, commit_addr;
+ half_coord commit_addr, mask_in_addr, mask_out_addr, mask_hold_addr, max_addr;
assign mask_addr = mask_in_addr[$bits(mask_in_addr) - 1:$bits(mask_in_addr) - $bits(mask_addr)];
assign max_addr[0] = 1;
assign max_addr[$bits(max_addr) - 1:1] = `GFX_X_RES * `GFX_Y_RES - 1;
assign fb_ready = !fb_read || !fb_waitrequest;
+ assign next_vsync = commit && start_vsync;
+ assign start_vsync = mask_hold_addr == max_addr;
assign effective_mask = mask || !enable_clear;
gfx_flush_flow #(.STAGES(`GFX_MASK_STAGES)) mask_flow
(
- .in_valid(1),
- .out_ready(fb_ready && mask_fifo_ready),
+ .in_valid(!wait_vsync),
+ .out_ready(fb_ready && mask_fifo_ready && !next_vsync),
.out_valid(pop),
.*
);
@@ -97,24 +100,28 @@ module gfx_scanout
if (!rst_n) begin
put <= 0;
fb_read <= 0;
+ wait_vsync <= 0;
commit_addr <= 0;
mask_in_addr <= 0;
end else begin
mask_in_addr <= mask_in_addr + 1;
- if (mask_in_addr == max_addr)
- mask_in_addr <= 0;
- if (flush)
+ if (flush || wait_vsync)
mask_in_addr <= commit_addr;
- if (commit)
- commit_addr <= mask_hold_addr;
+ if (commit) begin
+ wait_vsync <= start_vsync;
+ commit_addr <= start_vsync ? 0 : mask_out_addr;
+ end
if (fb_ready)
- fb_read <= mask_fifo_ready && pop && effective_mask;
+ fb_read <= mask_fifo_ready && pop && !next_vsync && effective_mask;
if (mask_fifo_ready)
- put <= fb_ready && pop;
+ put <= fb_ready && pop && !next_vsync;
+
+ if (vsync)
+ wait_vsync <= 0;
end
always_ff @(posedge clk) begin
diff --git a/rtl/gfx/gfx_scanout_dac.sv b/rtl/gfx/gfx_scanout_dac.sv
index c8fe218..ba8b0b7 100644
--- a/rtl/gfx/gfx_scanout_dac.sv
+++ b/rtl/gfx/gfx_scanout_dac.sv
@@ -87,7 +87,7 @@ module gfx_scanout_dac
end else begin
vsync <= 0;
if (in_ready && dac_valid) begin
- vsync <= scan_endofpacket;
+ vsync <= skid_in.endofpacket;
dac_valid <= 0;
end