Commit f074d0b9 authored by Mike Lyons's avatar Mike Lyons

Checking in in-progress SPI. Need to move command decode to SPI clock rather than sysclk.

parent 4ed89c7c
`timescale 1ns / 1ps
//////////////////////////////////////////////////////////////////////////////////
// Company:
// Engineer:
//
// Create Date: 19:24:33 10/18/2011
// Design Name:
// Module Name: spiifc
// Project Name:
// Target Devices:
// Tool versions:
// Description:
//
// Dependencies:
//
// Revision:
// Revision 0.01 - File Created
// Additional Comments:
//
//////////////////////////////////////////////////////////////////////////////////
module spiifc(
Reset,
SysClk,
SPI_CLK,
SPI_MISO,
SPI_MOSI,
SPI_SS,
txMemAddr,
txMemData,
rcMemAddr,
rcMemData,
rcMemWE,
debug_out
);
//
// Parameters
//
parameter AddrBits = 12;
//
// Input/Output defs
//
input Reset;
input SysClk;
input SPI_CLK;
output SPI_MISO;
input SPI_MOSI;
input SPI_SS;
output [AddrBits-1:0] txMemAddr;
input [7:0] txMemData;
output [AddrBits-1:0] rcMemAddr;
output [7:0] rcMemData;
output rcMemWE;
output [7:0] debug_out;
//
// Registers
//
reg rcByte_valid;
wire rcClockBridgeEmpty;
wire readRcByte;
assign getRcByte = ~rcClockBridgeEmpty;
wire rcClockBridgeReadValid;
wire rcClockBridgeFull;
wire [7:0] rcByte;
clock_bridge recvClockBridge (
.rst(Reset), // input rst
.wr_clk(~SPI_CLK), // input wr_clk
.rd_clk(SysClk), // input rd_clk
.din(SPI_MOSI), // input [0 : 0] din
.wr_en(~SPI_SS), // input wr_en
.rd_en(getRcByte), // input rd_en
.dout(rcByte), // output [7 : 0] dout
.full(rcClockBridgeFull), // output full
.empty(rcClockBridgeEmpty), // output empty
.valid(rcClockBridgeReadValid) // output valid
);
always @(posedge SysClk) begin
rcByte_valid <= getRcByte;
end
wire txCmdClkBridgeEmpty;
wire txCmdClkBridgeFull;
wire [7:0] txCmd;
wire txCmdValid;
assign txCmdValid = ~txCmdClkBridgeEmpty;
wire postTxCmd;
assign postTxCmd =
fifo_8bit_to_8bit txCmdClkBridge(
.rst(Reset), // input rst
.wr_clk(SysClk), // input wr_clk
.rd_clk(SPI_CLK), // input rd_clk
.din(din), // input [7 : 0] din
.wr_en(post), // input wr_en
.rd_en(txCmdValid), // input rd_en
.dout(txCmd), // output [7 : 0] dout
.full(txCmdClkBridgeFull), // output full
.empty(txCmdClkBridgeEmpty) // output empty
);
/*
* TRANSMIT: FPGA TO PC
*/
assign SPI_MISO = txMemData[bitIndex];
reg [2:0] bitIndex;
reg [AddrBits-1:0] byteAddr;
assign txMemAddr = byteAddr;
reg [7:0] debug_reg;
assign debug_out = debug_reg;
initial begin
debug_reg <= 8'h00;
//rcState <= 0;
end
//
// Clocked logic
//
always @(posedge SPI_CLK) begin
if (Reset) begin
bitIndex <= 3'd0;
byteAddr <= 0;
end else if (SPI_SS == 1'b0) begin
bitIndex <= bitIndex - 3'd1;
if (bitIndex == 3'd1) begin
byteAddr <= byteAddr + 1;
end
end
end
/*
* RECEIVE: PC TO FPGA
*/
// Detect start of receive
reg ss_prev;
wire ss_negedge;
always @(posedge SysClk) begin
ss_prev <= SPI_SS;
end
assign ss_negedge = (ss_prev == 1'b1 && SPI_SS == 1'b0 ? 1'b1 : 1'b0);
`define RC_MODE_GET_STATUS 8'd0
`define RC_MODE_GET_BUFFER 8'd1
`define RC_MODE_PUT_BUFFER 8'd2
reg [7:0] rcMode;
`define RC_STATE_CMD 8'd0
`define RC_STATE_SIZE 8'd1
`define RC_STATE_PAYLOAD 8'd2
reg [7:0] rcState;
reg [31:0] rcByteCount;
reg [31:0] rcByteSize;
reg [7:0] rcMemData_reg;
reg [AddrBits-1:0] rcMemAddr_reg;
reg rcMemWE_reg;
assign rcMemData = rcMemData_reg;
assign rcMemAddr = rcMemAddr_reg;
assign rcMemWE = rcMemWE_reg;
always @(posedge SysClk) begin
/*
// About to receive
if (ss_negedge) begin
rcBitIndex <= 3'd7;
rcState <= `RC_STATE_CMD;
debug_reg[0] <= 1;
end
// Receiving
if (receiving) begin
rcByte[rcBitIndex] <= SPI_MOSI;
rcBitIndex <= rcBitIndex - 3'd1;
end
rcByte_valid <= (receiving && rcBitIndex == 3'd0 ? 1'b1 : 1'b0);
*/
// Handle the complete incoming byte
if (rcByte_valid) begin
debug_reg[7:4] <= rcByte[3:0];
// First byte: the command
if (`RC_STATE_CMD == rcState || ss_negedge) begin
// Disable writing to the read buffer (will be left on if the prev
// cycle was writing to it)
rcMemWE_reg <= 1'b0;
debug_reg[0] <= 1;
// Decode the SPI command
case (rcByte)
`RC_MODE_GET_STATUS: begin end // no status yet
`RC_MODE_GET_BUFFER: begin rcMode <= `RC_MODE_GET_BUFFER; rcState <= `RC_STATE_SIZE; end
`RC_MODE_PUT_BUFFER: begin rcMode <= `RC_MODE_PUT_BUFFER; rcState <= `RC_STATE_SIZE; end
endcase
// Initialize counters
rcByteCount <= 32'd0;
rcByteSize <= 32'd0;
end
// Record size (in bytes) of payload
if (`RC_STATE_SIZE == rcState) begin
debug_reg[1] <= 1;
case (rcByteCount)
32'd0: begin rcByteSize[31:24] <= rcByte; rcByteCount <= 32'd1; end
32'd1: begin rcByteSize[23:16] <= rcByte; rcByteCount <= 32'd2; end
32'd2: begin rcByteSize[15: 8] <= rcByte; rcByteCount <= 32'd3; end
32'd3: begin
rcByteSize[ 7: 0] <= rcByte;
rcByteCount <= 32'd0;
rcState <= `RC_STATE_PAYLOAD;
rcByteCount <= 32'd0;
if (`RC_MODE_GET_BUFFER == rcMode) begin
// TODO: want reset tx byte addr here probably
end
end
endcase
end
// The payload
if (rcState == `RC_STATE_PAYLOAD) begin
debug_reg[2] <= 1;
case (rcMode)
`RC_MODE_GET_BUFFER: begin
// IGNORE EVERYTHING SO STUFF CAN BE READ OUT
end
`RC_MODE_PUT_BUFFER: begin
//debug_reg[4] <= 1;
rcMemWE_reg <= 1'b1;
rcMemData_reg <= rcByte;
rcMemAddr_reg <= rcByteCount[AddrBits-1:0];
end
endcase
if (rcByteCount == rcByteSize - 1) begin
rcState <= `RC_STATE_CMD;
//debug_reg[5] <= 1;
end else begin
rcByteCount <= rcByteCount + 32'd1;
end
end
end
else begin // not valid byte
if (ss_negedge) begin
rcState <= `RC_STATE_CMD;
end
end
end
//reg [7:0] rcByteReg;
//wire [7:0] rcByte;
//assign rcByte = {rcByteReg[7:1], (SPI_SS == 1'b0 && bitIndex ==
/*
//
// Receive (GPU to SPI)
//
reg SPI_SS_prev_cycle;
// This is the register backing rcByteId. It is always one cycle
// behind the true value of rcByteId, which we have to do a little
// work to get instantaneously correct using wire logic.
reg [31:0] rcByteIdPrev;
wire [31:0] rcByteId;
assign rcByteId = (SPI_SS_prev_cycle == 1 && SPI_SS == 0 ? 32'd0 : 32'd1 + rcByteIdPrev);
// 1 if we're receiving from GPC, 0 if not.
wire isRecv;
assign isRecv = ~SPI_SS;
// Bits to Byte aggregator
reg [2:0] rcBitId;
reg [7:0] rcByte;
reg [31:0] rcSizeBytes;
always @(posedge SPI_CLK) begin
if (1 == isRecv) begin
case (rcByteId)
0: rcSizeBytes[ 7: 0] <=
end
// Update registers for next cycle
SPI_SS_prev_cycle <= SPI_SS;
rcByteId <= rcByteIdPrev;
end
*/
endmodule
`timescale 1ns / 1ps
////////////////////////////////////////////////////////////////////////////////
// Company:
// Engineer:
//
// Create Date: 19:46:21 10/18/2011
// Design Name: spiifc
// Module Name: C:/workspace/robobees/hbp/fpga/spiifc/spiifc_tb.v
// Project Name: spiifc
// Target Device:
// Tool versions:
// Description:
//
// Verilog Test Fixture created by ISE for module: spiifc
//
// Dependencies:
//
// Revision:
// Revision 0.01 - File Created
// Additional Comments:
//
////////////////////////////////////////////////////////////////////////////////
module spiifc_tb;
// Inputs
reg Reset;
reg SPI_CLK;
reg SPI_MOSI;
reg SPI_SS;
reg [7:0] MemData;
// Outputs
wire SPI_MISO;
wire [11:0] MemAddr;
// Memory
reg [7:0] Mem [0:4095];
integer i;
// Instantiate the Unit Under Test (UUT)
spiifc uut (
.Reset(Reset),
.SPI_CLK(SPI_CLK),
.SPI_MISO(SPI_MISO),
.SPI_MOSI(SPI_MOSI),
.SPI_SS(SPI_SS),
.MemAddr(MemAddr),
.MemData(MemData)
);
always @(posedge SPI_CLK) begin
MemData <= Mem[MemAddr];
end
always @(*) begin
#50;
SPI_CLK <= ~SPI_CLK;
end
initial begin
// Initialize memory
for (i = 0; i < 4096; i = i + 2) begin
// Mem[i] <= i[7:0];
Mem[i] <= 8'hFF;
Mem[i+1] <= 8'h00;
end
// Initialize Inputs
Reset = 0;
SPI_CLK = 0;
SPI_MOSI = 0;
SPI_SS = 1;
// Wait 100 ns for global reset to finish
#100;
// Add stimulus here
Reset <= 1'b1;
#100;
Reset <= 1'b0;
#100;
SPI_SS <= 1'b0;
#4000;
SPI_SS <= 1'b1;
#400;
$finish;
end
endmodule
`timescale 1ns / 1ps
////////////////////////////////////////////////////////////////////////////////
// Company:
// Engineer:
//
// Create Date: 11:08:12 02/15/2012
// Design Name: spiifc
// Module Name: C:/workspace/robobees/hbp/fpga/spitest/pcores/spi_v1_00_a/hdl/verilog/spiifc_tb2.v
// Project Name: spi
// Target Device:
// Tool versions:
// Description:
//
// Verilog Test Fixture created by ISE for module: spiifc
//
// Dependencies:
//
// Revision:
// Revision 0.01 - File Created
// Additional Comments:
//
////////////////////////////////////////////////////////////////////////////////
module spiifc_tb2;
// Inputs
reg Reset;
reg SysClk;
reg SPI_CLK;
reg SPI_MOSI;
reg SPI_SS;
reg [7:0] txMemData;
// Outputs
wire SPI_MISO;
wire [11:0] txMemAddr;
wire [11:0] rcMemAddr;
wire [7:0] rcMemData;
wire rcMemWE;
// Instantiate the Unit Under Test (UUT)
spiifc uut (
.Reset(Reset),
.SysClk(SysClk),
.SPI_CLK(SPI_CLK),
.SPI_MISO(SPI_MISO),
.SPI_MOSI(SPI_MOSI),
.SPI_SS(SPI_SS),
.txMemAddr(txMemAddr),
.txMemData(txMemData),
.rcMemAddr(rcMemAddr),
.rcMemData(rcMemData),
.rcMemWE(rcMemWE)
);
task recvByte;
input [7:0] rcByte;
integer rcBitIndex;
begin
$display("%g - spiifc receiving byte '0x%h'", $time, rcByte);
for (rcBitIndex = 0; rcBitIndex < 8; rcBitIndex = rcBitIndex + 1) begin
SPI_MOSI = rcByte[7 - rcBitIndex];
#100;
end
end
endtask
always begin
#20 SysClk = ~SysClk;
end
always begin
#50 SPI_CLK = ~SPI_CLK;
end
integer fdRcBytes;
integer dummy;
integer currRcByte;
integer rcBytesNotEmpty;
reg [8*10:1] rcBytesStr;
initial begin
// Initialize Inputs
Reset = 0;
SysClk = 0;
SPI_CLK = 0;
SPI_MOSI = 0;
SPI_SS = 1;
txMemData = 0;
// Wait 100 ns for global reset to finish
#100;
// Add stimulus here
SPI_SS = 0;
// For each byte, transmit its bits
fdRcBytes = $fopen("rc-bytes.txt", "r");
rcBytesNotEmpty = 1;
while (rcBytesNotEmpty) begin
rcBytesNotEmpty = $fgets(rcBytesStr, fdRcBytes);
if (rcBytesNotEmpty) begin
dummy = $sscanf(rcBytesStr, "%x", currRcByte);
recvByte(currRcByte);
end
end
// Wrap it up.
SPI_SS = 1;
#1000;
$finish;
end
endmodule
//----------------------------------------------------------------------------
// user_logic.vhd - module
//----------------------------------------------------------------------------
//
// ***************************************************************************
// ** Copyright (c) 1995-2011 Xilinx, Inc. All rights reserved. **
// ** **
// ** Xilinx, Inc. **
// ** XILINX IS PROVIDING THIS DESIGN, CODE, OR INFORMATION "AS IS" **
// ** AS A COURTESY TO YOU, SOLELY FOR USE IN DEVELOPING PROGRAMS AND **
// ** SOLUTIONS FOR XILINX DEVICES. BY PROVIDING THIS DESIGN, CODE, **
// ** OR INFORMATION AS ONE POSSIBLE IMPLEMENTATION OF THIS FEATURE, **
// ** APPLICATION OR STANDARD, XILINX IS MAKING NO REPRESENTATION **
// ** THAT THIS IMPLEMENTATION IS FREE FROM ANY CLAIMS OF INFRINGEMENT, **
// ** AND YOU ARE RESPONSIBLE FOR OBTAINING ANY RIGHTS YOU MAY REQUIRE **
// ** FOR YOUR IMPLEMENTATION. XILINX EXPRESSLY DISCLAIMS ANY **
// ** WARRANTY WHATSOEVER WITH RESPECT TO THE ADEQUACY OF THE **
// ** IMPLEMENTATION, INCLUDING BUT NOT LIMITED TO ANY WARRANTIES OR **
// ** REPRESENTATIONS THAT THIS IMPLEMENTATION IS FREE FROM CLAIMS OF **
// ** INFRINGEMENT, IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS **
// ** FOR A PARTICULAR PURPOSE. **
// ** **
// ***************************************************************************
//
//----------------------------------------------------------------------------
// Filename: user_logic.vhd
// Version: 1.00.a
// Description: User logic module.
// Date: Wed Oct 19 16:39:24 2011 (by Create and Import Peripheral Wizard)
// Verilog Standard: Verilog-2001
//----------------------------------------------------------------------------
// Naming Conventions:
// active low signals: "*_n"
// clock signals: "clk", "clk_div#", "clk_#x"
// reset signals: "rst", "rst_n"
// generics: "C_*"
// user defined types: "*_TYPE"
// state machine next state: "*_ns"
// state machine current state: "*_cs"
// combinatorial signals: "*_com"
// pipelined or register delay signals: "*_d#"
// counter signals: "*cnt*"
// clock enable signals: "*_ce"
// internal version of output port: "*_i"
// device pins: "*_pin"
// ports: "- Names begin with Uppercase"
// processes: "*_PROCESS"
// component instantiations: "<ENTITY_>I_<#|FUNC>"
//----------------------------------------------------------------------------
module user_logic
(
// -- ADD USER PORTS BELOW THIS LINE ---------------
// --USER ports added here
SPI_CLK,
SPI_MISO,
SPI_MOSI,
SPI_SS,
DebugLeds,
// -- ADD USER PORTS ABOVE THIS LINE ---------------
// -- DO NOT EDIT BELOW THIS LINE ------------------
// -- Bus protocol ports, do not add to or delete
Bus2IP_Clk, // Bus to IP clock
Bus2IP_Reset, // Bus to IP reset
Bus2IP_Addr, // Bus to IP address bus
Bus2IP_CS, // Bus to IP chip select for user logic memory selection
Bus2IP_RNW, // Bus to IP read/not write
Bus2IP_Data, // Bus to IP data bus
Bus2IP_BE, // Bus to IP byte enables
Bus2IP_RdCE, // Bus to IP read chip enable
Bus2IP_WrCE, // Bus to IP write chip enable
Bus2IP_Burst, // Bus to IP burst-mode qualifier
Bus2IP_BurstLength, // Bus to IP burst length
Bus2IP_RdReq, // Bus to IP read request
Bus2IP_WrReq, // Bus to IP write request
IP2Bus_AddrAck, // IP to Bus address acknowledgement
IP2Bus_Data, // IP to Bus data bus
IP2Bus_RdAck, // IP to Bus read transfer acknowledgement
IP2Bus_WrAck, // IP to Bus write transfer acknowledgement
IP2Bus_Error, // IP to Bus error response
IP2Bus_IntrEvent // IP to Bus interrupt event
// -- DO NOT EDIT ABOVE THIS LINE ------------------
); // user_logic
// -- ADD USER PARAMETERS BELOW THIS LINE ------------
// --USER parameters added here
// -- ADD USER PARAMETERS ABOVE THIS LINE ------------
// -- DO NOT EDIT BELOW THIS LINE --------------------
// -- Bus protocol parameters, do not add to or delete
parameter C_SLV_AWIDTH = 32;
parameter C_SLV_DWIDTH = 32;
parameter C_NUM_REG = 16;
parameter C_NUM_MEM = 1;
parameter C_NUM_INTR = 1;
// -- DO NOT EDIT ABOVE THIS LINE --------------------
// -- ADD USER PORTS BELOW THIS LINE -----------------
// --USER ports added here
input SPI_CLK;
output SPI_MISO;
input SPI_MOSI;
input SPI_SS;
output [0:7] DebugLeds;
// -- ADD USER PORTS ABOVE THIS LINE -----------------
// -- DO NOT EDIT BELOW THIS LINE --------------------
// -- Bus protocol ports, do not add to or delete
input Bus2IP_Clk;
input Bus2IP_Reset;
input [0 : C_SLV_AWIDTH-1] Bus2IP_Addr;
input [0 : C_NUM_MEM-1] Bus2IP_CS;
input Bus2IP_RNW;
input [0 : C_SLV_DWIDTH-1] Bus2IP_Data;
input [0 : C_SLV_DWIDTH/8-1] Bus2IP_BE;
input [0 : C_NUM_REG-1] Bus2IP_RdCE;
input [0 : C_NUM_REG-1] Bus2IP_WrCE;
input Bus2IP_Burst;
input [0 : 8] Bus2IP_BurstLength;
input Bus2IP_RdReq;
input Bus2IP_WrReq;
output IP2Bus_AddrAck;
output [0 : C_SLV_DWIDTH-1] IP2Bus_Data;
output IP2Bus_RdAck;
output IP2Bus_WrAck;
output IP2Bus_Error;
output [0 : C_NUM_INTR-1] IP2Bus_IntrEvent;
// -- DO NOT EDIT ABOVE THIS LINE --------------------
//----------------------------------------------------------------------------
// Implementation
//----------------------------------------------------------------------------
// --USER nets declarations added here, as needed for user logic
assign DebugLeds = debugLedsReg;
reg [7:0] debugLedsReg;
// Nets for user logic slave model s/w accessible register example
reg [0 : C_SLV_DWIDTH-1] slv_reg0;
reg [0 : C_SLV_DWIDTH-1] slv_reg1;
reg [0 : C_SLV_DWIDTH-1] slv_reg2;
reg [0 : C_SLV_DWIDTH-1] slv_reg3;
reg [0 : C_SLV_DWIDTH-1] slv_reg4;
reg [0 : C_SLV_DWIDTH-1] slv_reg5;
reg [0 : C_SLV_DWIDTH-1] slv_reg6;
reg [0 : C_SLV_DWIDTH-1] slv_reg7;
reg [0 : C_SLV_DWIDTH-1] slv_reg8;
reg [0 : C_SLV_DWIDTH-1] slv_reg9;
reg [0 : C_SLV_DWIDTH-1] slv_reg10;
reg [0 : C_SLV_DWIDTH-1] slv_reg11;
reg [0 : C_SLV_DWIDTH-1] slv_reg12;
reg [0 : C_SLV_DWIDTH-1] slv_reg13;
reg [0 : C_SLV_DWIDTH-1] slv_reg14;
reg [0 : C_SLV_DWIDTH-1] slv_reg15;
wire [0 : 15] slv_reg_write_sel;
wire [0 : 15] slv_reg_read_sel;
reg [0 : C_SLV_DWIDTH-1] slv_ip2bus_data;
wire slv_read_ack;
wire slv_write_ack;
integer byte_index, bit_index;
// --USER logic implementation added here
wire [11:0] SpiIfcMemAddr;
wire [7:0] SpiIfcMemData;
spiifc spiIfc(
.Reset(Bus2IP_Reset),
.SPI_CLK(SPI_CLK),
.SPI_MISO(SPI_MISO),
.SPI_MOSI(SPI_MOSI),
.SPI_SS(SPI_SS),
.txMemAddr(SpiIfcMemAddr),
.txMemData(SpiIfcMemData)
);
wire [31:0] douta_dummy;
wire [ 7:0] dinb_dummy;
assign dinb_dummy = 8'h00;
wire [11:0] byteAddr;
spimem your_instance_name (
.clka(Bus2IP_Clk), // input clka
.ena(Bus2IP_CS[0] & (~Bus2IP_RNW) & Bus2IP_WrReq), // input ena
.wea(1'b1), // input [0 : 0] wea
.addra({Bus2IP_Addr[20:29]}), // input [9 : 0] addra
.dina({Bus2IP_Data}), // input [31 : 0] dina
.douta(douta_dummy), // output [31 : 0] douta
.clkb(SPI_CLK), // input clkb
.enb(1'b1), // input enb
.web(1'b0), // input [0 : 0] web
.addrb(SpiIfcMemAddr), // input [11 : 0] addrb
.dinb(dinb_dummy), // input [7 : 0] dinb
.doutb(SpiIfcMemData) // output [7 : 0] doutb
);
// ------------------------------------------------------
// Example code to read/write user logic slave model s/w accessible registers
//
// Note:
// The example code presented here is to show you one way of reading/writing
// software accessible registers implemented in the user logic slave model.
// Each bit of the Bus2IP_WrCE/Bus2IP_RdCE signals is configured to correspond
// to one software accessible register by the top level template. For example,
// if you have four 32 bit software accessible registers in the user logic,
// you are basically operating on the following memory mapped registers:
//
// Bus2IP_WrCE/Bus2IP_RdCE Memory Mapped Register
// "1000" C_BASEADDR + 0x0
// "0100" C_BASEADDR + 0x4
// "0010" C_BASEADDR + 0x8
// "0001" C_BASEADDR + 0xC
//
// ------------------------------------------------------
assign
slv_reg_write_sel = Bus2IP_WrCE[0:15],
slv_reg_read_sel = Bus2IP_RdCE[0:15],
slv_write_ack = Bus2IP_WrCE[0] || Bus2IP_WrCE[1] || Bus2IP_WrCE[2] || Bus2IP_WrCE[3] || Bus2IP_WrCE[4] || Bus2IP_WrCE[5] || Bus2IP_WrCE[6] || Bus2IP_WrCE[7] || Bus2IP_WrCE[8] || Bus2IP_WrCE[9] || Bus2IP_WrCE[10] || Bus2IP_WrCE[11] || Bus2IP_WrCE[12] || Bus2IP_WrCE[13] || Bus2IP_WrCE[14] || Bus2IP_WrCE[15],
slv_read_ack = Bus2IP_RdCE[0] || Bus2IP_RdCE[1] || Bus2IP_RdCE[2] || Bus2IP_RdCE[3] || Bus2IP_RdCE[4] || Bus2IP_RdCE[5] || Bus2IP_RdCE[6] || Bus2IP_RdCE[7] || Bus2IP_RdCE[8] || Bus2IP_RdCE[9] || Bus2IP_RdCE[10] || Bus2IP_RdCE[11] || Bus2IP_RdCE[12] || Bus2IP_RdCE[13] || Bus2IP_RdCE[14] || Bus2IP_RdCE[15];
// implement slave model register(s)
always @( posedge Bus2IP_Clk )
begin: SLAVE_REG_WRITE_PROC
debugLedsReg <= {Bus2IP_CS[0], Bus2IP_RNW, Bus2IP_WrReq, IP2Bus_WrAck, 3'b0011};
if ( Bus2IP_Reset == 1 )
begin
slv_reg0 <= 0;
slv_reg1 <= 0;
slv_reg2 <= 0;
slv_reg3 <= 0;
slv_reg4 <= 0;
slv_reg5 <= 0;
slv_reg6 <= 0;
slv_reg7 <= 0;
slv_reg8 <= 0;
slv_reg9 <= 0;
slv_reg10 <= 0;
slv_reg11 <= 0;
slv_reg12 <= 0;
slv_reg13 <= 0;
slv_reg14 <= 0;
slv_reg15 <= 0;
end
else
case ( slv_reg_write_sel )
16'b1000000000000000 :
for ( byte_index = 0; byte_index <= (C_SLV_DWIDTH/8)-1; byte_index = byte_index+1 )
if ( Bus2IP_BE[byte_index] == 1 )
for ( bit_index = byte_index*8; bit_index <= byte_index*8+7; bit_index = bit_index+1 )
slv_reg0[bit_index] <= Bus2IP_Data[bit_index];
16'b0100000000000000 :
for ( byte_index = 0; byte_index <= (C_SLV_DWIDTH/8)-1; byte_index = byte_index+1 )
if ( Bus2IP_BE[byte_index] == 1 )
for ( bit_index = byte_index*8; bit_index <= byte_index*8+7; bit_index = bit_index+1 )
slv_reg1[bit_index] <= Bus2IP_Data[bit_index];
16'b0010000000000000 :
for ( byte_index = 0; byte_index <= (C_SLV_DWIDTH/8)-1; byte_index = byte_index+1 )
if ( Bus2IP_BE[byte_index] == 1 )
for ( bit_index = byte_index*8; bit_index <= byte_index*8+7; bit_index = bit_index+1 )
slv_reg2[bit_index] <= Bus2IP_Data[bit_index];
16'b0001000000000000 :
for ( byte_index = 0; byte_index <= (C_SLV_DWIDTH/8)-1; byte_index = byte_index+1 )
if ( Bus2IP_BE[byte_index] == 1 )
for ( bit_index = byte_index*8; bit_index <= byte_index*8+7; bit_index = bit_index+1 )
slv_reg3[bit_index] <= Bus2IP_Data[bit_index];
16'b0000100000000000 :
for ( byte_index = 0; byte_index <= (C_SLV_DWIDTH/8)-1; byte_index = byte_index+1 )
if ( Bus2IP_BE[byte_index] == 1 )
for ( bit_index = byte_index*8; bit_index <= byte_index*8+7; bit_index = bit_index+1 )
slv_reg4[bit_index] <= Bus2IP_Data[bit_index];
16'b0000010000000000 :
for ( byte_index = 0; byte_index <= (C_SLV_DWIDTH/8)-1; byte_index = byte_index+1 )
if ( Bus2IP_BE[byte_index] == 1 )
for ( bit_index = byte_index*8; bit_index <= byte_index*8+7; bit_index = bit_index+1 )
slv_reg5[bit_index] <= Bus2IP_Data[bit_index];
16'b0000001000000000 :
for ( byte_index = 0; byte_index <= (C_SLV_DWIDTH/8)-1; byte_index = byte_index+1 )
if ( Bus2IP_BE[byte_index] == 1 )
for ( bit_index = byte_index*8; bit_index <= byte_index*8+7; bit_index = bit_index+1 )
slv_reg6[bit_index] <= Bus2IP_Data[bit_index];
16'b0000000100000000 :
for ( byte_index = 0; byte_index <= (C_SLV_DWIDTH/8)-1; byte_index = byte_index+1 )
if ( Bus2IP_BE[byte_index] == 1 )
for ( bit_index = byte_index*8; bit_index <= byte_index*8+7; bit_index = bit_index+1 )
slv_reg7[bit_index] <= Bus2IP_Data[bit_index];
16'b0000000010000000 :
for ( byte_index = 0; byte_index <= (C_SLV_DWIDTH/8)-1; byte_index = byte_index+1 )
if ( Bus2IP_BE[byte_index] == 1 )
for ( bit_index = byte_index*8; bit_index <= byte_index*8+7; bit_index = bit_index+1 )
slv_reg8[bit_index] <= Bus2IP_Data[bit_index];
16'b0000000001000000 :
for ( byte_index = 0; byte_index <= (C_SLV_DWIDTH/8)-1; byte_index = byte_index+1 )
if ( Bus2IP_BE[byte_index] == 1 )
for ( bit_index = byte_index*8; bit_index <= byte_index*8+7; bit_index = bit_index+1 )
slv_reg9[bit_index] <= Bus2IP_Data[bit_index];
16'b0000000000100000 :
for ( byte_index = 0; byte_index <= (C_SLV_DWIDTH/8)-1; byte_index = byte_index+1 )
if ( Bus2IP_BE[byte_index] == 1 )
for ( bit_index = byte_index*8; bit_index <= byte_index*8+7; bit_index = bit_index+1 )
slv_reg10[bit_index] <= Bus2IP_Data[bit_index];
16'b0000000000010000 :
for ( byte_index = 0; byte_index <= (C_SLV_DWIDTH/8)-1; byte_index = byte_index+1 )
if ( Bus2IP_BE[byte_index] == 1 )
for ( bit_index = byte_index*8; bit_index <= byte_index*8+7; bit_index = bit_index+1 )
slv_reg11[bit_index] <= Bus2IP_Data[bit_index];
16'b0000000000001000 :
for ( byte_index = 0; byte_index <= (C_SLV_DWIDTH/8)-1; byte_index = byte_index+1 )
if ( Bus2IP_BE[byte_index] == 1 )
for ( bit_index = byte_index*8; bit_index <= byte_index*8+7; bit_index = bit_index+1 )
slv_reg12[bit_index] <= Bus2IP_Data[bit_index];
16'b0000000000000100 :
for ( byte_index = 0; byte_index <= (C_SLV_DWIDTH/8)-1; byte_index = byte_index+1 )
if ( Bus2IP_BE[byte_index] == 1 )
for ( bit_index = byte_index*8; bit_index <= byte_index*8+7; bit_index = bit_index+1 )
slv_reg13[bit_index] <= Bus2IP_Data[bit_index];
16'b0000000000000010 :
for ( byte_index = 0; byte_index <= (C_SLV_DWIDTH/8)-1; byte_index = byte_index+1 )
if ( Bus2IP_BE[byte_index] == 1 )
for ( bit_index = byte_index*8; bit_index <= byte_index*8+7; bit_index = bit_index+1 )
slv_reg14[bit_index] <= Bus2IP_Data[bit_index];
16'b0000000000000001 :
for ( byte_index = 0; byte_index <= (C_SLV_DWIDTH/8)-1; byte_index = byte_index+1 )
if ( Bus2IP_BE[byte_index] == 1 )
for ( bit_index = byte_index*8; bit_index <= byte_index*8+7; bit_index = bit_index+1 )
slv_reg15[bit_index] <= Bus2IP_Data[bit_index];
default : ;
endcase
end // SLAVE_REG_WRITE_PROC
// implement slave model register read mux
always @( slv_reg_read_sel or slv_reg0 or slv_reg1 or slv_reg2 or slv_reg3 or slv_reg4 or slv_reg5 or slv_reg6 or slv_reg7 or slv_reg8 or slv_reg9 or slv_reg10 or slv_reg11 or slv_reg12 or slv_reg13 or slv_reg14 or slv_reg15 )
begin: SLAVE_REG_READ_PROC
case ( slv_reg_read_sel )
16'b1000000000000000 : slv_ip2bus_data <= slv_reg0;
16'b0100000000000000 : slv_ip2bus_data <= slv_reg1;
16'b0010000000000000 : slv_ip2bus_data <= slv_reg2;
16'b0001000000000000 : slv_ip2bus_data <= slv_reg3;
16'b0000100000000000 : slv_ip2bus_data <= slv_reg4;
16'b0000010000000000 : slv_ip2bus_data <= slv_reg5;
16'b0000001000000000 : slv_ip2bus_data <= slv_reg6;
16'b0000000100000000 : slv_ip2bus_data <= slv_reg7;
16'b0000000010000000 : slv_ip2bus_data <= slv_reg8;
16'b0000000001000000 : slv_ip2bus_data <= slv_reg9;
16'b0000000000100000 : slv_ip2bus_data <= slv_reg10;
16'b0000000000010000 : slv_ip2bus_data <= slv_reg11;
16'b0000000000001000 : slv_ip2bus_data <= slv_reg12;
16'b0000000000000100 : slv_ip2bus_data <= slv_reg13;
16'b0000000000000010 : slv_ip2bus_data <= slv_reg14;
16'b0000000000000001 : slv_ip2bus_data <= slv_reg15;
default : slv_ip2bus_data <= 0;
endcase
end // SLAVE_REG_READ_PROC
// ------------------------------------------------------------
// Example code to drive IP to Bus signals
// ------------------------------------------------------------
assign IP2Bus_AddrAck = slv_write_ack || slv_read_ack;
assign IP2Bus_Data = slv_ip2bus_data;
assign IP2Bus_WrAck = slv_write_ack;
assign IP2Bus_RdAck = slv_read_ack;
assign IP2Bus_Error = 0;
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