blob: 9c80a5822afe6de0b19327014f0ae2b883e7cd08 [file] [log] [blame] [edit]
`include "i2c_master.v"
`include "i2c_probe.v"
`include "i2c_scan.v"
`include "simpleuart.v"
`default_nettype none
// ============================================================================
module top
(
input wire clk,
input wire [15:0] sw,
output wire [15:0] led,
input wire rx,
output wire tx,
inout wire jc1, // sda
inout wire jc2, // scl
output wire jc3, // unused
input wire jc4 // unused
);
// ============================================================================
// IOBUFs
wire sda_i;
wire sda_o;
wire sda_t;
wire scl_i;
wire scl_o;
wire scl_t;
IOBUF # (
.IOSTANDARD("LVCMOS33"),
.DRIVE(12),
.SLEW("SLOW")
)
iobuf_sda
(
.I (sda_i),
.O (sda_o),
.T (sda_t),
.IO (jc1)
);
IOBUF # (
.IOSTANDARD("LVCMOS33"),
.DRIVE(12),
.SLEW("SLOW")
)
iobuf_scl
(
.I (scl_i),
.O (scl_o),
.T (scl_t),
.IO (jc2)
);
// ============================================================================
// Clock buffer, reset generator
reg [3:0] rst_sr;
wire rst;
wire clk_g;
initial rst_sr <= 4'hF;
always @(posedge clk_g)
if (sw[0]) rst_sr <= 4'hF;
else rst_sr = {1'b0, rst_sr[3:1]};
assign rst = rst_sr[0];
wire clk_ibuf;
IBUF ibuf (.I(clk), .O(clk_ibuf));
BUFG bufg (.I(clk_ibuf), .O(clk_g));
// ============================================================================
// I2C scanner
wire i2c_scan_trg;
wire i2c_scan_trg_en;
wire i2c_scan_bsy;
// Button synchronizer
reg [3:0] i2c_scan_trg_en_sr;
initial i2c_scan_trg_en_sr <= 4'h0;
always @(posedge clk_g)
i2c_scan_trg_en_sr <= {sw[1], i2c_scan_trg_en_sr[3:1]};
// The scanner
i2c_scan #
(
.UART_PRESCALER (868), // 115200 @100MHz
.I2C_PRESCALER (250) // 100kHz @100MHz
)
i2c_scan
(
.clk (clk_g),
.rst (rst),
.scl_i (scl_o),
.scl_o (scl_i),
.scl_t (scl_t),
.sda_i (sda_o),
.sda_o (sda_i),
.sda_t (sda_t),
.rx (rx),
.tx (tx),
.i_trg (i2c_scan_trg & i2c_scan_trg_en_sr[0]),
.i_bsy (i2c_scan_bsy)
);
// Trigger generator
reg [32:0] trg_cnt;
always @(posedge clk_g)
if (rst) trg_cnt <= 0;
else if (trg_cnt[32]) trg_cnt <= 1 * 100000000; // 1s @100MHz
else trg_cnt <= trg_cnt - 1;
assign i2c_scan_trg = trg_cnt[32];
// ============================================================================
// I/O
assign led[0] = rst;
assign led[1] = i2c_scan_bsy;
assign led[15:2] = sw[15:2];
endmodule