Commit dccb0d8b authored by Andrea Boccardi's avatar Andrea Boccardi

as before (forgot a file)

parent 77de1364
module VmeToWishBone(
input Rst_irq,
input Clk_ik,
output reg [21:0] Adr_obq22,
output reg [31:0] Dat_obq32,
input [31:0] Dat_ib32,
output reg We_oq,
output reg Cyc_oq,
output reg Stb_oq,
input Ack_i,
input [4:0] VmeGa_ib5,
input VmeGap_i,
input VmeAs_ia,
input VmeDs1_ia,
input VmeDs2_ia,
input [5:0] VmeAm_ib6,
input VmeWr_in,
output reg VmeDtAck_oqn,
input VmeLWord_i,
input [31:1] VmeAddr_ib31,
inout [31:0] VmeData_iozb32,
output reg VmeDataOe_oq,
output reg VmeDataDir_oq, //1 set FPGA => VME
input VmeIAckInn_in,
input VmeIAckn_in,
output reg VmeIAckOutn_oqn,
output reg [7:1] VmeIrqn_oqnb7,
input [2:0] IntLevel_ib3,
input [7:0] IrqVector_ib8,
input UseGa_i,
input [4:0] ManualAddress_ib5,
input AssertInterrupt_i,
output reg ClearInt_op);
// Board Base Address
wire GapError = ^{~VmeGap_i, VmeGa_ib5};
wire [4:0] BoardBaseAddr_b5 = (GapError || ~UseGa_i) ? ManualAddress_ib5 : ~VmeGa_ib5;
// Synchronization of DS, AS and IACKIN signals
reg [2:0] Ds1Shr_dq, Ds2Shr_dq, AsShr_dq, IAckInShr_dq;
always @(posedge Clk_ik) Ds1Shr_dq <= {Ds1Shr_dq[1:0], VmeDs1_ia};
always @(posedge Clk_ik) Ds2Shr_dq <= {Ds2Shr_dq[1:0], VmeDs2_ia};
always @(posedge Clk_ik) AsShr_dq <= {AsShr_dq[1:0], VmeAs_ia};
always @(posedge Clk_ik) IAckInShr_dq <= {IAckInShr_dq[1:0], VmeIAckInn_in};
wire a_Ds1_q = Ds1Shr_dq[2];
wire a_Ds2_q = Ds2Shr_dq[2];
wire a_As_q = AsShr_dq[2];
wire a_IAckIn_q = IAckInShr_dq[2];
// Vme accesses detection
wire ValidAm_a = (VmeAm_ib6==6'h0F) || (VmeAm_ib6==6'h0D) || (VmeAm_ib6==6'h0B) || (VmeAm_ib6==6'h09);
wire ValidRWBA_a = VmeAddr_ib31[31:24]=={3'b0, BoardBaseAddr_b5};
wire ValidIntAckBA_a = VmeAddr_ib31[3:1]==IntLevel_ib3;
wire VmeRWStrobes_a = ~a_As_q && ~a_Ds1_q && ~a_Ds2_q;
wire VmeIntAckStrobes_a = ~a_As_q && ~a_Ds1_q && a_Ds2_q;
wire VmeRWAccess_a = VmeRWStrobes_a && ValidRWBA_a && ValidAm_a && VmeIAckn_in && ~VmeLWord_i;
wire VmeIntAckAccess_a = VmeIntAckStrobes_a && ValidIntAckBA_a && ~a_IAckIn_q && ~&VmeIrqn_oqnb7 && VmeIAckOutn_oqn; // if VmeIAckOutn_oqn is low it means we already passed the interrupt to the next board
// Interrupt Request Assertion
always @(posedge Clk_ik) begin
VmeIrqn_oqnb7 <= 7'b111_1111;
if (AssertInterrupt_i) VmeIrqn_oqnb7[IntLevel_ib3] <= 1'b0;
end
// State Machine
reg [1:0] State_q, NextState_a;
localparam s_Idle = 2'b00,
s_Write = 2'b01,
s_Read = 2'b10,
s_IntAck = 2'b11;
always @(posedge Clk_ik) State_q <= Rst_irq ? s_Idle : NextState_a;
always @* begin
NextState_a = State_q;
case (State_q)
s_Idle:
if (VmeRWAccess_a) NextState_a = VmeWr_in ? s_Read : s_Write;
else if (VmeIntAckAccess_a) NextState_a = s_IntAck;
s_Write:
if (~Ack_i && ~Stb_oq && ~VmeRWAccess_a) NextState_a = s_Idle;
s_Read:
if (~Ack_i && ~Stb_oq && ~VmeRWAccess_a) NextState_a = s_Idle;
s_IntAck:
if (a_Ds1_q && a_IAckIn_q) NextState_a = s_Idle;
default:
NextState_a = s_Idle;
endcase
end
reg [31:0] VmeDataReg_qb32;
reg VmeDataRegOe;
assign VmeData_iozb32 = VmeDataRegOe ? VmeDataReg_qb32 : 32'hz;
always @(posedge Clk_ik) begin
if (Rst_irq) begin
Adr_obq22 <= 22'h0;
Dat_obq32 <= 32'h0;
We_oq <= 1'b0;
Stb_oq <= 1'b0;
Cyc_oq <= 1'b0;
VmeDtAck_oqn <= 1'b1;
VmeDataReg_qb32 <= 32'h0;
VmeDataRegOe <= 1'b0;
VmeDataOe_oq <= 1'b0;
VmeDataDir_oq <= 1'b0;
ClearInt_op <= 1'b0;
VmeIAckOutn_oqn <= 1'b1;
end else case (State_q)
s_Idle: begin
Adr_obq22 <= 22'h0;
Dat_obq32 <= 32'h0;
We_oq <= 1'b0;
Stb_oq <= 1'b0;
Cyc_oq <= 1'b0;
VmeDtAck_oqn <= 1'b1;
VmeDataReg_qb32 <= 32'h0;
VmeDataRegOe <= 1'b0;
VmeDataOe_oq <= 1'b1;
VmeDataDir_oq <= 1'b0;
ClearInt_op <= 1'b0;
if (VmeIntAckStrobes_a) VmeIAckOutn_oqn <= (NextState_a==s_IntAck) ? 1'b1 : a_IAckIn_q;
if (NextState_a == s_Write) begin
Adr_obq22 <= VmeAddr_ib31[23:2];
Dat_obq32 <= VmeData_iozb32;
We_oq <= 1'b1;
Stb_oq <= 1'b1;
Cyc_oq <= 1'b1;
end
if (NextState_a == s_Read) begin
Adr_obq22 <= VmeAddr_ib31[23:2];
Stb_oq <= 1'b1;
Cyc_oq <= 1'b1;
VmeDataRegOe <= 1'b0;
VmeDataOe_oq <= 1'b1;
VmeDataDir_oq <= 1'b1;
end
if (NextState_a == s_IntAck) begin
VmeDataReg_qb32 <= {24'h0, IrqVector_ib8};
VmeDataOe_oq <= 1'b1;
VmeDataDir_oq <= 1'b1;
ClearInt_op <= 1'b1;
end
end
s_Write: begin
if (Ack_i) begin
Stb_oq <= 1'b0;
Cyc_oq <= 1'b0;
We_oq <= 1'b0;
VmeDtAck_oqn <= 1'b0;
end
end
s_Read: begin
if (Ack_i && Stb_oq) begin
Stb_oq <= 1'b0;
Cyc_oq <= 1'b0;
VmeDataReg_qb32 <= Dat_ib32;
VmeDataRegOe <= 1'b1;
end
if (~Stb_oq) VmeDtAck_oqn <= 1'b0;
if (NextState_a==s_Idle) VmeDataRegOe <= 1'b0;
end
s_IntAck: begin
ClearInt_op <= 1'b0;
VmeDataRegOe <= 1'b1;
VmeDtAck_oqn <= ~VmeDataRegOe;
if (NextState_a==s_Idle) begin
VmeDataRegOe <= 1'b0;
VmeDtAck_oqn <= 1'b1;
end
end
default: begin
Adr_obq22 <= 22'h0;
Dat_obq32 <= 32'h0;
We_oq <= 1'b0;
Stb_oq <= 1'b0;
Cyc_oq <= 1'b0;
VmeDtAck_oqn <= 1'b1;
VmeDataReg_qb32 <= 32'h0;
VmeDataRegOe <= 1'b0;
VmeDataOe_oq <= 1'b0;
VmeDataDir_oq <= 1'b0;
ClearInt_op <= 1'b0;
VmeIAckOutn_oqn <= 1'b1;
end
endcase
end
endmodule
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment