mirror of
https://github.com/retroSoC/retroSoC.git
synced 2026-11-04 22:32:36 +00:00
Integrate RNG, CRC, WS2812, Crypto, I2S master and the SDIO private AXI owner on SAFE24. Preserve the 128 KiB main SRAM and six private Crypto macros, add product-specific DMA assignments and reject unsupported SDK operations.
Correct APB read strobes, I2S receive assembly and SDIO command timing, backpressure and descriptor retirement. Add pin-level workloads, source-bound evidence checks and publication/commercial consumer compatibility.
Validation of the final P6 worktree: 1726 pytest tests passed with one optional pypdf skip (exit 0, 4021.61 seconds; terminal session 36439). Both PDKs passed both RTL simulators, netlist boot and 38-macro binding checks. Shared formal, Mini compatibility and software/source quality gates passed.
Evidence remains attributed to the retained dirty-worktree snapshots based on b3b30a72cd under build/ics55-tiny-2026-10-12-11-50-2eb98c0e1fae/meta/tiny-r2-p6/. Timing is negative and warning observations are not promoted. This commit does not accept P6, qualify physical operation or enable P7.
124 lines
3.2 KiB
Systemverilog
124 lines
3.2 KiB
Systemverilog
// Copyright (c) 2023-2026 Yuchi Miao <miaoyuchi@ict.ac.cn>
|
|
// retroSoC is licensed under Mulan PSL v2.
|
|
// You can use this software according to the terms and conditions of the Mulan PSL v2.
|
|
// You may obtain a copy of Mulan PSL v2 at:
|
|
// http://license.coscl.org.cn/MulanPSL2
|
|
// THIS SOFTWARE IS PROVIDED ON AN "AS IS" BASIS, WITHOUT WARRANTIES OF ANY KIND,
|
|
// EITHER EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO NON-INFRINGEMENT,
|
|
// MERCHANTABILITY OR FIT FOR A PARTICULAR PURPOSE.
|
|
// See the Mulan PSL v2 for more details.
|
|
|
|
module i2s_recv (
|
|
input logic clk_i,
|
|
input logic rst_n_i,
|
|
input logic sclk_pos_i,
|
|
input logic lrck_i,
|
|
input logic bitmode_i,
|
|
input logic adcdat_i,
|
|
output logic [23:0] data_o,
|
|
output logic done_o
|
|
|
|
);
|
|
|
|
logic s_lrck_dely_d, s_lrck_dely_q;
|
|
logic s_lrck_trg;
|
|
logic [4:0] s_bit_cnt_d, s_bit_cnt_q;
|
|
logic [4:0] s_bit_num;
|
|
logic s_done_d, s_done_q;
|
|
logic [23:0] s_recv_data_d, s_recv_data_q;
|
|
logic [23:0] s_data_d, s_data_q;
|
|
|
|
|
|
assign s_bit_num = bitmode_i ? 5'd23 : 5'd15;
|
|
assign data_o = s_data_q;
|
|
assign done_o = s_done_q;
|
|
assign s_lrck_trg = lrck_i ^ s_lrck_dely_q;
|
|
|
|
|
|
assign s_lrck_dely_d = lrck_i;
|
|
dffer #(
|
|
.DATA_WIDTH(1)
|
|
) u_lrck_dely_dffer (
|
|
.clk_i (clk_i),
|
|
.rst_n_i(rst_n_i),
|
|
.en_i (sclk_pos_i),
|
|
.dat_i (s_lrck_dely_d),
|
|
.dat_o (s_lrck_dely_q)
|
|
);
|
|
|
|
|
|
always_comb begin
|
|
s_bit_cnt_d = s_bit_cnt_q;
|
|
if (s_lrck_trg) s_bit_cnt_d = '0;
|
|
else if (s_bit_cnt_q < s_bit_num) begin
|
|
s_bit_cnt_d = s_bit_cnt_q + 1'b1;
|
|
end
|
|
end
|
|
dffer #(
|
|
.DATA_WIDTH(5)
|
|
) u_bit_cnt_dffer (
|
|
.clk_i (clk_i),
|
|
.rst_n_i(rst_n_i),
|
|
.en_i (sclk_pos_i),
|
|
.dat_i (s_bit_cnt_d),
|
|
.dat_o (s_bit_cnt_q)
|
|
);
|
|
|
|
|
|
always_comb begin
|
|
s_recv_data_d = s_recv_data_q;
|
|
if (s_lrck_trg) begin
|
|
s_recv_data_d = '0;
|
|
end else if (s_bit_cnt_q < s_bit_num) begin
|
|
if (bitmode_i) begin
|
|
s_recv_data_d[23:0] = {s_recv_data_q[22:0], adcdat_i};
|
|
end else begin
|
|
s_recv_data_d[23:16] = s_recv_data_q[23:16];
|
|
s_recv_data_d[15:0] = {s_recv_data_q[14:0], adcdat_i};
|
|
end
|
|
end
|
|
end
|
|
dffer #(
|
|
.DATA_WIDTH(24)
|
|
) u_recv_data_dffer (
|
|
.clk_i (clk_i),
|
|
.rst_n_i(rst_n_i),
|
|
.en_i (sclk_pos_i),
|
|
.dat_i (s_recv_data_d),
|
|
.dat_o (s_recv_data_q)
|
|
);
|
|
|
|
|
|
// I2S changes LRCK one bit before the next sample's MSB. The bit
|
|
// sampled on that transition is the current sample's LSB, not the next
|
|
// sample's first bit. Publish completion after data_o has captured it.
|
|
assign s_done_d = sclk_pos_i && s_lrck_trg;
|
|
dffr #(
|
|
.DATA_WIDTH(1)
|
|
) u_done_dffr (
|
|
.clk_i (clk_i),
|
|
.rst_n_i(rst_n_i),
|
|
.dat_i (s_done_d),
|
|
.dat_o (s_done_q)
|
|
);
|
|
|
|
|
|
always_comb begin
|
|
s_data_d = s_data_q;
|
|
if (s_lrck_trg) begin
|
|
if (bitmode_i) s_data_d = {s_recv_data_q[22:0], adcdat_i};
|
|
else s_data_d = {8'd0, s_recv_data_q[14:0], adcdat_i};
|
|
end
|
|
end
|
|
dffer #(
|
|
.DATA_WIDTH(24)
|
|
) u_data_dffer (
|
|
.clk_i (clk_i),
|
|
.rst_n_i(rst_n_i),
|
|
.en_i (sclk_pos_i),
|
|
.dat_i (s_data_d),
|
|
.dat_o (s_data_q)
|
|
);
|
|
|
|
endmodule
|