mirror of
https://github.com/MiSTer-devel/Menu_MiSTer.git
synced 2026-04-19 03:04:31 +00:00
Update sys.
This commit is contained in:
174
sys/alsa.sv
174
sys/alsa.sv
@@ -1,7 +1,7 @@
|
||||
//============================================================================
|
||||
//
|
||||
// ALSA sound support for MiSTer
|
||||
// (c)2019 Sorgelig
|
||||
// (c)2019,2020 Alexey Melnikov
|
||||
//
|
||||
// This program is free software; you can redistribute it and/or modify it
|
||||
// under the terms of the GNU General Public License as published by the Free
|
||||
@@ -22,111 +22,135 @@
|
||||
module alsa
|
||||
(
|
||||
input reset,
|
||||
|
||||
output reg en_out,
|
||||
input en_in,
|
||||
|
||||
input ram_clk,
|
||||
output reg [28:0] ram_address,
|
||||
output reg [7:0] ram_burstcount,
|
||||
input ram_waitrequest,
|
||||
input [63:0] ram_readdata,
|
||||
input ram_readdatavalid,
|
||||
output reg ram_read,
|
||||
input clk,
|
||||
|
||||
output reg [31:3] ram_address,
|
||||
input [63:0] ram_data,
|
||||
output reg ram_req = 0,
|
||||
input ram_ready,
|
||||
|
||||
input spi_ss,
|
||||
input spi_sck,
|
||||
input spi_mosi,
|
||||
output spi_miso,
|
||||
|
||||
output reg [15:0] pcm_l,
|
||||
output reg [15:0] pcm_r
|
||||
);
|
||||
|
||||
reg spi_new = 0;
|
||||
reg [127:0] spi_data;
|
||||
reg [60:0] buf_info;
|
||||
reg [6:0] spicnt = 0;
|
||||
always @(posedge spi_sck, posedge spi_ss) begin
|
||||
reg [7:0] mosi;
|
||||
reg [6:0] spicnt = 0;
|
||||
reg [95:0] spi_data;
|
||||
|
||||
if(spi_ss) spicnt <= 0;
|
||||
else begin
|
||||
mosi <= {mosi[6:0],spi_mosi};
|
||||
|
||||
spi_data[{spicnt[6:3],~spicnt[2:0]}] <= spi_mosi;
|
||||
if(&spicnt) buf_info <= {spi_data[82:67],spi_data[50:35],spi_data[31:3]};
|
||||
spicnt <= spicnt + 1'd1;
|
||||
if(&spicnt[2:0]) begin
|
||||
spi_data[{spicnt[6:3],3'b000} +:8] <= {mosi[6:0],spi_mosi};
|
||||
spi_new <= &spicnt;
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
reg [31:0] buf_addr;
|
||||
reg [31:0] buf_len;
|
||||
reg [31:0] buf_wptr = 0;
|
||||
assign spi_miso = spi_out[{spicnt[4:3],~spicnt[2:0]}];
|
||||
|
||||
always @(posedge ram_clk) begin
|
||||
reg n1,n2,n3;
|
||||
reg [127:0] data1,data2;
|
||||
reg [31:0] spi_out = 0;
|
||||
always @(posedge clk) if(spi_ss) spi_out <= {buf_rptr, hurryup, 8'h00};
|
||||
|
||||
n1 <= spi_new;
|
||||
n2 <= n1;
|
||||
n3 <= n2;
|
||||
|
||||
data1 <= spi_data;
|
||||
reg [31:3] buf_addr;
|
||||
reg [18:3] buf_len;
|
||||
reg [18:3] buf_wptr = 0;
|
||||
|
||||
always @(posedge clk) begin
|
||||
reg [60:0] data1,data2;
|
||||
|
||||
data1 <= buf_info;
|
||||
data2 <= data1;
|
||||
|
||||
if(~n3 & n2) {buf_wptr,buf_len,buf_addr} <= data2[95:0];
|
||||
if(data2 == data1) {buf_wptr,buf_len,buf_addr} <= data2;
|
||||
end
|
||||
|
||||
reg [31:0] buf_rptr = 0;
|
||||
always @(posedge ram_clk) begin
|
||||
reg got_first = 0;
|
||||
reg ready = 0;
|
||||
reg ud = 0;
|
||||
reg [31:0] readdata;
|
||||
reg [2:0] hurryup = 0;
|
||||
reg [18:3] buf_rptr = 0;
|
||||
|
||||
if(~ram_waitrequest) ram_read <= 0;
|
||||
if(ram_readdatavalid && ram_burstcount) begin
|
||||
ram_burstcount <= 0;
|
||||
ready <= 1;
|
||||
readdata <= ud ? ram_readdata[63:32] : ram_readdata[31:0];
|
||||
if(buf_rptr[31:2] >= buf_len[31:2]) buf_rptr <= 0;
|
||||
end
|
||||
always @(posedge clk) begin
|
||||
reg [18:3] len = 0;
|
||||
reg [1:0] ready = 0;
|
||||
reg [63:0] readdata;
|
||||
reg got_first = 0;
|
||||
reg [7:0] ce_cnt = 0;
|
||||
reg [1:0] state = 0;
|
||||
|
||||
if(reset) {ready, got_first, ram_burstcount} <= 0;
|
||||
else
|
||||
if(buf_rptr[31:2] != buf_wptr[31:2]) begin
|
||||
if(~got_first) begin
|
||||
buf_rptr <= buf_wptr;
|
||||
got_first <= 1;
|
||||
end
|
||||
else
|
||||
if(!ram_burstcount && ~ram_waitrequest && ~ready && en_out == en_in) begin
|
||||
ram_address <= buf_addr[31:3] + buf_rptr[31:3];
|
||||
ud <= buf_rptr[2];
|
||||
ram_burstcount <= 1;
|
||||
ram_read <= 1;
|
||||
buf_rptr <= buf_rptr + 4;
|
||||
end
|
||||
if(reset) begin
|
||||
ready <= 0;
|
||||
ce_cnt <= 0;
|
||||
state <= 0;
|
||||
got_first <= 0;
|
||||
len <= 0;
|
||||
end
|
||||
else begin
|
||||
|
||||
if(ready & ce_48k) begin
|
||||
{pcm_r,pcm_l} <= readdata;
|
||||
ready <= 0;
|
||||
//ramp up
|
||||
if(len[18:14] && (hurryup < 1)) hurryup <= 1;
|
||||
if(len[18:16] && (hurryup < 2)) hurryup <= 2;
|
||||
if(len[18:17] && (hurryup < 4)) hurryup <= 4;
|
||||
|
||||
//ramp down
|
||||
if(!len[18:15] && (hurryup > 2)) hurryup <= 2;
|
||||
if(!len[18:13] && (hurryup > 1)) hurryup <= 1;
|
||||
if(!len[18:10]) hurryup <= 0;
|
||||
|
||||
if(ce_sample && ~&ce_cnt) ce_cnt <= ce_cnt + 1'd1;
|
||||
|
||||
case(state)
|
||||
0: if(!ce_sample) begin
|
||||
if(ready) begin
|
||||
if(ce_cnt) begin
|
||||
{readdata[31:0],pcm_r,pcm_l} <= readdata;
|
||||
ready <= ready - 1'd1;
|
||||
ce_cnt <= ce_cnt - 1'd1;
|
||||
end
|
||||
end
|
||||
else if(buf_rptr != buf_wptr) begin
|
||||
if(~got_first) begin
|
||||
buf_rptr <= buf_wptr;
|
||||
got_first <= 1;
|
||||
end
|
||||
else begin
|
||||
ram_address <= buf_addr + buf_rptr;
|
||||
ram_req <= ~ram_req;
|
||||
buf_rptr <= buf_rptr + 1'd1;
|
||||
len <= (buf_wptr < buf_rptr) ? (buf_len + buf_wptr - buf_rptr) : (buf_wptr - buf_rptr);
|
||||
state <= 1;
|
||||
end
|
||||
end
|
||||
else begin
|
||||
len <= 0;
|
||||
ce_cnt <= 0;
|
||||
hurryup <= 0;
|
||||
end
|
||||
end
|
||||
1: if(ram_ready) begin
|
||||
ready <= 2;
|
||||
readdata <= ram_data;
|
||||
if(buf_rptr >= buf_len) buf_rptr <= buf_rptr - buf_len;
|
||||
state <= 0;
|
||||
end
|
||||
endcase
|
||||
end
|
||||
|
||||
if(ce_48k) en_out <= ~en_out;
|
||||
end
|
||||
|
||||
reg ce_48k;
|
||||
always @(posedge ram_clk) begin
|
||||
reg [15:0] acc = 0;
|
||||
localparam F48K = 48000;
|
||||
localparam F50M = 50000000;
|
||||
|
||||
ce_48k <= 0;
|
||||
acc <= acc + 16'd48;
|
||||
if(acc >= 50000) begin
|
||||
acc <= acc - 16'd50000;
|
||||
ce_48k <= 1;
|
||||
reg ce_sample;
|
||||
always @(posedge clk) begin
|
||||
reg [31:0] acc = 0;
|
||||
|
||||
ce_sample <= 0;
|
||||
acc <= acc + F48K + {hurryup,6'd0};
|
||||
if(acc >= F50M) begin
|
||||
acc <= acc - F50M;
|
||||
ce_sample <= 1;
|
||||
end
|
||||
end
|
||||
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
//============================================================================
|
||||
//
|
||||
// Copyright (C) 2017-2019 Sorgelig
|
||||
// Copyright (C) 2017-2020 Sorgelig
|
||||
//
|
||||
//============================================================================
|
||||
|
||||
@@ -10,8 +10,9 @@
|
||||
// 8 : 3R 3G 2B
|
||||
// 9 : 3R 3G 3B
|
||||
// 12 : 4R 4G 4B
|
||||
// 24 : 8R 8G 8B
|
||||
|
||||
module arcade_rotate_fx #(parameter WIDTH=320, HEIGHT=240, DW=8, GAMMA=1)
|
||||
module arcade_video #(parameter WIDTH=320, HEIGHT=240, DW=8, GAMMA=1)
|
||||
(
|
||||
input clk_video,
|
||||
input ce_pix,
|
||||
@@ -45,7 +46,6 @@ module arcade_rotate_fx #(parameter WIDTH=320, HEIGHT=240, DW=8, GAMMA=1)
|
||||
input forced_scandoubler,
|
||||
input no_rotate,
|
||||
input rotate_ccw,
|
||||
input direct_video,
|
||||
inout [21:0] gamma_bus
|
||||
);
|
||||
|
||||
@@ -99,167 +99,57 @@ screen_rotate #(WIDTH,HEIGHT,DW,4) rotator
|
||||
.vblank_out(rvblank)
|
||||
);
|
||||
|
||||
wire [3:0] Rr,Gr,Br;
|
||||
|
||||
generate
|
||||
if(DW == 6) begin
|
||||
assign Rr = {RGB_out[5:4],RGB_out[5:4]};
|
||||
assign Gr = {RGB_out[3:2],RGB_out[3:2]};
|
||||
assign Br = {RGB_out[1:0],RGB_out[1:0]};
|
||||
wire [3:0] Rr = {RGB_out[5:4],RGB_out[5:4]};
|
||||
wire [3:0] Gr = {RGB_out[3:2],RGB_out[3:2]};
|
||||
wire [3:0] Br = {RGB_out[1:0],RGB_out[1:0]};
|
||||
end
|
||||
else if(DW == 8) begin
|
||||
assign Rr = {RGB_out[7:5],RGB_out[7]};
|
||||
assign Gr = {RGB_out[4:2],RGB_out[4]};
|
||||
assign Br = {RGB_out[1:0],RGB_out[1:0]};
|
||||
wire [3:0] Rr = {RGB_out[7:5],RGB_out[7]};
|
||||
wire [3:0] Gr = {RGB_out[4:2],RGB_out[4]};
|
||||
wire [3:0] Br = {RGB_out[1:0],RGB_out[1:0]};
|
||||
end
|
||||
else if(DW == 9) begin
|
||||
assign Rr = {RGB_out[8:6],RGB_out[8]};
|
||||
assign Gr = {RGB_out[5:3],RGB_out[5]};
|
||||
assign Br = {RGB_out[2:0],RGB_out[2]};
|
||||
wire [3:0] Rr = {RGB_out[8:6],RGB_out[8]};
|
||||
wire [3:0] Gr = {RGB_out[5:3],RGB_out[5]};
|
||||
wire [3:0] Br = {RGB_out[2:0],RGB_out[2]};
|
||||
end
|
||||
else begin
|
||||
assign Rr = RGB_out[11:8];
|
||||
assign Gr = RGB_out[7:4];
|
||||
assign Br = RGB_out[3:0];
|
||||
else if(DW == 12) begin
|
||||
wire [3:0] Rr = RGB_out[11:8];
|
||||
wire [3:0] Gr = RGB_out[7:4];
|
||||
wire [3:0] Br = RGB_out[3:0];
|
||||
end
|
||||
else begin // 24
|
||||
wire [7:0] Rr = RGB_out[23:16];
|
||||
wire [7:0] Gr = RGB_out[15:8];
|
||||
wire [7:0] Br = RGB_out[7:0];
|
||||
end
|
||||
endgenerate
|
||||
|
||||
reg norot;
|
||||
always @(posedge VGA_CLK) norot <= no_rotate | direct_video;
|
||||
|
||||
assign HDMI_CLK = VGA_CLK;
|
||||
assign HDMI_SL = (no_rotate & ~direct_video) ? 2'd0 : sl[1:0];
|
||||
wire [2:0] sl = fx ? fx - 1'd1 : 3'd0;
|
||||
wire scandoubler = fx || forced_scandoubler;
|
||||
|
||||
video_mixer #(WIDTH+4, 1, GAMMA) video_mixer
|
||||
(
|
||||
.clk_vid(HDMI_CLK),
|
||||
.ce_pix(CE | (~scandoubler & ~gamma_bus[19] & ~norot)),
|
||||
.ce_pix_out(HDMI_CE),
|
||||
|
||||
.scandoubler(scandoubler),
|
||||
.hq2x(fx==1),
|
||||
.gamma_bus(gamma_bus),
|
||||
|
||||
.R(norot ? R[7:4] : Rr),
|
||||
.G(norot ? G[7:4] : Gr),
|
||||
.B(norot ? B[7:4] : Br),
|
||||
|
||||
.HSync (norot ? HS : rhs),
|
||||
.VSync (norot ? VS : rvs),
|
||||
.HBlank(norot ? HBL : rhblank),
|
||||
.VBlank(norot ? VBL : rvblank),
|
||||
|
||||
.VGA_R(HDMI_R),
|
||||
.VGA_G(HDMI_G),
|
||||
.VGA_B(HDMI_B),
|
||||
.VGA_VS(HDMI_VS),
|
||||
.VGA_HS(HDMI_HS),
|
||||
.VGA_DE(HDMI_DE)
|
||||
);
|
||||
|
||||
assign VGA_CE = direct_video ? HDMI_CE : CE;
|
||||
assign VGA_R = direct_video ? HDMI_R : R;
|
||||
assign VGA_G = direct_video ? HDMI_G : G;
|
||||
assign VGA_B = direct_video ? HDMI_B : B;
|
||||
assign VGA_HS = direct_video ? HDMI_HS : HS;
|
||||
assign VGA_VS = direct_video ? HDMI_VS : VS;
|
||||
assign VGA_DE = direct_video ? HDMI_DE : ~(HBL | VBL);
|
||||
|
||||
endmodule
|
||||
|
||||
//////////////////////////////////////////////////////////
|
||||
// DW:
|
||||
// 6 : 2R 2G 2B
|
||||
// 8 : 3R 3G 2B
|
||||
// 9 : 3R 3G 3B
|
||||
// 12 : 4R 4G 4B
|
||||
|
||||
module arcade_fx #(parameter WIDTH=320, DW=8, GAMMA=1)
|
||||
(
|
||||
input clk_video,
|
||||
input ce_pix,
|
||||
|
||||
input[DW-1:0] RGB_in,
|
||||
input HBlank,
|
||||
input VBlank,
|
||||
input HSync,
|
||||
input VSync,
|
||||
|
||||
output VGA_CLK,
|
||||
output VGA_CE,
|
||||
output [7:0] VGA_R,
|
||||
output [7:0] VGA_G,
|
||||
output [7:0] VGA_B,
|
||||
output VGA_HS,
|
||||
output VGA_VS,
|
||||
output VGA_DE,
|
||||
|
||||
output HDMI_CLK,
|
||||
output HDMI_CE,
|
||||
output [7:0] HDMI_R,
|
||||
output [7:0] HDMI_G,
|
||||
output [7:0] HDMI_B,
|
||||
output HDMI_HS,
|
||||
output HDMI_VS,
|
||||
output HDMI_DE,
|
||||
output [1:0] HDMI_SL,
|
||||
|
||||
input [2:0] fx,
|
||||
input forced_scandoubler,
|
||||
inout [21:0] gamma_bus
|
||||
);
|
||||
|
||||
wire [7:0] R,G,B;
|
||||
wire CE,HS,VS,HBL,VBL;
|
||||
|
||||
wire VGA_HBL, VGA_VBL;
|
||||
arcade_vga #(DW) vga
|
||||
(
|
||||
.clk_video(clk_video),
|
||||
.ce_pix(ce_pix),
|
||||
|
||||
.RGB_in(RGB_in),
|
||||
.HBlank(HBlank),
|
||||
.VBlank(VBlank),
|
||||
.HSync(HSync),
|
||||
.VSync(VSync),
|
||||
|
||||
.VGA_CLK(VGA_CLK),
|
||||
.VGA_CE(CE),
|
||||
.VGA_R(R),
|
||||
.VGA_G(G),
|
||||
.VGA_B(B),
|
||||
.VGA_HS(HS),
|
||||
.VGA_VS(VS),
|
||||
.VGA_HBL(HBL),
|
||||
.VGA_VBL(VBL)
|
||||
);
|
||||
|
||||
assign HDMI_CLK = VGA_CLK;
|
||||
assign HDMI_SL = sl[1:0];
|
||||
wire [2:0] sl = fx ? fx - 1'd1 : 3'd0;
|
||||
wire scandoubler = fx || forced_scandoubler;
|
||||
|
||||
video_mixer #(WIDTH+4, 1, GAMMA) video_mixer
|
||||
video_mixer #(.LINE_LENGTH(WIDTH+4), .HALF_DEPTH(DW!=24), .GAMMA(GAMMA)) video_mixer
|
||||
(
|
||||
.clk_vid(HDMI_CLK),
|
||||
.ce_pix(CE),
|
||||
.ce_pix(CE | (~scandoubler & ~gamma_bus[19] & ~no_rotate)),
|
||||
.ce_pix_out(HDMI_CE),
|
||||
|
||||
.scandoubler(scandoubler),
|
||||
.hq2x(fx==1),
|
||||
.gamma_bus(gamma_bus),
|
||||
|
||||
.R(R[7:4]),
|
||||
.G(G[7:4]),
|
||||
.B(B[7:4]),
|
||||
.R(no_rotate ? ((DW!=24) ? R[7:4] : R) : Rr),
|
||||
.G(no_rotate ? ((DW!=24) ? G[7:4] : G) : Gr),
|
||||
.B(no_rotate ? ((DW!=24) ? B[7:4] : B) : Br),
|
||||
|
||||
.HSync(HS),
|
||||
.VSync(VS),
|
||||
.HBlank(HBL),
|
||||
.VBlank(VBL),
|
||||
.HSync (no_rotate ? HS : rhs),
|
||||
.VSync (no_rotate ? VS : rvs),
|
||||
.HBlank(no_rotate ? HBL : rhblank),
|
||||
.VBlank(no_rotate ? VBL : rvblank),
|
||||
|
||||
.VGA_R(HDMI_R),
|
||||
.VGA_G(HDMI_G),
|
||||
@@ -269,13 +159,13 @@ video_mixer #(WIDTH+4, 1, GAMMA) video_mixer
|
||||
.VGA_DE(HDMI_DE)
|
||||
);
|
||||
|
||||
assign VGA_CE = HDMI_CE;
|
||||
assign VGA_R = HDMI_R;
|
||||
assign VGA_G = HDMI_G;
|
||||
assign VGA_B = HDMI_B;
|
||||
assign VGA_HS = HDMI_HS;
|
||||
assign VGA_VS = HDMI_VS;
|
||||
assign VGA_DE = HDMI_DE;
|
||||
assign VGA_CE = no_rotate ? HDMI_CE : CE;
|
||||
assign VGA_R = no_rotate ? HDMI_R : R;
|
||||
assign VGA_G = no_rotate ? HDMI_G : G;
|
||||
assign VGA_B = no_rotate ? HDMI_B : B;
|
||||
assign VGA_HS = no_rotate ? HDMI_HS : HS;
|
||||
assign VGA_VS = no_rotate ? HDMI_VS : VS;
|
||||
assign VGA_DE = no_rotate ? HDMI_DE : ~(HBL | VBL);
|
||||
|
||||
endmodule
|
||||
|
||||
@@ -345,11 +235,16 @@ generate
|
||||
assign VGA_G = {RGB_fix[5:3],RGB_fix[5:3],RGB_fix[5:4]};
|
||||
assign VGA_B = {RGB_fix[2:0],RGB_fix[2:0],RGB_fix[2:1]};
|
||||
end
|
||||
else begin
|
||||
else if(DW == 12) begin
|
||||
assign VGA_R = {RGB_fix[11:8],RGB_fix[11:8]};
|
||||
assign VGA_G = {RGB_fix[7:4],RGB_fix[7:4]};
|
||||
assign VGA_B = {RGB_fix[3:0],RGB_fix[3:0]};
|
||||
end
|
||||
else begin // 24
|
||||
assign VGA_R = RGB_fix[23:16];
|
||||
assign VGA_G = RGB_fix[15:8];
|
||||
assign VGA_B = RGB_fix[7:0];
|
||||
end
|
||||
endgenerate
|
||||
|
||||
endmodule
|
||||
|
||||
@@ -164,9 +164,9 @@ ENTITY ascal IS
|
||||
|
||||
-- Framebuffer palette in 8bpp mode
|
||||
pal_clk : IN std_logic :='0';
|
||||
pal_dw : IN unsigned(23 DOWNTO 0) :=x"000000"; -- R G B
|
||||
pal_dr : OUT unsigned(23 DOWNTO 0) :=x"000000";
|
||||
pal_a : IN unsigned(7 DOWNTO 0) :=x"00"; -- Colour index
|
||||
pal_dw : IN unsigned(47 DOWNTO 0) :=x"000000000000"; -- R1 G1 B1 R0 G0 B0
|
||||
pal_dr : OUT unsigned(47 DOWNTO 0) :=x"000000000000";
|
||||
pal_a : IN unsigned(6 DOWNTO 0) :="0000000"; -- Colour index/2
|
||||
pal_wr : IN std_logic :='0';
|
||||
|
||||
------------------------------------
|
||||
@@ -283,11 +283,11 @@ ARCHITECTURE rtl OF ascal IS
|
||||
SUBTYPE uint12 IS natural RANGE 0 TO 4095;
|
||||
SUBTYPE uint13 IS natural RANGE 0 TO 8191;
|
||||
|
||||
TYPE arr_uv24 IS ARRAY (natural RANGE <>) OF unsigned(23 DOWNTO 0);
|
||||
TYPE arr_uv48 IS ARRAY (natural RANGE <>) OF unsigned(47 DOWNTO 0);
|
||||
TYPE arr_uv36 IS ARRAY (natural RANGE <>) OF unsigned(35 DOWNTO 0);
|
||||
TYPE arr_int9 IS ARRAY (natural RANGE <>) OF integer RANGE -256 TO 255;
|
||||
TYPE arr_uint12 IS ARRAY (natural RANGE <>) OF uint12;
|
||||
|
||||
|
||||
----------------------------------------------------------
|
||||
-- Input image
|
||||
SIGNAL i_pvs,i_pfl,i_pde,i_pce : std_logic;
|
||||
@@ -385,8 +385,11 @@ ARCHITECTURE rtl OF ascal IS
|
||||
SIGNAL o_run : std_logic;
|
||||
SIGNAL o_mode,o_hmode,o_vmode : unsigned(4 DOWNTO 0);
|
||||
SIGNAL o_format : unsigned(5 DOWNTO 0);
|
||||
SIGNAL o_fb_pal_dr : unsigned(23 DOWNTO 0);
|
||||
SIGNAL pal_mem : arr_uv24(0 TO 255);
|
||||
SIGNAL o_fb_pal_dr : unsigned(23 DOWNTO 0);
|
||||
SIGNAL o_fb_pal_dr_x2 : unsigned(47 DOWNTO 0);
|
||||
SIGNAL pal_idx: unsigned(7 DOWNTO 0);
|
||||
SIGNAL pal_idx_lsb: std_logic;
|
||||
SIGNAL pal_mem : arr_uv48(0 TO 127);
|
||||
ATTRIBUTE ramstyle of pal_mem : signal is "no_rw_check";
|
||||
SIGNAL o_htotal,o_hsstart,o_hsend : uint12;
|
||||
SIGNAL o_hmin,o_hmax,o_hdisp : uint12;
|
||||
@@ -2046,10 +2049,11 @@ BEGIN
|
||||
pal_dr<=pal_mem(to_integer(pal_a));
|
||||
END IF;
|
||||
END PROCESS;
|
||||
|
||||
o_fb_pal_dr<=
|
||||
pal_mem(to_integer(shift_opack(o_acpt4,o_shift,o_dr,o_format)(0 TO 7)))
|
||||
WHEN rising_edge(o_clk);
|
||||
|
||||
pal_idx <= shift_opack(o_acpt4,o_shift,o_dr,o_format)(0 TO 7);
|
||||
pal_idx_lsb <= pal_idx(0) WHEN rising_edge(o_clk);
|
||||
o_fb_pal_dr_x2 <= pal_mem(to_integer(pal_idx(7 DOWNTO 1))) WHEN rising_edge(o_clk);
|
||||
o_fb_pal_dr <= o_fb_pal_dr_x2(47 DOWNTO 24) WHEN pal_idx_lsb = '1' ELSE o_fb_pal_dr_x2(23 DOWNTO 0);
|
||||
END GENERATE GenPal;
|
||||
|
||||
GenNoPal:IF NOT PALETTE GENERATE
|
||||
|
||||
108
sys/ddr_svc.sv
Normal file
108
sys/ddr_svc.sv
Normal file
@@ -0,0 +1,108 @@
|
||||
//
|
||||
// Copyright (c) 2020 Alexey Melnikov
|
||||
//
|
||||
//
|
||||
// This source file is free software: you can redistribute it and/or modify
|
||||
// it under the terms of the GNU General Public License as published
|
||||
// by the Free Software Foundation, either version 3 of the License, or
|
||||
// (at your option) any later version.
|
||||
//
|
||||
// This source file is distributed in the hope that it will be useful,
|
||||
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
// GNU General Public License for more details.
|
||||
//
|
||||
// You should have received a copy of the GNU General Public License
|
||||
// along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
//
|
||||
// ------------------------------------------
|
||||
//
|
||||
|
||||
// 16-bit version
|
||||
|
||||
module ddr_svc
|
||||
(
|
||||
input clk,
|
||||
|
||||
input ram_waitrequest,
|
||||
output [7:0] ram_burstcnt,
|
||||
output [28:0] ram_addr,
|
||||
input [63:0] ram_readdata,
|
||||
input ram_read_ready,
|
||||
output reg ram_read,
|
||||
output [63:0] ram_writedata,
|
||||
output [7:0] ram_byteenable,
|
||||
output reg ram_write,
|
||||
|
||||
output [7:0] ram_bcnt,
|
||||
|
||||
input [31:3] ch0_addr,
|
||||
input [7:0] ch0_burst,
|
||||
output [63:0] ch0_data,
|
||||
input ch0_req,
|
||||
output ch0_ready,
|
||||
|
||||
input [31:3] ch1_addr,
|
||||
input [7:0] ch1_burst,
|
||||
output [63:0] ch1_data,
|
||||
input ch1_req,
|
||||
output ch1_ready
|
||||
);
|
||||
|
||||
assign ram_burstcnt = ram_burst;
|
||||
assign ram_byteenable = 8'hFF;
|
||||
assign ram_addr = ram_address;
|
||||
assign ram_writedata = 0;
|
||||
|
||||
assign ch0_data = ram_q[0];
|
||||
assign ch1_data = ram_q[1];
|
||||
assign ch0_ready = ready[0];
|
||||
assign ch1_ready = ready[1];
|
||||
|
||||
reg [7:0] ram_burst;
|
||||
reg [63:0] ram_q[2];
|
||||
reg [31:3] ram_address;
|
||||
reg [1:0] ack = 0;
|
||||
reg [1:0] ready;
|
||||
reg state = 0;
|
||||
reg ch = 0;
|
||||
|
||||
always @(posedge clk) begin
|
||||
ready <= 0;
|
||||
|
||||
if(!ram_waitrequest) begin
|
||||
ram_read <= 0;
|
||||
ram_write <= 0;
|
||||
|
||||
case(state)
|
||||
0: if(ch0_req != ack[0]) begin
|
||||
ack[0] <= ch0_req;
|
||||
ram_address <= ch0_addr;
|
||||
ram_burst <= ch0_burst;
|
||||
ram_read <= 1;
|
||||
ch <= 0;
|
||||
ram_bcnt <= 8'hFF;
|
||||
state <= 1;
|
||||
end
|
||||
else if(ch1_req != ack[1]) begin
|
||||
ack[1] <= ch1_req;
|
||||
ram_address <= ch1_addr;
|
||||
ram_burst <= ch1_burst;
|
||||
ram_read <= 1;
|
||||
ch <= 1;
|
||||
ram_bcnt <= 8'hFF;
|
||||
state <= 1;
|
||||
end
|
||||
1: begin
|
||||
if(ram_read_ready) begin
|
||||
ram_bcnt <= ram_bcnt + 1'd1;
|
||||
ram_q[ch] <= ram_readdata;
|
||||
ready[ch] <= 1;
|
||||
if ((ram_bcnt+2'd2) == ram_burst) state <= 0;
|
||||
end
|
||||
end
|
||||
endcase
|
||||
end
|
||||
end
|
||||
|
||||
endmodule
|
||||
86
sys/fbpal.sv
86
sys/fbpal.sv
@@ -1,86 +0,0 @@
|
||||
//============================================================================
|
||||
//
|
||||
// Framebuffer Palette support for MiSTer
|
||||
// (c)2019 Sorgelig
|
||||
//
|
||||
// This program is free software; you can redistribute it and/or modify it
|
||||
// under the terms of the GNU General Public License as published by the Free
|
||||
// Software Foundation; either version 2 of the License, or (at your option)
|
||||
// any later version.
|
||||
//
|
||||
// This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
// ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
// FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
|
||||
// more details.
|
||||
//
|
||||
// You should have received a copy of the GNU General Public License along
|
||||
// with this program; if not, write to the Free Software Foundation, Inc.,
|
||||
// 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
//
|
||||
//============================================================================
|
||||
|
||||
module fbpal
|
||||
(
|
||||
input reset,
|
||||
|
||||
input en_in,
|
||||
output reg en_out,
|
||||
|
||||
input ram_clk,
|
||||
output reg [28:0] ram_address,
|
||||
output reg [7:0] ram_burstcount,
|
||||
input ram_waitrequest,
|
||||
input [63:0] ram_readdata,
|
||||
input ram_readdatavalid,
|
||||
output reg ram_read,
|
||||
|
||||
input [31:0] fb_address,
|
||||
|
||||
input pal_en,
|
||||
output reg [7:0] pal_a,
|
||||
output reg [23:0] pal_d,
|
||||
output reg pal_wr
|
||||
);
|
||||
|
||||
reg [31:0] base_addr;
|
||||
always @(posedge ram_clk) base_addr <= fb_address - 4096;
|
||||
|
||||
reg [6:0] buf_rptr = 0;
|
||||
always @(posedge ram_clk) begin
|
||||
reg [23:0] odd_d;
|
||||
|
||||
if(~pal_a[0] & pal_wr) {pal_a[0], pal_d} <= {1'b1, odd_d};
|
||||
else pal_wr <= 0;
|
||||
|
||||
if(~ram_waitrequest) ram_read <= 0;
|
||||
|
||||
if(pal_en & ~reset) begin
|
||||
if(ram_burstcount) begin
|
||||
if(ram_readdatavalid) begin
|
||||
ram_burstcount <= 0;
|
||||
|
||||
odd_d <= ram_readdata[55:32];
|
||||
pal_d <= ram_readdata[23:0];
|
||||
pal_a <= {buf_rptr, 1'b0};
|
||||
pal_wr <= 1;
|
||||
|
||||
en_out <= en_in;
|
||||
buf_rptr <= buf_rptr + 1'd1;
|
||||
end
|
||||
end
|
||||
else begin
|
||||
if(~ram_waitrequest && en_out != en_in) begin
|
||||
ram_address <= base_addr[31:3] + buf_rptr;
|
||||
ram_burstcount <= 1;
|
||||
ram_read <= 1;
|
||||
end
|
||||
end
|
||||
end
|
||||
else begin
|
||||
en_out <= en_in;
|
||||
buf_rptr <= 0;
|
||||
ram_burstcount <= 0;
|
||||
end
|
||||
end
|
||||
|
||||
endmodule
|
||||
@@ -3,7 +3,6 @@ set_global_assignment -name VERILOG_FILE [file join $::quartus(qip_path) s
|
||||
set_global_assignment -name SDC_FILE [file join $::quartus(qip_path) sys_top.sdc ]
|
||||
set_global_assignment -name VHDL_FILE [file join $::quartus(qip_path) ascal.vhd ]
|
||||
set_global_assignment -name VHDL_FILE [file join $::quartus(qip_path) pll_hdmi_adj.vhd ]
|
||||
set_global_assignment -name SYSTEMVERILOG_FILE [file join $::quartus(qip_path) fbpal.sv ]
|
||||
set_global_assignment -name SYSTEMVERILOG_FILE [file join $::quartus(qip_path) hq2x.sv ]
|
||||
set_global_assignment -name VERILOG_FILE [file join $::quartus(qip_path) scandoubler.v ]
|
||||
set_global_assignment -name VERILOG_FILE [file join $::quartus(qip_path) scanlines.v ]
|
||||
@@ -22,6 +21,7 @@ set_global_assignment -name SYSTEMVERILOG_FILE [file join $::quartus(qip_path) l
|
||||
set_global_assignment -name VERILOG_FILE [file join $::quartus(qip_path) sigma_delta_dac.v ]
|
||||
set_global_assignment -name SYSTEMVERILOG_FILE [file join $::quartus(qip_path) hdmi_config.sv ]
|
||||
set_global_assignment -name SYSTEMVERILOG_FILE [file join $::quartus(qip_path) mcp23009.sv ]
|
||||
set_global_assignment -name SYSTEMVERILOG_FILE [file join $::quartus(qip_path) ddr_svc.sv ]
|
||||
set_global_assignment -name SYSTEMVERILOG_FILE [file join $::quartus(qip_path) sysmem.sv ]
|
||||
set_global_assignment -name VERILOG_FILE [file join $::quartus(qip_path) sd_card.v ]
|
||||
set_global_assignment -name VERILOG_FILE [file join $::quartus(qip_path) hps_io.v ]
|
||||
|
||||
126
sys/sys_top.v
126
sys/sys_top.v
@@ -423,12 +423,12 @@ cyclonev_hps_interface_peripheral_uart uart
|
||||
`endif
|
||||
);
|
||||
|
||||
wire aspi_sck,aspi_mosi,aspi_ss;
|
||||
wire aspi_sck,aspi_mosi,aspi_ss,aspi_miso;
|
||||
cyclonev_hps_interface_peripheral_spi_master spi
|
||||
(
|
||||
.sclk_out(aspi_sck),
|
||||
.txd(aspi_mosi), // mosi
|
||||
.rxd(1), // miso
|
||||
.rxd(aspi_miso), // miso
|
||||
|
||||
.ss_0_n(aspi_ss),
|
||||
.ss_in_n(1)
|
||||
@@ -494,15 +494,15 @@ sysmem_lite sysmem
|
||||
|
||||
//64-bit DDR3 RAM access
|
||||
.ram2_clk(clk_audio),
|
||||
.ram2_address((ap_en1 == ap_en2) ? aram_address : pram_address),
|
||||
.ram2_burstcount((ap_en1 == ap_en2) ? aram_burstcount : pram_burstcount),
|
||||
.ram2_waitrequest(aram_waitrequest),
|
||||
.ram2_readdata(aram_readdata),
|
||||
.ram2_readdatavalid(aram_readdatavalid),
|
||||
.ram2_read((ap_en1 == ap_en2) ? aram_read : pram_read),
|
||||
.ram2_writedata(0),
|
||||
.ram2_byteenable(8'hFF),
|
||||
.ram2_write(0),
|
||||
.ram2_address(ram2_address),
|
||||
.ram2_burstcount(ram2_burstcount),
|
||||
.ram2_waitrequest(ram2_waitrequest),
|
||||
.ram2_readdata(ram2_readdata),
|
||||
.ram2_readdatavalid(ram2_readdatavalid),
|
||||
.ram2_read(ram2_read),
|
||||
.ram2_writedata(ram2_writedata),
|
||||
.ram2_byteenable(ram2_byteenable),
|
||||
.ram2_write(ram2_write),
|
||||
|
||||
//128-bit DDR3 RAM access
|
||||
// HDMI frame buffer
|
||||
@@ -518,6 +518,46 @@ sysmem_lite sysmem
|
||||
.vbuf_read(vbuf_read)
|
||||
);
|
||||
|
||||
wire [28:0] ram2_address;
|
||||
wire [7:0] ram2_burstcount;
|
||||
wire [7:0] ram2_byteenable;
|
||||
wire ram2_waitrequest;
|
||||
wire [63:0] ram2_readdata;
|
||||
wire [63:0] ram2_writedata;
|
||||
wire ram2_readdatavalid;
|
||||
wire ram2_read;
|
||||
wire ram2_write;
|
||||
wire [7:0] ram2_bcnt;
|
||||
|
||||
ddr_svc ddr_svc
|
||||
(
|
||||
.clk(clk_audio),
|
||||
|
||||
.ram_waitrequest(ram2_waitrequest),
|
||||
.ram_burstcnt(ram2_burstcount),
|
||||
.ram_addr(ram2_address),
|
||||
.ram_readdata(ram2_readdata),
|
||||
.ram_read_ready(ram2_readdatavalid),
|
||||
.ram_read(ram2_read),
|
||||
.ram_writedata(ram2_writedata),
|
||||
.ram_byteenable(ram2_byteenable),
|
||||
.ram_write(ram2_write),
|
||||
.ram_bcnt(ram2_bcnt),
|
||||
|
||||
.ch0_addr(alsa_address),
|
||||
.ch0_burst(1),
|
||||
.ch0_data(alsa_readdata),
|
||||
.ch0_req(alsa_req),
|
||||
.ch0_ready(alsa_ready),
|
||||
|
||||
.ch1_addr(pal_addr),
|
||||
.ch1_burst(128),
|
||||
.ch1_data(pal_data),
|
||||
.ch1_req(pal_req),
|
||||
.ch1_ready(pal_wr)
|
||||
);
|
||||
|
||||
|
||||
wire [27:0] vbuf_address;
|
||||
wire [7:0] vbuf_burstcount;
|
||||
wire vbuf_waitrequest;
|
||||
@@ -687,37 +727,21 @@ pll_hdmi_adj pll_hdmi_adj
|
||||
.o_writedata(cfg_data)
|
||||
);
|
||||
|
||||
wire [23:0] pal_d;
|
||||
wire [7:0] pal_a;
|
||||
wire [63:0] pal_data;
|
||||
wire [47:0] pal_d = {pal_data[55:32], pal_data[23:0]};
|
||||
wire [6:0] pal_a = ram2_bcnt[6:0];
|
||||
wire pal_wr;
|
||||
|
||||
wire ap_en1, ap_en2;
|
||||
reg [28:0] pal_addr;
|
||||
reg pal_req = 0;
|
||||
always @(posedge clk_pal) begin
|
||||
reg old_vs;
|
||||
|
||||
wire [28:0] pram_address;
|
||||
wire [7:0] pram_burstcount;
|
||||
wire pram_read;
|
||||
pal_addr <= FB_BASE[31:3] - 29'd512;
|
||||
|
||||
fbpal fbpal
|
||||
(
|
||||
.reset(reset),
|
||||
.en_in(ap_en2),
|
||||
.en_out(ap_en1),
|
||||
|
||||
.ram_clk(clk_pal),
|
||||
.ram_address(pram_address),
|
||||
.ram_burstcount(pram_burstcount),
|
||||
.ram_waitrequest(aram_waitrequest),
|
||||
.ram_readdata(aram_readdata),
|
||||
.ram_readdatavalid(aram_readdatavalid),
|
||||
.ram_read(pram_read),
|
||||
|
||||
.fb_address(FB_BASE),
|
||||
|
||||
.pal_en(~FB_FMT[2] & FB_FMT[1] & FB_FMT[0] & FB_EN),
|
||||
.pal_a(pal_a),
|
||||
.pal_d(pal_d),
|
||||
.pal_wr(pal_wr)
|
||||
);
|
||||
old_vs <= hdmi_vs;
|
||||
if(~old_vs & hdmi_vs & ~FB_FMT[2] & FB_FMT[1] & FB_FMT[0] & FB_EN) pal_req <= ~pal_req;
|
||||
end
|
||||
|
||||
|
||||
///////////////////////// HDMI output /////////////////////////////////
|
||||
@@ -1087,32 +1111,28 @@ audio_out audio_out
|
||||
.spdif(spdif)
|
||||
);
|
||||
|
||||
wire [28:0] aram_address;
|
||||
wire [7:0] aram_burstcount;
|
||||
wire aram_waitrequest;
|
||||
wire [63:0] aram_readdata;
|
||||
wire aram_readdatavalid;
|
||||
wire aram_read;
|
||||
wire [28:0] alsa_address;
|
||||
wire [63:0] alsa_readdata;
|
||||
wire alsa_ready;
|
||||
wire alsa_req;
|
||||
wire alsa_late;
|
||||
|
||||
wire [15:0] alsa_l, alsa_r;
|
||||
|
||||
alsa alsa
|
||||
(
|
||||
.reset(reset),
|
||||
.en_in(ap_en1),
|
||||
.en_out(ap_en2),
|
||||
.clk(clk_audio),
|
||||
|
||||
.ram_clk(clk_audio),
|
||||
.ram_address(aram_address),
|
||||
.ram_burstcount(aram_burstcount),
|
||||
.ram_waitrequest(aram_waitrequest),
|
||||
.ram_readdata(aram_readdata),
|
||||
.ram_readdatavalid(aram_readdatavalid),
|
||||
.ram_read(aram_read),
|
||||
.ram_address(alsa_address),
|
||||
.ram_data(alsa_readdata),
|
||||
.ram_req(alsa_req),
|
||||
.ram_ready(alsa_ready),
|
||||
|
||||
.spi_ss(aspi_ss),
|
||||
.spi_sck(aspi_sck),
|
||||
.spi_mosi(aspi_mosi),
|
||||
.spi_miso(aspi_miso),
|
||||
|
||||
.pcm_l(alsa_l),
|
||||
.pcm_r(alsa_r)
|
||||
|
||||
Reference in New Issue
Block a user