📄 pci_wb_slave.v
字号:
begin
n_state = S_IDLE ;
del_done = 1'b1 ;
wbr_fifo_flush = ~wbr_fifo_empty_in ;
end
else
begin
n_state = S_READ ;
end
end // S_READ
S_CONF_WRITE: begin
`ifdef HOST
wbw_data_out_sel = SEL_CCYC_ADDR ;
del_req = do_ccyc_req && ~burst_transfer ;
del_done = do_ccyc_comp && ~burst_transfer ;
del_in_progress = do_ccyc_comp && ~burst_transfer ;
`endif
n_state = S_IDLE ; // next state after configuration access is always idle
if ( burst_transfer )
begin
err = 1'b1 ;
end
else
begin
`ifdef HOST
if ( do_ccyc_req || (ccyc_hit && ~do_ccyc_comp))
begin
rty = 1'b1 ;
end
else
if ( do_ccyc_comp )
begin
err = del_error_in ;
ack = ~del_error_in ;
end
else
begin
ack = ~ccyc_hit ;
conf_wenable = ~ccyc_hit ;
end
`else
ack = 1'b1 ;
conf_wenable = 1'b1 ;
`endif
end
end // S_CONF_WRITE
S_CONF_READ: begin
`ifdef HOST
wbw_data_out_sel = SEL_CCYC_ADDR ;
del_req = ~burst_transfer && ( do_ccyc_req || do_iack_req ) ;
del_done = ~burst_transfer && ( do_ccyc_comp || do_iack_comp ) ;
del_in_progress = ~burst_transfer && ( do_ccyc_comp || do_iack_comp ) ;
wbr_fifo_renable = ~burst_transfer && ( do_ccyc_comp || do_iack_comp ) ;
`endif
n_state = S_IDLE ; // next state after configuration access is always idle
if ( burst_transfer )
begin
err = 1'b1 ;
end
else
begin
`ifdef HOST
if ( do_ccyc_req || ( ccyc_hit && ~do_ccyc_comp ))
begin
rty = 1'b1 ;
end
else
if ( do_iack_req || ( iack_hit && ~do_iack_comp ))
begin
rty = 1'b1 ;
end
else
if ( do_iack_comp || do_ccyc_comp )
begin
err = del_error_in ;
ack = ~del_error_in ;
end
else
begin
ack = ~( ccyc_hit || iack_hit ) ;
conf_renable = ~( ccyc_hit || iack_hit ) ;
end
`else
ack = 1'b1 ;
conf_renable = 1'b1 ;
`endif
end
end //S_CONF_READ
default:begin
n_state = S_IDLE ; // return to idle state
end //default
endcase
end
// configuration space offset output assignment
assign wb_conf_offset_out = {wb_addr_in[11:2], 2'b00} ; // upper 10 bits of address input and two zeros
// data output assignment - for image writes, first data is address, subsequent data comes from intermediate register
reg [31:0] wb_data ;
`ifdef HOST
reg [1:0] wbw_data_out_sel_reg ;
always@(posedge wb_clock_in or posedge reset_in)
begin
if ( reset_in )
wbw_data_out_sel_reg <= #`FF_DELAY SEL_ADDR_IN ;
else
wbw_data_out_sel_reg <= #`FF_DELAY wbw_data_out_sel ;
end
always@(wbw_data_out_sel_reg or wb_addr_in or ccyc_addr_in or d_incoming)
begin
case ( wbw_data_out_sel_reg )
SEL_CCYC_ADDR: wb_data = ccyc_addr_in ;
SEL_DATA_IN: wb_data = d_incoming ;
default: wb_data = wb_addr_in ;
endcase
end
`else
`ifdef GUEST
reg wbw_data_out_sel_reg ;
always@(posedge wb_clock_in or posedge reset_in)
begin
if ( reset_in )
wbw_data_out_sel_reg <= #`FF_DELAY SEL_ADDR_IN ;
else
wbw_data_out_sel_reg <= #`FF_DELAY wbw_data_out_sel ;
end
always@(wbw_data_out_sel_reg or wb_addr_in or d_incoming)
begin
if ( wbw_data_out_sel_reg )
wb_data = wb_addr_in ;
else
wb_data = d_incoming ;
end
`endif
`endif
// command / byte enable assignment - with address, bus command is provided, with data - byte enables are provided
reg [3:0] wb_cbe ;
always@(wbw_data_out_sel_reg or d_incoming or map)
begin
if (wbw_data_out_sel_reg && map)
wb_cbe = `BC_IO_WRITE ;
else
if (wbw_data_out_sel_reg)
wb_cbe = `BC_MEM_WRITE ;
else
wb_cbe = ~(d_incoming[35:32]) ;
end
// for configuration writes, data output is always data from WISHBONE - in guest implementation data is all 0.
`ifdef GUEST
assign wb_conf_data_out = 32'h00000000 ;
`endif
`ifdef GUEST
`ifdef NO_CNF_IMAGE
`else
`define PCI_WB_SLAVE_DO_OUT_MUX
`endif
`else
`ifdef HOST
`define PCI_WB_SLAVE_DO_OUT_MUX ;
`endif
`endif
`ifdef PCI_WB_SLAVE_DO_OUT_MUX
reg [31:0] sdata_source ;
// WISHBONE data output select lines for output multiplexor
wire sdata_o_sel_new = ( wb_conf_hit_in && ~wiack_hit && ~wccyc_hit ) ? CONF_SEL : WBR_SEL ;
reg sdata_o_sel ;
always@(posedge wb_clock_in or posedge reset_in)
begin
if ( reset_in )
sdata_o_sel <= #`FF_DELAY WBR_SEL ;
else
if ( decode_en )
sdata_o_sel <= #`FF_DELAY sdata_o_sel_new ;
end
always@(sdata_o_sel or wbr_fifo_data_in or wb_conf_data_in)
begin
case (sdata_o_sel)
WBR_SEL :sdata_source = wbr_fifo_data_in ;
CONF_SEL:sdata_source = wb_conf_data_in ;
endcase
end
`else
wire [31:0] sdata_source = wbr_fifo_data_in ;
`endif
`ifdef REGISTER_WBS_OUTPUTS
always@(posedge wb_clock_in or posedge reset_in)
begin
if ( reset_in )
begin
ACK_O <= #`FF_DELAY 1'b0 ;
RTY_O <= #`FF_DELAY 1'b0 ;
ERR_O <= #`FF_DELAY 1'b0 ;
SDATA_O <= #`FF_DELAY 0 ;
del_write_out <= #`FF_DELAY 1'b0 ;
`ifdef HOST
wb_conf_wenable_out <= #`FF_DELAY 1'b0 ;
wb_conf_data_out <= #`FF_DELAY 0 ;
`endif
del_bc_out <= #`FF_DELAY `BC_RESERVED0 ;
del_req_out <= #`FF_DELAY 1'b0 ;
del_done_out <= #`FF_DELAY 1'b0 ;
del_burst_out <= #`FF_DELAY 1'b0 ;
del_in_progress_out <= #`FF_DELAY 1'b0 ;
wb_conf_be_out <= #`FF_DELAY 0 ;
wb_data_out <= #`FF_DELAY 0 ;
wb_cbe_out <= #`FF_DELAY 0 ;
wbw_fifo_wenable_out <= #`FF_DELAY 0 ;
wbw_fifo_control_out <= #`FF_DELAY 0 ;
wbr_fifo_renable_out <= #`FF_DELAY 0 ;
end
else
begin
ACK_O <= #`FF_DELAY ack && !ACK_O ;
RTY_O <= #`FF_DELAY rty && !RTY_O ;
ERR_O <= #`FF_DELAY err && !ERR_O ;
SDATA_O <= #`FF_DELAY sdata_source ;
del_write_out <= #`FF_DELAY WE_I ;
`ifdef HOST
wb_conf_wenable_out <= #`FF_DELAY conf_wenable ;
wb_conf_data_out <= #`FF_DELAY SDATA_I ;
`endif
del_bc_out <= #`FF_DELAY del_bc ;
del_req_out <= #`FF_DELAY del_req ;
del_done_out <= #`FF_DELAY del_done ;
del_burst_out <= #`FF_DELAY del_burst ;
del_in_progress_out <= #`FF_DELAY del_in_progress ;
wb_conf_be_out <= #`FF_DELAY SEL_I ;
wb_data_out <= #`FF_DELAY wb_data ;
wb_cbe_out <= #`FF_DELAY wb_cbe ;
wbw_fifo_wenable_out <= #`FF_DELAY wbw_fifo_wenable ;
wbw_fifo_control_out <= #`FF_DELAY wbw_fifo_control ;
wbr_fifo_renable_out <= #`FF_DELAY wbr_fifo_renable ;
end
end
`else
assign SDATA_O = sdata_source ;
assign ACK_O = ack ;
assign RTY_O = rty ;
assign ERR_O = err ;
// write operation indicator for delayed transaction requests
assign del_write_out = WE_I ;
assign del_bc_out = del_bc ;
assign del_req_out = del_req ; // read request
assign del_done_out = del_done ; // read done
assign del_burst_out = del_burst ;
assign del_in_progress_out = del_in_progress ;
`ifdef HOST
assign wb_conf_data_out = SDATA_I ;
assign wb_conf_wenable_out = conf_wenable ;
`endif
// Configuration space byte enables output
assign wb_conf_be_out = SEL_I ; // just route select lines from WISHBONE to conf space
assign wb_data_out = wb_data ;
assign wb_cbe_out = wb_cbe ;
assign wbw_fifo_wenable_out = wbw_fifo_wenable ; //write enable for WBW_FIFO
assign wbw_fifo_control_out = wbw_fifo_control ; //control bus output for WBW_FIFO
assign wbr_fifo_renable_out = wbr_fifo_renable ; //read enable for wbr_fifo
`endif
endmodule //WB_SLAVE
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -