📄 20050527 freedev_aic23.v
字号:
module freedev_aic23(clk,rst_n,cs_n,rd_n,wr_n,addr,rdata,wdata,
lrcin,din,lrcout,dout,bclk);
// parameter
input clk; // master clk
input rst_n; // reset
input cs_n; // chip select
input rd_n; // read signal
input wr_n; // write signal
input [2:0]addr;// address
output [15:0]rdata; // out data
input [15:0]wdata; // in data
reg [15:0] rdata;
input lrcin; // aic master mode,from AIC23 to fpga
output din; // to DAC
input lrcout; // aic master mode,from AIC23 TO fpga
input dout; // from ADC
input bclk; // bclk from AIC23
//
// variable declarations
//
// registers
reg [15:0] mode_reg; // modele register address 000
reg [15:0] command_reg; // command register address 001
reg [15:0] state_reg; // state register address 010
reg [15:0] left_data; // left data address 011
reg [15:0] right_data; // right data address 100
// generate write signals
wire wacc = ~cs_n & ~wr_n;
// generate read signals
wire racc = ~cs_n & ~rd_n;
// clk时钟域:avalone slave 接口部分
// generate registers
always @(posedge clk or negedge rst_n)
if (!rst_n)
begin
mode_reg <= #1 16'h0000;
command_reg <= #1 16'h0000;
state_reg <= #1 16'h0000;
left_data <= #1 16'h0000;
right_data <= #1 16'h0000;
end
else
if ( wacc )
begin
case ( addr ) // synopsis parallel_case
3'b000 : mode_reg <= #1 wdata;
3'b001 : command_reg <= #1 wdata;
3'b010 : state_reg <= #1 wdata;
3'b011 : left_data <= #1 wdata;
3'b100 : right_data <= #1 wdata;
default: ;
endcase
end
always @(posedge clk)
begin
if( racc )
case (addr) // synopsis parallel_case
3'b000: rdata <= #1 mode_reg;
3'b001: rdata <= #1 command_reg;
3'b010: rdata <= #1 state_reg;
3'b011: rdata <= #1 left_data;
3'b100: rdata <= #1 right_data;
3'b101: rdata <= #1 16'h0; // reserved
3'b110: rdata <= #1 16'h0; // reserved
3'b111: rdata <= #1 16'h0; // reserved
endcase
end
//跨时钟域异步控制信号
wire bypass_mode = mode_reg[1:0]==2'b00 ? 1:0 ; //复位默认是数字旁路
wire byte_mode = mode_reg[1:0]==2'b01 ? 1:0;
wire dma_mode = mode_reg[1:0]==2'b10 ? 1:0;
//bclk时钟域: TLV320AIC23数字音频接口
reg s_lrcin,d_lrcin; //lrcin同步和延时
reg s_lrcout,d_lrcout; //lrcout同步和延时
always @(posedge bclk)
begin
d_lrcin <= s_lrcin;
s_lrcin <= lrcin;
d_lrcout <= s_lrcout;
s_lrcout <= lrcout;
end
wire in_flag,out_flag; //AIC23 DSP MODE
assign in_flag = ~d_lrcout & s_lrcout;
assign out_flag= ~d_lrcin & s_lrcin;
reg [31:0]recv; // recv data from aic23 adc
reg [31:0]recved; // recved data
reg [4:0]recv_count; // recv counter
reg [1:0]recv_state; // recv state
// state machine
parameter IDLE = 2'b00;
parameter START = 2'b01;
parameter STOP = 2'b10;
parameter HOLD = 2'b11;
//数字音频接口DSP方式数据处理块
always @(posedge bclk)
if(~rst_n)
begin
recv_state <= IDLE;
end else
begin
if(lrcin)
begin
recved <= #1 recv;
recv <= #1 32'h0;
recv_count <= #1 5'h0;
recv_state <= #1 START;
end
else if(recv_state == START)
begin
recv <= #1 {recv[30:0],dout};
recv_count <= recv_count + 5'h1;
if( recv_count == 5'b11111)
begin
recv_state <= #1 STOP;
end
end
end
//数字音频接口DSP模式旁路处理块
reg [31:0]send; // send data to dac
reg [31:0]sended; // sended data
reg [4:0]send_count; // send counter
reg [1:0]send_state; // send state
reg bypass_out;
always @(negedge bclk)
if(~rst_n)
begin
send_state <= IDLE;
end else
begin
if(out_flag)
begin
bypass_out <= #1 recved[31];
send <= #1 {recved[30:0],1'b0};
send_count <= #1 5'h1;
send_state <= #1 START;
end
else if(send_state == START)
begin
bypass_out <= #1 send[31];
send <= #1 {send[30:0],1'b0};
send_count <= send_count + 5'h1;
if( send_count == 5'b11111)
begin
send_state <= #1 STOP;
end
end
end
//数字音频接口DSP模式字节模式
reg [31:0]bsend; // send data to dac
reg [31:0]bsended; // sended data
reg [4:0]bsend_count; // send counter
reg [1:0]bsend_state; // send state
reg byte_out;
always @(negedge bclk)
if(~rst_n)
begin
bsend_state <= IDLE;
end else
begin
if(out_flag)
begin
byte_out <= #1 left_data[15];
bsend <= #1 {left_data[14:0],right_data[15:0],1'b0};
bsend_count <= #1 5'h1;
bsend_state <= #1 START;
end
else if(bsend_state == START)
begin
byte_out <= #1 bsend[31];
bsend <= #1 {bsend[30:0],1'b0};
bsend_count <= bsend_count + 5'h1;
if( bsend_count == 5'b11111)
begin
bsend_state <= #1 STOP;
end
end
end
//输出优先选择
assign din = byte_mode?byte_out:(bypass_mode ? bypass_out:0);
reg [31:0]dp_data;
reg [5:0]dp_raddr;
reg dp_rden;
reg [5:0]dp_waddr;
reg dp_wren;
reg [31:0]dp_q;
//双口同步RAM
lpm_dpram dpram(
.data(dp_data),
.rdaddress(dp_raddr),
.rdclock(clk),
.rden(dp_rden),
.wraddress(dp_waddr),
.wrclock(bclk),
.wren(dp_wren),
.q(dp_q));
endmodule
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -