Border matching seems to be mostly working
This commit is contained in:
parent
f9c31078d9
commit
aeda28a467
5 changed files with 284 additions and 159 deletions
|
|
@ -42,7 +42,7 @@
|
|||
<Option Name="IPUserFilesDir" Val="$PIPUSERFILESDIR"/>
|
||||
<Option Name="IPStaticSourceDir" Val="$PIPUSERFILESDIR/ipstatic"/>
|
||||
<Option Name="EnableBDX" Val="FALSE"/>
|
||||
<Option Name="WTXSimLaunchSim" Val="560"/>
|
||||
<Option Name="WTXSimLaunchSim" Val="588"/>
|
||||
<Option Name="WTModelSimLaunchSim" Val="0"/>
|
||||
<Option Name="WTQuestaLaunchSim" Val="0"/>
|
||||
<Option Name="WTIesLaunchSim" Val="0"/>
|
||||
|
|
|
|||
|
|
@ -23,6 +23,8 @@ module window_matcher(
|
|||
output [11:0] win_h_dbg,
|
||||
output reg [11:0] win_w,
|
||||
output reg [11:0] win_h,
|
||||
output reg [11:0] win_right,
|
||||
output reg [11:0] win_bottom,
|
||||
output reg win_locked,
|
||||
input [7:0] win_red, [7:0] win_green, [7:0] win_blue,
|
||||
|
||||
|
|
@ -312,6 +314,8 @@ module window_matcher(
|
|||
win_h <= 0;
|
||||
win_x <= 0;
|
||||
win_y <= 0;
|
||||
win_right <= 0;
|
||||
win_bottom <= 0;
|
||||
|
||||
end else begin
|
||||
if (in_vsync_reg == 0 && in_vsync == 1) begin
|
||||
|
|
@ -322,11 +326,16 @@ module window_matcher(
|
|||
win_h <= win_h_int;
|
||||
win_x <= win_x_int;
|
||||
win_y <= win_y_int;
|
||||
win_right <= win_x_int + win_w_int + 1;
|
||||
win_bottom <= win_y_int + win_h_int + 1;
|
||||
|
||||
end else begin
|
||||
win_w <= 0;
|
||||
win_h <= 0;
|
||||
win_x <= 0;
|
||||
win_y <= 0;
|
||||
win_right <= 0;
|
||||
win_bottom <= 0;
|
||||
end
|
||||
end
|
||||
end
|
||||
|
|
@ -334,48 +343,33 @@ module window_matcher(
|
|||
|
||||
|
||||
/* Window H/VSYNC outputs */
|
||||
reg [11:0] win_blank_ctr;
|
||||
reg [11:0] win_hsync_ctr;
|
||||
reg win_hactive;
|
||||
|
||||
always @(posedge clk) begin
|
||||
if (rst) begin
|
||||
win_blank <= 1;
|
||||
win_hactive <= 0;
|
||||
win_blank_ctr <= 0;
|
||||
win_hsync_ctr <= 0;
|
||||
|
||||
end else begin
|
||||
if (win_locked) begin
|
||||
/* hsync */
|
||||
if (scan_x == win_x && win_hactive) begin
|
||||
win_blank <= 0;
|
||||
win_blank_ctr <= 1;
|
||||
end
|
||||
|
||||
if (win_blank == 0) begin
|
||||
win_blank_ctr <= win_blank_ctr + 1;
|
||||
end
|
||||
|
||||
if (win_blank_ctr == win_w || in_blank) begin
|
||||
if (scan_x == win_right || in_blank) begin
|
||||
win_blank <= 1;
|
||||
win_blank_ctr <= 0;
|
||||
end
|
||||
|
||||
if (win_hactive && in_blank_reg && !in_blank) begin
|
||||
win_hsync_ctr <= win_hsync_ctr + 1;
|
||||
end
|
||||
|
||||
if (scan_y == win_y) begin
|
||||
win_hactive <= 1;
|
||||
end
|
||||
|
||||
if (win_hsync_ctr == win_h && !in_blank_reg && in_blank) begin
|
||||
if (scan_y == win_bottom && !in_blank_reg && in_blank) begin
|
||||
win_hactive <= 0;
|
||||
end
|
||||
|
||||
if (in_vsync_reg == 1 && in_vsync == 0) begin
|
||||
win_hsync_ctr <= 0;
|
||||
win_hactive <= 0;
|
||||
end
|
||||
end
|
||||
|
|
@ -383,44 +377,34 @@ module window_matcher(
|
|||
end
|
||||
|
||||
/* Border matching */
|
||||
localparam BORDER_COLOR = 24'h162329,
|
||||
BACKGROUND_COLOR = 24'hd61ca1,
|
||||
FONT_FG_COLOR = 24'he1e31b;
|
||||
localparam BORDER_COLOR = 24'h000000,
|
||||
BACKGROUND_COLOR = 24'hd020a0,
|
||||
FONT_FG_COLOR = 24'he0e010;
|
||||
wire is_border_px = (in_pxd_unfucked & 24'hf0f0f0) == (BORDER_COLOR & 24'hf0f0f0);
|
||||
wire is_bg_px = (in_pxd_unfucked & 24'hf0f0f0) == (BACKGROUND_COLOR & 24'hf0f0f0) ||
|
||||
(in_pxd_unfucked & 24'hf0f0f0) == (FONT_FG_COLOR & 24'hf0f0f0);
|
||||
reg [11:0] border_right;
|
||||
reg [11:0] border_bottom;
|
||||
reg row_valid_border_h, row_valid_border_v;
|
||||
reg valid_border;
|
||||
wire [11:0] border_top = win_y - 2;
|
||||
wire [11:0] border_left = win_x - 2;
|
||||
localparam BSTATE_WAITING = 15'b000000000000001,
|
||||
BSTATE_TOP1 = 15'b000000000000010,
|
||||
BSTATE_TOP1_RIGHT = 15'b000000000000100,
|
||||
BSTATE_TOP2_LEFT = 15'b000000000001000,
|
||||
BSTATE_TOP2 = 15'b000000000010000,
|
||||
BSTATE_TOP2_RIGHT = 15'b000000000100000,
|
||||
BSTATE_MID_LEFT = 15'b000000001000000,
|
||||
BSTATE_MID_L1 = 15'b000000010000000,
|
||||
BSTATE_MID_L2 = 15'b000000010000000,
|
||||
BSTATE_MID_CENTER = 15'b000000010000000,
|
||||
BSTATE_MID_R1 = 15'b000000010000000,
|
||||
BSTATE_MID_R2 = 15'b000000010000000,
|
||||
BSTATE_MID_RIGHT = 15'b000000100000000,
|
||||
BSTATE_BOT1_LEFT = 15'b000001000000000,
|
||||
BSTATE_BOT1 = 15'b000010000000000,
|
||||
BSTATE_BOT1_RIGHT = 15'b000100000000000,
|
||||
BSTATE_BOT2 = 15'b001000000000000,
|
||||
BSTATE_FINISHED = 15'b010000000000000;
|
||||
BSTATE_INVALID = 15'b100000000000000;
|
||||
wire [14:0] bstate;
|
||||
wire [11:0] border_w = border_right - win_x - 1;
|
||||
wire [11:0] border_h = border_bottom - win_y;
|
||||
|
||||
localparam BSTATE_WAITING = 15'b000000000000001, /* 0001 */
|
||||
BSTATE_FIRST_LINE = 15'b000000000000010, /* 0002 */
|
||||
BSTATE_FIRST_LINE_RIGHT = 15'b000000000000100, /* 0004 */
|
||||
BSTATE_FIRST_LINE_DONE = 15'b000000000001000, /* 0008 */
|
||||
BSTATE_WIN_LINE_WAIT = 15'b000000000010000, /* 0010 */
|
||||
BSTATE_WIN_LINE_WIN = 15'b000000000100000, /* 0020 */
|
||||
BSTATE_WIN_LINE_BUSY = 15'b000000001000000, /* 0040 */
|
||||
BSTATE_WIN_LINE_DONE = 15'b000000010000000, /* 0080 */
|
||||
BSTATE_LINE_WAIT = 15'b000000100000000, /* 0100 */
|
||||
BSTATE_LINE_BUSY = 15'b000001000000000, /* 0200 */
|
||||
BSTATE_LINE_DONE = 15'b000010000000000, /* 0400 */
|
||||
BSTATE_DONE = 15'b000100000000000, /* 0800 */
|
||||
BSTATE_INVALID = 15'b100000000000000; /* 4000 */
|
||||
reg [14:0] bstate;
|
||||
|
||||
always @(posedge clk) begin
|
||||
if (rst || in_vsync || !win_locked || win_x < 2 || win_y < 2) begin
|
||||
row_valid_border_h <= 0;
|
||||
row_valid_border_v <= 0;
|
||||
valid_border <= 0;
|
||||
if (rst || in_vsync || !win_locked || win_x == 0 || win_y == 0) begin
|
||||
border_right <= 0;
|
||||
border_bottom <= 0;
|
||||
bstate <= BSTATE_WAITING;
|
||||
|
|
@ -428,87 +412,89 @@ module window_matcher(
|
|||
end else if (!in_blank) begin
|
||||
case (bstate)
|
||||
(BSTATE_WAITING): begin
|
||||
if (scan_x == border_left && scan_y == border_top) begin /* top left pixel of border */
|
||||
bstate <= is_border_px ? BSTATE_TOP1 : BSTATE_INVALID;
|
||||
if (scan_x == win_x && scan_y == win_y) begin
|
||||
bstate <= BSTATE_FIRST_LINE;
|
||||
end
|
||||
end
|
||||
(BSTATE_FIRST_LINE): begin
|
||||
if (scan_x == win_right) begin
|
||||
bstate <= is_bg_px ? BSTATE_FIRST_LINE_RIGHT : BSTATE_INVALID;
|
||||
end
|
||||
end
|
||||
(BSTATE_TOP1): begin
|
||||
if (!is_border_px) begin
|
||||
(BSTATE_FIRST_LINE_RIGHT): begin
|
||||
if (!is_bg_px) begin
|
||||
bstate <= is_border_px ? BSTATE_FIRST_LINE_DONE : BSTATE_INVALID;
|
||||
border_right <= scan_x;
|
||||
bstate <= BSTATE_TOP1_RIGHT;
|
||||
end
|
||||
end
|
||||
(BSTATE_TOP2_LEFT): begin
|
||||
if (scan_x == border_left) begin
|
||||
bstate <= is_border_px ? BSTATE_TOP2 : BSTATE_INVALID;
|
||||
(BSTATE_WIN_LINE_WAIT): begin
|
||||
if (scan_x == win_x) begin
|
||||
if (scan_y == win_bottom) begin
|
||||
bstate <= is_border_px ? BSTATE_LINE_BUSY : BSTATE_INVALID;
|
||||
end else begin
|
||||
bstate <= is_border_px ? BSTATE_WIN_LINE_WIN : BSTATE_INVALID;
|
||||
end
|
||||
end
|
||||
end
|
||||
(BSTATE_TOP2): begin
|
||||
(BSTATE_WIN_LINE_WIN): begin
|
||||
if (scan_x == win_right) begin
|
||||
if (is_border_px) begin
|
||||
bstate <= BSTATE_DONE;
|
||||
border_bottom = scan_y;
|
||||
end else begin
|
||||
bstate <= is_bg_px ? BSTATE_WIN_LINE_BUSY : BSTATE_INVALID;
|
||||
end
|
||||
end
|
||||
end
|
||||
(BSTATE_WIN_LINE_BUSY): begin
|
||||
if (scan_x == border_right) begin
|
||||
bstate <= BSTATE_TOP2_RIGHT;
|
||||
bstate <= is_border_px ? BSTATE_WIN_LINE_DONE : BSTATE_INVALID;
|
||||
end else begin
|
||||
bstate <= is_border_px ? BSTATE_TOP2 : BSTATE_INVALID;
|
||||
bstate <= is_bg_px ? BSTATE_WIN_LINE_BUSY : BSTATE_INVALID;
|
||||
end
|
||||
end
|
||||
(BSTATE_MID_LEFT): begin
|
||||
if (scan_x == border_left) begin
|
||||
bstate <= is_border_px ? BSTATE_MID_L1 : BSTATE_INVALID;
|
||||
(BSTATE_LINE_WAIT): begin
|
||||
if (scan_x == win_x) begin
|
||||
bstate <= is_border_px ? BSTATE_LINE_BUSY : BSTATE_INVALID;
|
||||
end
|
||||
end
|
||||
(BSTATE_MID_L1): begin
|
||||
bstate <= is_border_px ? BSTATE_MID_L2 : BSTATE_INVALID;
|
||||
end
|
||||
(BSTATE_MID_L2): begin
|
||||
if (is_border_px) begin
|
||||
bstate <= BSTATE_BOT1;
|
||||
end else if (is_bg_px) begin
|
||||
bstate <= BSTATE_MID_C;
|
||||
end else begin
|
||||
bstate <= BSTATE_INVALID;
|
||||
end
|
||||
end
|
||||
(BSTATE_MID_C): begin
|
||||
if (is_border_px) begin
|
||||
bstate <= BSTATE_MID_R1;
|
||||
end else if (is_bg_px) begin
|
||||
bstate <= BSTATE_MID_C;
|
||||
end else begin
|
||||
bstate <= BSTATE_INVALID;
|
||||
end
|
||||
end
|
||||
(BSTATE_MID_R1): begin
|
||||
bstate <= is_border_px ? BSTATE_MID_R2 : BSTATE_INVALID;
|
||||
end
|
||||
(BSTATE_MID_R2): begin
|
||||
bstate <= (scan_x == border_right) ? BSTATE_MID_RIGHT : BSTATE_INVALID;
|
||||
end
|
||||
(BSTATE_BOT1): begin
|
||||
(BSTATE_LINE_BUSY): begin
|
||||
if (scan_x == border_right) begin
|
||||
bstate <= BSTATE_BOT1_RIGHT;
|
||||
bstate <= is_border_px ? BSTATE_LINE_DONE : BSTATE_INVALID;
|
||||
|
||||
end else begin
|
||||
bstate <= is_border_px ? BSTATE_BOT1 : BSTATE_INVALID;
|
||||
if (is_border_px) begin
|
||||
bstate <= BSTATE_DONE;
|
||||
border_bottom = scan_y;
|
||||
|
||||
end else begin
|
||||
bstate <= is_bg_px ? BSTATE_LINE_BUSY : BSTATE_INVALID;
|
||||
end
|
||||
end
|
||||
end
|
||||
(BSTATE_BOT2): begin
|
||||
if (scan_x == border_right) begin
|
||||
bstate <= BSTATE_BOT1_RIGHT;
|
||||
end else begin
|
||||
bstate <= is_border_px ? BSTATE_BOT1 : BSTATE_INVALID;
|
||||
end
|
||||
end
|
||||
(BSTATE_FINISHED): begin
|
||||
(BSTATE_DONE): begin
|
||||
/* do nothing, reset on next vsync. */
|
||||
end
|
||||
(BSTATE_INVALID): begin
|
||||
/* do nothing, reset on next vsync. */
|
||||
end
|
||||
endcase
|
||||
|
||||
end else begin /* blank */
|
||||
end else if (in_blank && !in_blank_reg) begin /* blank */
|
||||
case (bstate)
|
||||
(BSTATE_TOP1_RIGHT): bstate <= BSTATE_TOP2_LEFT;
|
||||
(BSTATE_TOP2_RIGHT): bstate <= BSTATE_MID_LEFT;
|
||||
(BSTATE_MID_RIGHT): bstate <= BSTATE_MID_LEFT;
|
||||
(BSTATE_BOT1_RIGHT): bstate <= BSTATE_BOT2_LEFT;
|
||||
(BSTATE_WAITING ): bstate <= BSTATE_WAITING;
|
||||
(BSTATE_FIRST_LINE ): bstate <= BSTATE_INVALID;
|
||||
(BSTATE_FIRST_LINE_RIGHT): bstate <= BSTATE_INVALID;
|
||||
(BSTATE_FIRST_LINE_DONE ): bstate <= BSTATE_WIN_LINE_WAIT;
|
||||
(BSTATE_WIN_LINE_WAIT ): bstate <= BSTATE_INVALID;
|
||||
(BSTATE_WIN_LINE_WIN ): bstate <= BSTATE_INVALID;
|
||||
(BSTATE_WIN_LINE_BUSY ): bstate <= BSTATE_INVALID;
|
||||
(BSTATE_WIN_LINE_DONE ): bstate <= BSTATE_WIN_LINE_WAIT;
|
||||
(BSTATE_LINE_WAIT ): bstate <= BSTATE_INVALID;
|
||||
(BSTATE_LINE_BUSY ): bstate <= BSTATE_INVALID;
|
||||
(BSTATE_LINE_DONE ): bstate <= BSTATE_LINE_WAIT;
|
||||
(BSTATE_DONE ): bstate <= BSTATE_DONE;
|
||||
(BSTATE_INVALID ): bstate <= BSTATE_INVALID;
|
||||
endcase
|
||||
end
|
||||
end
|
||||
|
|
|
|||
0
demo/fpga/test_bench/test_data/.gitkeep
Normal file
0
demo/fpga/test_bench/test_data/.gitkeep
Normal file
|
|
@ -60,6 +60,7 @@ module window_matcher_tb();
|
|||
end
|
||||
|
||||
`include "test_data/00WM_TEST_POS_LOADERS.v"
|
||||
`include "test_data/00WM_TEST_BORDER_LOADERS.v"
|
||||
|
||||
integer read_pos;
|
||||
reg [23:0] expected_data;
|
||||
|
|
@ -69,7 +70,8 @@ module window_matcher_tb();
|
|||
reg win_blank_exp_last, win_header_last;
|
||||
reg in_vsync_last;
|
||||
initial begin
|
||||
`include "test_data/00WM_TEST_POS_RUNNERS.v"
|
||||
//`include "test_data/00WM_TEST_POS_RUNNERS.v"
|
||||
`include "test_data/00WM_TEST_BORDER_RUNNERS.v"
|
||||
$finish;
|
||||
end
|
||||
|
||||
|
|
|
|||
File diff suppressed because one or more lines are too long
Loading…
Add table
Add a link
Reference in a new issue