demo: basic lm32 design

parent aa250eba
This diff is collapsed.
/*
* Milkymist VJ SoC
* Copyright (C) 2007, 2008, 2009, 2011 Sebastien Bourdeauducq
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, version 3 of the License.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
/*
* System clock frequency in Hz.
*/
`define CLOCK_FREQUENCY 125000000
/*
* System clock period in ns (must be in sync with CLOCK_FREQUENCY).
*/
`define CLOCK_PERIOD 8
/*
* Default baudrate for the debug UART.
*/
`define BAUD_RATE 115200
/*
* Milkymist VJ SoC
* Copyright (C) 2007, 2008, 2009, 2010 Sebastien Bourdeauducq
* Copyright (C) 2011 CERN
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, version 3 of the License.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
`include "setup.v"
module system(
input clkin,
input resetin,
// UART
input uart_rxd,
output uart_txd,
// GPIO
input [2:0] btn,
output [1:0] led
);
//------------------------------------------------------------------
// Clock and Reset Generation
//------------------------------------------------------------------
wire sys_clk;
wire hard_reset;
assign sys_clk = clkin;
`ifndef SIMULATION
/* Synchronize the reset input */
reg rst0;
reg rst1;
always @(posedge sys_clk) rst0 <= resetin;
always @(posedge sys_clk) rst1 <= rst0;
/* Debounce it
* and generate power-on reset.
*/
reg [19:0] rst_debounce;
reg sys_rst;
initial rst_debounce <= 20'hFFFFF;
initial sys_rst <= 1'b1;
always @(posedge sys_clk) begin
if(rst1 | hard_reset)
rst_debounce <= 20'hFFFFF;
else if(rst_debounce != 20'd0)
rst_debounce <= rst_debounce - 20'd1;
sys_rst <= rst_debounce != 20'd0;
end
`else
wire sys_rst;
assign sys_rst = resetin;
`endif
//------------------------------------------------------------------
// Wishbone master wires
//------------------------------------------------------------------
wire [31:0] cpuibus_adr,
cpudbus_adr;
wire [2:0] cpuibus_cti,
cpudbus_cti;
wire [31:0] cpuibus_dat_r,
cpudbus_dat_r,
cpudbus_dat_w;
wire [3:0] cpudbus_sel;
wire cpudbus_we;
wire cpuibus_cyc,
cpudbus_cyc;
wire cpuibus_stb,
cpudbus_stb;
wire cpuibus_ack,
cpudbus_ack;
//------------------------------------------------------------------
// Wishbone slave wires
//------------------------------------------------------------------
wire [31:0] brg_adr,
bram_adr,
csrbrg_adr;
wire [2:0] brg_cti,
bram_cti;
wire [31:0] bram_dat_r,
bram_dat_w,
csrbrg_dat_r,
csrbrg_dat_w;
wire [3:0] bram_sel;
wire bram_we,
csrbrg_we,
aceusb_we;
wire bram_cyc,
csrbrg_cyc;
wire bram_stb,
csrbrg_stb;
wire bram_ack,
csrbrg_ack;
//---------------------------------------------------------------------------
// Wishbone switch
//---------------------------------------------------------------------------
conbus #(
.s_addr_w(3),
.s0_addr(3'b000), // bram 0x00000000
.s1_addr(3'b001), // free 0x20000000
.s2_addr(3'b010), // free 0x40000000
.s3_addr(3'b100), // CSR bridge 0x80000000
.s4_addr(3'b101) // free 0xa0000000
) conbus (
.sys_clk(sys_clk),
.sys_rst(sys_rst),
// Master 0
.m0_dat_i(32'hx),
.m0_dat_o(cpuibus_dat_r),
.m0_adr_i(cpuibus_adr),
.m0_cti_i(cpuibus_cti),
.m0_we_i(1'b0),
.m0_sel_i(4'hf),
.m0_cyc_i(cpuibus_cyc),
.m0_stb_i(cpuibus_stb),
.m0_ack_o(cpuibus_ack),
// Master 1
.m1_dat_i(cpudbus_dat_w),
.m1_dat_o(cpudbus_dat_r),
.m1_adr_i(cpudbus_adr),
.m1_cti_i(cpudbus_cti),
.m1_we_i(cpudbus_we),
.m1_sel_i(cpudbus_sel),
.m1_cyc_i(cpudbus_cyc),
.m1_stb_i(cpudbus_stb),
.m1_ack_o(cpudbus_ack),
// Master 2
.m2_dat_i(32'bx),
.m2_dat_o(),
.m2_adr_i(32'bx),
.m2_cti_i(3'bx),
.m2_we_i(1'bx),
.m2_sel_i(4'bx),
.m2_cyc_i(1'b0),
.m2_stb_i(1'b0),
.m2_ack_o(),
// Master 3
.m3_dat_i(32'bx),
.m3_dat_o(),
.m3_adr_i(32'bx),
.m3_cti_i(3'bx),
.m3_we_i(1'bx),
.m3_sel_i(4'bx),
.m3_cyc_i(1'b0),
.m3_stb_i(1'b0),
.m3_ack_o(),
// Master 4
.m4_dat_i(32'bx),
.m4_dat_o(),
.m4_adr_i(32'bx),
.m4_cti_i(3'bx),
.m4_we_i(1'bx),
.m4_sel_i(4'bx),
.m4_cyc_i(1'b0),
.m4_stb_i(1'b0),
.m4_ack_o(),
// Slave 0
.s0_dat_i(bram_dat_r),
.s0_dat_o(bram_dat_w),
.s0_adr_o(bram_adr),
.s0_cti_o(bram_cti),
.s0_sel_o(bram_sel),
.s0_we_o(bram_we),
.s0_cyc_o(bram_cyc),
.s0_stb_o(bram_stb),
.s0_ack_i(bram_ack),
// Slave 1
.s1_dat_i(32'bx),
.s1_adr_o(),
.s1_cyc_o(),
.s1_stb_o(),
.s1_ack_i(1'b0),
// Slave 2
.s2_dat_i(32'bx),
.s2_dat_o(),
.s2_adr_o(),
.s2_cti_o(),
.s2_sel_o(),
.s2_we_o(),
.s2_cyc_o(),
.s2_stb_o(),
.s2_ack_i(1'b0),
// Slave 3
.s3_dat_i(csrbrg_dat_r),
.s3_dat_o(csrbrg_dat_w),
.s3_adr_o(csrbrg_adr),
.s3_we_o(csrbrg_we),
.s3_cyc_o(csrbrg_cyc),
.s3_stb_o(csrbrg_stb),
.s3_ack_i(csrbrg_ack),
// Slave 4
.s4_dat_i(32'bx),
.s4_dat_o(),
.s4_adr_o(),
.s4_we_o(),
.s4_cyc_o(),
.s4_stb_o(),
.s4_ack_i(1'b0)
);
//------------------------------------------------------------------
// CSR bus
//------------------------------------------------------------------
wire [13:0] csr_a;
wire csr_we;
wire [31:0] csr_dw;
wire [31:0] csr_dr_uart,
csr_dr_sysctl;
//---------------------------------------------------------------------------
// WISHBONE to CSR bridge
//---------------------------------------------------------------------------
csrbrg csrbrg(
.sys_clk(sys_clk),
.sys_rst(sys_rst),
.wb_adr_i(csrbrg_adr),
.wb_dat_i(csrbrg_dat_w),
.wb_dat_o(csrbrg_dat_r),
.wb_cyc_i(csrbrg_cyc),
.wb_stb_i(csrbrg_stb),
.wb_we_i(csrbrg_we),
.wb_ack_o(csrbrg_ack),
.csr_a(csr_a),
.csr_we(csr_we),
.csr_do(csr_dw),
/* combine all slave->master data lines with an OR */
.csr_di(
csr_dr_uart
|csr_dr_sysctl
)
);
//---------------------------------------------------------------------------
// Interrupts
//---------------------------------------------------------------------------
wire gpio_irq;
wire timer0_irq;
wire timer1_irq;
wire uartrx_irq;
wire uarttx_irq;
wire [31:0] cpu_interrupt;
assign cpu_interrupt = {27'd0,
uarttx_irq,
uartrx_irq,
timer1_irq,
timer0_irq,
gpio_irq
};
//---------------------------------------------------------------------------
// LM32 CPU
//---------------------------------------------------------------------------
lm32_top cpu(
.clk_i(sys_clk),
.rst_i(sys_rst),
.interrupt(cpu_interrupt),
.I_ADR_O(cpuibus_adr),
.I_DAT_I(cpuibus_dat_r),
.I_DAT_O(),
.I_SEL_O(),
.I_CYC_O(cpuibus_cyc),
.I_STB_O(cpuibus_stb),
.I_ACK_I(cpuibus_ack),
.I_WE_O(),
.I_CTI_O(cpuibus_cti),
.I_LOCK_O(),
.I_BTE_O(),
.I_ERR_I(1'b0),
.I_RTY_I(1'b0),
.D_ADR_O(cpudbus_adr),
.D_DAT_I(cpudbus_dat_r),
.D_DAT_O(cpudbus_dat_w),
.D_SEL_O(cpudbus_sel),
.D_CYC_O(cpudbus_cyc),
.D_STB_O(cpudbus_stb),
.D_ACK_I(cpudbus_ack),
.D_WE_O (cpudbus_we),
.D_CTI_O(cpudbus_cti),
.D_LOCK_O(),
.D_BTE_O(),
.D_ERR_I(1'b0),
.D_RTY_I(1'b0)
);
//---------------------------------------------------------------------------
// BRAM
//---------------------------------------------------------------------------
bram #(
.adr_width(14)
) bram (
.sys_clk(sys_clk),
.sys_rst(sys_rst),
.wb_adr_i(bram_adr),
.wb_dat_o(bram_dat_r),
.wb_dat_i(bram_dat_w),
.wb_sel_i(bram_sel),
.wb_stb_i(bram_stb),
.wb_cyc_i(bram_cyc),
.wb_ack_o(bram_ack),
.wb_we_i(bram_we)
);
//---------------------------------------------------------------------------
// UART
//---------------------------------------------------------------------------
uart #(
.csr_addr(4'h0),
.clk_freq(`CLOCK_FREQUENCY),
.baud(`BAUD_RATE)
) uart (
.sys_clk(sys_clk),
.sys_rst(sys_rst),
.csr_a(csr_a),
.csr_we(csr_we),
.csr_di(csr_dw),
.csr_do(csr_dr_uart),
.rx_irq(uartrx_irq),
.tx_irq(uarttx_irq),
.uart_rxd(uart_rxd),
.uart_txd(uart_txd)
);
//---------------------------------------------------------------------------
// System Controller
//---------------------------------------------------------------------------
wire [13:0] gpio_outputs;
sysctl #(
.csr_addr(4'h1),
.ninputs(3),
.noutputs(2),
.systemid(32'h53504543) /* SPEC */
) sysctl (
.sys_clk(sys_clk),
.sys_rst(sys_rst),
.gpio_irq(gpio_irq),
.timer0_irq(timer0_irq),
.timer1_irq(timer1_irq),
.csr_a(csr_a),
.csr_we(csr_we),
.csr_di(csr_dw),
.csr_do(csr_dr_sysctl),
.gpio_inputs(btn),
.gpio_outputs(led),
.hard_reset(hard_reset)
);
endmodule
BOARD_SRC=$(wildcard $(BOARD_DIR)/*.v)
CONBUS_SRC=$(wildcard $(CORES_DIR)/conbus/rtl/*.v)
LM32_SRC= \
$(CORES_DIR)/lm32/rtl/lm32_cpu.v \
$(CORES_DIR)/lm32/rtl/lm32_instruction_unit.v \
$(CORES_DIR)/lm32/rtl/lm32_decoder.v \
$(CORES_DIR)/lm32/rtl/lm32_load_store_unit.v \
$(CORES_DIR)/lm32/rtl/lm32_adder.v \
$(CORES_DIR)/lm32/rtl/lm32_addsub.v \
$(CORES_DIR)/lm32/rtl/lm32_logic_op.v \
$(CORES_DIR)/lm32/rtl/lm32_shifter.v \
$(CORES_DIR)/lm32/rtl/lm32_interrupt.v \
$(CORES_DIR)/lm32/rtl/lm32_top.v
CSRBRG_SRC=$(wildcard $(CORES_DIR)/csrbrg/rtl/*.v)
BRAM_SRC=$(wildcard $(CORES_DIR)/bram/rtl/*.v)
UART_SRC=$(wildcard $(CORES_DIR)/uart/rtl/*.v)
SYSCTL_SRC=$(wildcard $(CORES_DIR)/sysctl/rtl/*.v)
CORES_SRC=$(CONBUS_SRC) $(LM32_SRC) $(CSRBRG_SRC) $(BRAM_SRC) $(UART_SRC) $(SYSCTL_SRC)
BOARD_DIR=../rtl
CORES_DIR=../../../cores
include ../sources.mak
SRC=$(BOARD_SRC) $(CORES_SRC)
all: build/system.bit
build/system.ucf: common.ucf xst.ucf
cat common.ucf xst.ucf > build/system.ucf
build/system.prj: $(SRC)
rm -f build/system.prj
for i in `echo $^`; do \
echo "verilog work ../$$i" >> build/system.prj; \
done
build/system.ngc: build/system.prj
cd build && xst -ifn ../system.xst
build/system.ngd: build/system.ngc build/system.ucf
cd build && ngdbuild -uc system.ucf system.ngc
include common.mak
timing: build/system-routed.twr
load: build/system.bit
cd build && impact -batch ../load.cmd
build/system.ncd: build/system.ngd
cd build && map -ol high -w system.ngd
build/system-routed.ncd: build/system.ncd
cd build && par -ol high -w system.ncd system-routed.ncd
build/system.bit: build/system-routed.ncd
cd build && bitgen -w system-routed.ncd system.bit
build/system-routed.twr: build/system-routed.ncd
cd build && trce -v 10 system-routed.ncd system.pcf
clean:
rm -rf build/*
.PHONY: timing usage load clean
# ==== Clock input ====
NET "clkin" TNM_NET = CLK_125MHZ;
TIMESPEC TS_CLK_125MHZ = PERIOD CLK_125MHZ 8 ns;
setMode -bscan
setCable -p auto
identify
assignfile -p 1 -file system.bit
program -p 1
quit
run
-ifn system.prj
-top system
-ifmt MIXED
-opt_mode SPEED
-opt_level 2
-ofn system.ngc
-p xc6slx45t-fgg484-2
TEX=bram.tex
DVI=$(TEX:.tex=.dvi)
PS=$(TEX:.tex=.ps)
PDF=$(TEX:.tex=.pdf)
AUX=$(TEX:.tex=.aux)
LOG=$(TEX:.tex=.log)
all: $(PDF)
%.dvi: %.tex
latex $<
%.ps: %.dvi
dvips $<
%.pdf: %.ps
ps2pdf $<
clean:
rm -f $(DVI) $(PS) $(PDF) $(AUX) $(LOG)
.PHONY: clean
\documentclass[a4paper,11pt]{article}
\usepackage{fullpage}
\usepackage[latin1]{inputenc}
\usepackage[T1]{fontenc}
\usepackage[normalem]{ulem}
\usepackage[english]{babel}
\usepackage{listings,babel}
\lstset{breaklines=true,basicstyle=\ttfamily}
\usepackage{graphicx}
\usepackage{moreverb}
\usepackage{url}
\title{Wishbone Block RAM}
\author{S\'ebastien Bourdeauducq}
\date{December 2009}
\begin{document}
\setlength{\parindent}{0pt}
\setlength{\parskip}{5pt}
\maketitle{}
\section{Specifications}
This core creates 32-bit storage RAM on the Wishbone bus by using FPGA Block RAM.
Byte-wide writes are supported. Burst access is not supported.
The typical use case is to provide initial memory for softcore CPUs.
\section{Using the core}
You should specify the block RAM storage depth, in bytes, by using the \verb!adr_width! parameter.
\section*{Copyright notice}
Copyright \copyright 2007-2009 S\'ebastien Bourdeauducq. \\
Permission is granted to copy, distribute and/or modify this document under the terms of the GNU Free Documentation License, Version 1.3; with no Invariant Sections, no Front-Cover Texts, and no Back-Cover Texts. A copy of the license is included in the LICENSE.FDL file at the root of the Milkymist source distribution.
\end{document}
/*
* Milkymist VJ SoC
* Copyright (C) 2007, 2008, 2009 Sebastien Bourdeauducq
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, version 3 of the License.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
module bram #(
parameter adr_width = 11 // in bytes
) (
input sys_clk,
input sys_rst,
input wb_stb_i,
input wb_cyc_i,
input wb_we_i,
output reg wb_ack_o,
input [31:0] wb_adr_i,
output [31:0] wb_dat_o,
input [31:0] wb_dat_i,
input [3:0] wb_sel_i
);
//-----------------------------------------------------------------
// Storage depth in 32 bit words
//-----------------------------------------------------------------
parameter word_width = adr_width - 2;
parameter word_depth = (1 << word_width);
//-----------------------------------------------------------------
// Actual RAM
//-----------------------------------------------------------------
reg [7:0] ram0 [0:word_depth-1];
reg [7:0] ram1 [0:word_depth-1];
reg [7:0] ram2 [0:word_depth-1];
reg [7:0] ram3 [0:word_depth-1];
wire [word_width-1:0] adr;
wire [7:0] ram0di;
wire ram0we;
wire [7:0] ram1di;
wire ram1we;
wire [7:0] ram2di;
wire ram2we;
wire [7:0] ram3di;
wire ram3we;
reg [7:0] ram0do;
reg [7:0] ram1do;
reg [7:0] ram2do;
reg [7:0] ram3do;
always @(posedge sys_clk) begin
if(ram0we)
ram0[adr] <= ram0di;
ram0do <= ram0[adr];
end
always @(posedge sys_clk) begin
if(ram1we)
ram1[adr] <= ram1di;
ram1do <= ram1[adr];
end
always @(posedge sys_clk) begin
if(ram2we)
ram2[adr] <= ram2di;
ram2do <= ram2[adr];
end
always @(posedge sys_clk) begin
if(ram3we)
ram3[adr] <= ram3di;
ram3do <= ram3[adr];
end
assign ram0we = wb_cyc_i & wb_stb_i & wb_we_i & wb_sel_i[0];
assign ram1we = wb_cyc_i & wb_stb_i & wb_we_i & wb_sel_i[1];
assign ram2we = wb_cyc_i & wb_stb_i & wb_we_i & wb_sel_i[2];
assign ram3we = wb_cyc_i & wb_stb_i & wb_we_i & wb_sel_i[3];
assign ram0di = wb_dat_i[7:0];
assign ram1di = wb_dat_i[15:8];
assign ram2di = wb_dat_i[23:16];
assign ram3di = wb_dat_i[31:24];
assign wb_dat_o = {ram3do, ram2do, ram1do, ram0do};
assign adr = wb_adr_i[adr_width-1:2];
always @(posedge sys_clk) begin
if(sys_rst)
wb_ack_o <= 1'b0;
else begin
if(wb_cyc_i & wb_stb_i)
wb_ack_o <= ~wb_ack_o;
else
wb_ack_o <= 1'b0;
end
end
endmodule
TEX=conbus.tex
DVI=$(TEX:.tex=.dvi)
PS=$(TEX:.tex=.ps)
PDF=$(TEX:.tex=.pdf)
AUX=$(TEX:.tex=.aux)
LOG=$(TEX:.tex=.log)
all: $(PDF)
%.dvi: %.tex
latex $<
%.ps: %.dvi
dvips $<
%.pdf: %.ps
ps2pdf $<
clean:
rm -f $(DVI) $(PS) $(PDF) $(AUX) $(LOG)
.PHONY: clean
\documentclass[a4paper,11pt]{article}
\usepackage{fullpage}
\usepackage[latin1]{inputenc}
\usepackage[T1]{fontenc}
\usepackage[normalem]{ulem}
\usepackage[english]{babel}
\usepackage{listings,babel}
\lstset{breaklines=true,basicstyle=\ttfamily}
\usepackage{graphicx}
\usepackage{moreverb}
\usepackage{url}
\title{Wishbone bus arbiter and address decoder}
\author{S\'ebastien Bourdeauducq}
\date{December 2009}
\begin{document}
\setlength{\parindent}{0pt}
\setlength{\parskip}{5pt}
\maketitle{}
\section{Specifications}
This core allows up to several masters to communicate with up to several slaves on a shared Wishbone bus.
It takes care of bus arbitration and remapping of the slave base addresses. It is very simple and does not take care of priorities. Scheduling occurs when a master releases the bus, and then the next master which requested the bus takes ownership.
It is based on \verb!wb_conbus! from OpenCores.
\section{Using the core}
All parameters and ports should be self-explanatory. No special care should be taken.
\section*{Copyright notice}
Copyright \copyright 2007-2009 S\'ebastien Bourdeauducq. \\
Permission is granted to copy, distribute and/or modify this document under the terms of the GNU Free Documentation License, Version 1.3; with no Invariant Sections, no Front-Cover Texts, and no Back-Cover Texts. A copy of the license is included in the LICENSE.FDL file at the root of the Milkymist source distribution.
\end{document}
/*
* Wishbone Arbiter and Address Decoder
* Copyright (C) 2008, 2009, 2010 Sebastien Bourdeauducq
* Copyright (C) 2000 Johny Chi - chisuhua@yahoo.com.cn
* This file is part of Milkymist.
*
* This source file may be used and distributed without
* restriction provided that this copyright statement is not
* removed from the file and that any derivative work contains
* the original copyright notice and the associated disclaimer.
*
* This source file is free software; you can redistribute it
* and/or modify it under the terms of the GNU Lesser General
* Public License as published by the Free Software Foundation;
* either version 2.1 of the License, or (at your option) any
* later version.
*
* This source is distributed in the hope that it will be
* useful, but WITHOUT ANY WARRANTY; without even the implied
* warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
* PURPOSE. See the GNU Lesser General Public License for more
* details.
*
* You should have received a copy of the GNU Lesser General
* Public License along with this source; if not, download it
* from http://www.opencores.org/lgpl.shtml.
*/
module conbus #(
parameter s_addr_w = 4,
parameter s0_addr = 4'h0,
parameter s1_addr = 4'h1,
parameter s2_addr = 4'h2,
parameter s3_addr = 4'h3,
parameter s4_addr = 4'h4,
parameter s5_addr = 4'h5
) (
input sys_clk,
input sys_rst,
// Master 0 Interface
input [31:0] m0_dat_i,
output [31:0] m0_dat_o,
input [31:0] m0_adr_i,
input [2:0] m0_cti_i,
input [3:0] m0_sel_i,
input m0_we_i,
input m0_cyc_i,
input m0_stb_i,
output m0_ack_o,
// Master 1 Interface
input [31:0] m1_dat_i,
output [31:0] m1_dat_o,
input [31:0] m1_adr_i,
input [2:0] m1_cti_i,
input [3:0] m1_sel_i,
input m1_we_i,
input m1_cyc_i,
input m1_stb_i,
output m1_ack_o,
// Master 2 Interface
input [31:0] m2_dat_i,
output [31:0] m2_dat_o,
input [31:0] m2_adr_i,
input [2:0] m2_cti_i,
input [3:0] m2_sel_i,
input m2_we_i,
input m2_cyc_i,
input m2_stb_i,
output m2_ack_o,
// Master 3 Interface
input [31:0] m3_dat_i,
output [31:0] m3_dat_o,
input [31:0] m3_adr_i,
input [2:0] m3_cti_i,
input [3:0] m3_sel_i,
input m3_we_i,
input m3_cyc_i,
input m3_stb_i,
output m3_ack_o,
// Master 4 Interface
input [31:0] m4_dat_i,
output [31:0] m4_dat_o,
input [31:0] m4_adr_i,
input [2:0] m4_cti_i,
input [3:0] m4_sel_i,
input m4_we_i,
input m4_cyc_i,
input m4_stb_i,
output m4_ack_o,
// Master 5 Interface
input [31:0] m5_dat_i,
output [31:0] m5_dat_o,
input [31:0] m5_adr_i,
input [2:0] m5_cti_i,
input [3:0] m5_sel_i,
input m5_we_i,
input m5_cyc_i,
input m5_stb_i,
output m5_ack_o,
// Slave 0 Interface
input [31:0] s0_dat_i,
output [31:0] s0_dat_o,
output [31:0] s0_adr_o,
output [2:0] s0_cti_o,
output [3:0] s0_sel_o,
output s0_we_o,
output s0_cyc_o,
output s0_stb_o,
input s0_ack_i,
// Slave 1 Interface
input [31:0] s1_dat_i,
output [31:0] s1_dat_o,
output [31:0] s1_adr_o,
output [2:0] s1_cti_o,
output [3:0] s1_sel_o,
output s1_we_o,
output s1_cyc_o,
output s1_stb_o,
input s1_ack_i,
// Slave 2 Interface
input [31:0] s2_dat_i,
output [31:0] s2_dat_o,
output [31:0] s2_adr_o,
output [2:0] s2_cti_o,
output [3:0] s2_sel_o,
output s2_we_o,
output s2_cyc_o,
output s2_stb_o,
input s2_ack_i,
// Slave 3 Interface
input [31:0] s3_dat_i,
output [31:0] s3_dat_o,
output [31:0] s3_adr_o,
output [2:0] s3_cti_o,
output [3:0] s3_sel_o,
output s3_we_o,
output s3_cyc_o,
output s3_stb_o,
input s3_ack_i,
// Slave 4 Interface
input [31:0] s4_dat_i,
output [31:0] s4_dat_o,
output [31:0] s4_adr_o,
output [2:0] s4_cti_o,
output [3:0] s4_sel_o,
output s4_we_o,
output s4_cyc_o,
output s4_stb_o,
input s4_ack_i,
// Slave 5 Interface
input [31:0] s5_dat_i,
output [31:0] s5_dat_o,
output [31:0] s5_adr_o,
output [2:0] s5_cti_o,
output [3:0] s5_sel_o,
output s5_we_o,
output s5_cyc_o,
output s5_stb_o,
input s5_ack_i
);
// address + CTI + data + byte select
// + cyc + we + stb
`define mbusw_ls 32 + 3 + 32 + 4 + 3
wire [5:0] slave_sel;
wire [5:0] gnt;
wire [`mbusw_ls -1:0] i_bus_m; // internal shared bus, master data and control to slave
wire [31:0] i_dat_s; // internal shared bus, slave data to master
wire i_bus_ack; // internal shared bus, ack signal
// master 0
assign m0_dat_o = i_dat_s;
assign m0_ack_o = i_bus_ack & gnt[0];
// master 1
assign m1_dat_o = i_dat_s;
assign m1_ack_o = i_bus_ack & gnt[1];
// master 2
assign m2_dat_o = i_dat_s;
assign m2_ack_o = i_bus_ack & gnt[2];
// master 3
assign m3_dat_o = i_dat_s;
assign m3_ack_o = i_bus_ack & gnt[3];
// master 4
assign m4_dat_o = i_dat_s;
assign m4_ack_o = i_bus_ack & gnt[4];
// master 5
assign m5_dat_o = i_dat_s;
assign m5_ack_o = i_bus_ack & gnt[5];
assign i_bus_ack = s0_ack_i | s1_ack_i | s2_ack_i | s3_ack_i | s4_ack_i | s5_ack_i;
// slave 0
assign {s0_adr_o, s0_cti_o, s0_sel_o, s0_dat_o, s0_we_o, s0_cyc_o} = i_bus_m[`mbusw_ls -1:1];
assign s0_stb_o = i_bus_m[1] & i_bus_m[0] & slave_sel[0]; // stb_o = cyc_i & stb_i & slave_sel
// slave 1
assign {s1_adr_o, s1_cti_o, s1_sel_o, s1_dat_o, s1_we_o, s1_cyc_o} = i_bus_m[`mbusw_ls -1:1];
assign s1_stb_o = i_bus_m[1] & i_bus_m[0] & slave_sel[1];
// slave 2
assign {s2_adr_o, s2_cti_o, s2_sel_o, s2_dat_o, s2_we_o, s2_cyc_o} = i_bus_m[`mbusw_ls -1:1];
assign s2_stb_o = i_bus_m[1] & i_bus_m[0] & slave_sel[2];
// slave 3
assign {s3_adr_o, s3_cti_o, s3_sel_o, s3_dat_o, s3_we_o, s3_cyc_o} = i_bus_m[`mbusw_ls -1:1];
assign s3_stb_o = i_bus_m[1] & i_bus_m[0] & slave_sel[3];
// slave 4
assign {s4_adr_o, s4_cti_o, s4_sel_o, s4_dat_o, s4_we_o, s4_cyc_o} = i_bus_m[`mbusw_ls -1:1];
assign s4_stb_o = i_bus_m[1] & i_bus_m[0] & slave_sel[4];
// slave 5
assign {s5_adr_o, s5_cti_o, s5_sel_o, s5_dat_o, s5_we_o, s5_cyc_o} = i_bus_m[`mbusw_ls -1:1];
assign s5_stb_o = i_bus_m[1] & i_bus_m[0] & slave_sel[5];
assign i_bus_m =
({`mbusw_ls{gnt[0]}} & {m0_adr_i, m0_cti_i, m0_sel_i, m0_dat_i, m0_we_i, m0_cyc_i, m0_stb_i})
|({`mbusw_ls{gnt[1]}} & {m1_adr_i, m1_cti_i, m1_sel_i, m1_dat_i, m1_we_i, m1_cyc_i, m1_stb_i})
|({`mbusw_ls{gnt[2]}} & {m2_adr_i, m2_cti_i, m2_sel_i, m2_dat_i, m2_we_i, m2_cyc_i, m2_stb_i})
|({`mbusw_ls{gnt[3]}} & {m3_adr_i, m3_cti_i, m3_sel_i, m3_dat_i, m3_we_i, m3_cyc_i, m3_stb_i})
|({`mbusw_ls{gnt[4]}} & {m4_adr_i, m4_cti_i, m4_sel_i, m4_dat_i, m4_we_i, m4_cyc_i, m4_stb_i})
|({`mbusw_ls{gnt[5]}} & {m5_adr_i, m5_cti_i, m5_sel_i, m5_dat_i, m5_we_i, m5_cyc_i, m5_stb_i});
assign i_dat_s =
({32{slave_sel[ 0]}} & s0_dat_i)
|({32{slave_sel[ 1]}} & s1_dat_i)
|({32{slave_sel[ 2]}} & s2_dat_i)
|({32{slave_sel[ 3]}} & s3_dat_i)
|({32{slave_sel[ 4]}} & s4_dat_i)
|({32{slave_sel[ 5]}} & s5_dat_i);
wire [5:0] req = {m5_cyc_i, m4_cyc_i, m3_cyc_i, m2_cyc_i, m1_cyc_i, m0_cyc_i};
conbus_arb conbus_arb(
.sys_clk(sys_clk),
.sys_rst(sys_rst),
.req(req),
.gnt(gnt)
);
assign slave_sel[0] = (i_bus_m[`mbusw_ls-1 : `mbusw_ls-s_addr_w] == s0_addr);
assign slave_sel[1] = (i_bus_m[`mbusw_ls-1 : `mbusw_ls-s_addr_w] == s1_addr);
assign slave_sel[2] = (i_bus_m[`mbusw_ls-1 : `mbusw_ls-s_addr_w] == s2_addr);
assign slave_sel[3] = (i_bus_m[`mbusw_ls-1 : `mbusw_ls-s_addr_w] == s3_addr);
assign slave_sel[4] = (i_bus_m[`mbusw_ls-1 : `mbusw_ls-s_addr_w] == s4_addr);
assign slave_sel[5] = (i_bus_m[`mbusw_ls-1 : `mbusw_ls-s_addr_w] == s5_addr);
endmodule
/*
* Milkymist VJ SoC
* Copyright (C) 2007, 2008, 2009, 2010 Sebastien Bourdeauducq
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, version 3 of the License.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
module conbus_arb(
input sys_clk,
input sys_rst,
input [5:0] req,
output [5:0] gnt
);
parameter [5:0] grant0 = 6'b000001,
grant1 = 6'b000010,
grant2 = 6'b000100,
grant3 = 6'b001000,
grant4 = 6'b010000,
grant5 = 6'b100000;
reg [5:0] state;
reg [5:0] next_state;
assign gnt = state;
always @(posedge sys_clk) begin
if(sys_rst)
state <= grant0;
else
state <= next_state;
end
always @(*) begin
next_state = state;
case(state)
grant0: begin
if(~req[0]) begin
if(req[1]) next_state = grant1;
else if(req[2]) next_state = grant2;
else if(req[3]) next_state = grant3;
else if(req[4]) next_state = grant4;
else if(req[5]) next_state = grant5;
end
end
grant1: begin
if(~req[1]) begin
if(req[2]) next_state = grant2;
else if(req[3]) next_state = grant3;
else if(req[4]) next_state = grant4;
else if(req[5]) next_state = grant5;
else if(req[0]) next_state = grant0;
end
end
grant2: begin
if(~req[2]) begin
if(req[3]) next_state = grant3;
else if(req[4]) next_state = grant4;
else if(req[5]) next_state = grant5;
else if(req[0]) next_state = grant0;
else if(req[1]) next_state = grant1;
end
end
grant3: begin
if(~req[3]) begin
if(req[4]) next_state = grant4;
else if(req[5]) next_state = grant5;
else if(req[0]) next_state = grant0;
else if(req[1]) next_state = grant1;
else if(req[2]) next_state = grant2;
end
end
grant4: begin
if(~req[4]) begin
if(req[5]) next_state = grant5;
else if(req[0]) next_state = grant0;
else if(req[1]) next_state = grant1;
else if(req[2]) next_state = grant2;
else if(req[3]) next_state = grant3;
end
end
grant5: begin
if(~req[5]) begin
if(req[0]) next_state = grant0;
else if(req[1]) next_state = grant1;
else if(req[2]) next_state = grant2;
else if(req[3]) next_state = grant3;
else if(req[4]) next_state = grant4;
end
end
endcase
end
endmodule
SOURCES=tb_conbus.v master.v slave.v $(wildcard ../rtl/*.v)
all: tb_conbus
sim: tb_conbus
./tb_conbus
cversim: $(SOURCES)
cver $(SOURCES)
clean:
rm -f tb_conbus verilog.log
tb_conbus: $(SOURCES)
iverilog -o tb_conbus $(SOURCES)
.PHONY: clean sim cversim
/*
* Milkymist VJ SoC
* Copyright (C) 2007, 2008, 2009 Sebastien Bourdeauducq
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, version 3 of the License.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
module master #(
parameter id = 0,
parameter nreads = 128,
parameter nwrites = 128,
parameter p = 4
) (
input sys_clk,
input sys_rst,
output reg [31:0] dat_w,
input [31:0] dat_r,
output reg [31:0] adr,
output [2:0] cti,
output reg we,
output reg [3:0] sel,
output cyc,
output stb,
input ack,
output reg tend
);
integer rcounter;
integer wcounter;
reg active;
assign cyc = active;
assign stb = active;
assign cti = 0;
always @(posedge sys_clk) begin
if(sys_rst) begin
dat_w = 0;
adr = 0;
we = 0;
sel = 0;
active = 0;
rcounter = 0;
wcounter = 0;
tend = 0;
end else begin
if(ack) begin
if(~active)
$display("[M%d] Spurious ack", id);
else begin
if(we)
$display("[M%d] Ack W: %x:%x [%x]", id, adr, dat_w, sel);
else
$display("[M%d] Ack R: %x:%x [%x]", id, adr, dat_r, sel);
end
active = 1'b0;
end else if(~active) begin
if(($random % p) == 0) begin
adr = $random;
adr = adr % 5;
adr = (adr << (32-3)) + id;
sel = sel + 1;
active = 1'b1;
if(($random % 2) == 0) begin
/* Read */
we = 1'b0;
rcounter = rcounter + 1;
end else begin
/* Write */
we = 1'b1;
dat_w = ($random << 16) + id;
wcounter = wcounter + 1;
end
end
end
tend = (rcounter >= nreads) && (wcounter >= nwrites);
end
end
endmodule
/*
* Milkymist VJ SoC
* Copyright (C) 2007, 2008, 2009 Sebastien Bourdeauducq
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, version 3 of the License.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
module slave #(
parameter id = 0,
parameter p = 3
) (
input sys_clk,
input sys_rst,
input [31:0] dat_w,
output reg [31:0] dat_r,
input [31:0] adr,
input [2:0] cti,
input we,
input [3:0] sel,
input cyc,
input stb,
output reg ack
);
always @(posedge sys_clk) begin
if(sys_rst) begin
dat_r = 0;
ack = 0;
end else begin
if(cyc & stb & ~ack) begin
if(($random % p) == 0) begin
ack = 1;
if(~we)
dat_r = ($random << 16) + id;
if(we)
$display("[S%d] Ack W: %x:%x [%x]", id, adr, dat_w, sel);
else
$display("[S%d] Ack R: %x:%x [%x]", id, adr, dat_r, sel);
end
end else
ack = 0;
end
end
endmodule
/*
* Milkymist VJ SoC
* Copyright (C) 2007, 2008, 2009 Sebastien Bourdeauducq
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, version 3 of the License.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
module tb_conbus();
reg sys_rst;
reg sys_clk;
//------------------------------------------------------------------
// Wishbone master wires
//------------------------------------------------------------------
wire [31:0] m0_adr,
m1_adr,
m2_adr,
m3_adr,
m4_adr;
wire [2:0] m0_cti,
m1_cti,
m2_cti,
m3_cti,
m4_cti;
wire [31:0] m0_dat_r,
m0_dat_w,
m1_dat_r,
m1_dat_w,
m2_dat_r,
m2_dat_w,
m3_dat_r,
m3_dat_w,
m4_dat_r,
m4_dat_w;
wire [3:0] m0_sel,
m1_sel,
m2_sel,
m3_sel,
m4_sel;
wire m0_we,
m1_we,
m2_we,
m3_we,
m4_we;
wire m0_cyc,
m1_cyc,
m2_cyc,
m3_cyc,
m4_cyc;
wire m0_stb,
m1_stb,
m2_stb,
m3_stb,
m4_stb;
wire m0_ack,
m1_ack,
m2_ack,
m3_ack,
m4_ack;
//------------------------------------------------------------------
// Wishbone slave wires
//------------------------------------------------------------------
wire [31:0] s0_adr,
s1_adr,
s2_adr,
s3_adr,
s4_adr;
wire [2:0] s0_cti,
s1_cti,
s2_cti,
s3_cti,
s4_cti;
wire [31:0] s0_dat_r,
s0_dat_w,
s1_dat_r,
s1_dat_w,
s2_dat_r,
s2_dat_w,
s3_dat_r,
s3_dat_w,
s4_dat_r,
s4_dat_w;
wire [3:0] s0_sel,
s1_sel,
s2_sel,
s3_sel,
s4_sel;
wire s0_we,
s1_we,
s2_we,
s3_we,
s4_we;
wire s0_cyc,
s1_cyc,
s2_cyc,
s3_cyc,
s4_cyc;
wire s0_stb,
s1_stb,
s2_stb,
s3_stb,
s4_stb;
wire s0_ack,
s1_ack,
s2_ack,
s3_ack,
s4_ack;
//---------------------------------------------------------------------------
// Wishbone switch
//---------------------------------------------------------------------------
conbus #(
.s_addr_w(3),
.s0_addr(3'b000), // 0x00000000
.s1_addr(3'b001), // 0x20000000
.s2_addr(3'b010), // 0x40000000
.s3_addr(3'b011), // 0x60000000
.s4_addr(3'b100) // 0x80000000
) dut (
.sys_clk(sys_clk),
.sys_rst(sys_rst),
// Master 0
.m0_dat_i(m0_dat_w),
.m0_dat_o(m0_dat_r),
.m0_adr_i(m0_adr),
.m0_cti_i(m0_cti),
.m0_we_i(m0_we),
.m0_sel_i(m0_sel),
.m0_cyc_i(m0_cyc),
.m0_stb_i(m0_stb),
.m0_ack_o(m0_ack),
// Master 1
.m1_dat_i(m1_dat_w),
.m1_dat_o(m1_dat_r),
.m1_adr_i(m1_adr),
.m1_cti_i(m1_cti),
.m1_we_i(m1_we),
.m1_sel_i(m1_sel),
.m1_cyc_i(m1_cyc),
.m1_stb_i(m1_stb),
.m1_ack_o(m1_ack),
// Master 2
.m2_dat_i(m2_dat_w),
.m2_dat_o(m2_dat_r),
.m2_adr_i(m2_adr),
.m2_cti_i(m2_cti),
.m2_we_i(m2_we),
.m2_sel_i(m2_sel),
.m2_cyc_i(m2_cyc),
.m2_stb_i(m2_stb),
.m2_ack_o(m2_ack),
// Master 3
.m3_dat_i(m3_dat_w),
.m3_dat_o(m3_dat_r),
.m3_adr_i(m3_adr),
.m3_cti_i(m3_cti),
.m3_we_i(m3_we),
.m3_sel_i(m3_sel),
.m3_cyc_i(m3_cyc),
.m3_stb_i(m3_stb),
.m3_ack_o(m3_ack),
// Master 4
.m4_dat_i(m4_dat_w),
.m4_dat_o(m4_dat_r),
.m4_adr_i(m4_adr),
.m4_cti_i(m4_cti),
.m4_we_i(m4_we),
.m4_sel_i(m4_sel),
.m4_cyc_i(m4_cyc),
.m4_stb_i(m4_stb),
.m4_ack_o(m4_ack),
// Slave 0
.s0_dat_i(s0_dat_r),
.s0_dat_o(s0_dat_w),
.s0_adr_o(s0_adr),
.s0_cti_o(s0_cti),
.s0_sel_o(s0_sel),
.s0_we_o(s0_we),
.s0_cyc_o(s0_cyc),
.s0_stb_o(s0_stb),
.s0_ack_i(s0_ack),
// Slave 1
.s1_dat_i(s1_dat_r),
.s1_dat_o(s1_dat_w),
.s1_adr_o(s1_adr),
.s1_cti_o(s1_cti),
.s1_sel_o(s1_sel),
.s1_we_o(s1_we),
.s1_cyc_o(s1_cyc),
.s1_stb_o(s1_stb),
.s1_ack_i(s1_ack),
// Slave 2
.s2_dat_i(s2_dat_r),
.s2_dat_o(s2_dat_w),
.s2_adr_o(s2_adr),
.s2_cti_o(s2_cti),
.s2_sel_o(s2_sel),
.s2_we_o(s2_we),
.s2_cyc_o(s2_cyc),
.s2_stb_o(s2_stb),
.s2_ack_i(s2_ack),
// Slave 3
.s3_dat_i(s3_dat_r),
.s3_dat_o(s3_dat_w),
.s3_adr_o(s3_adr),
.s3_cti_o(s3_cti),
.s3_sel_o(s3_sel),
.s3_we_o(s3_we),
.s3_cyc_o(s3_cyc),
.s3_stb_o(s3_stb),
.s3_ack_i(s3_ack),
// Slave 4
.s4_dat_i(s4_dat_r),
.s4_dat_o(s4_dat_w),
.s4_adr_o(s4_adr),
.s4_cti_o(s4_cti),
.s4_sel_o(s4_sel),
.s4_we_o(s4_we),
.s4_cyc_o(s4_cyc),
.s4_stb_o(s4_stb),
.s4_ack_i(s4_ack)
);
//---------------------------------------------------------------------------
// Masters
//---------------------------------------------------------------------------
wire m0_end;
master #(
.id(0)
) m0 (
.sys_clk(sys_clk),
.sys_rst(sys_rst),
.dat_w(m0_dat_w),
.dat_r(m0_dat_r),
.adr(m0_adr),
.cti(m0_cti),
.we(m0_we),
.sel(m0_sel),
.cyc(m0_cyc),
.stb(m0_stb),
.ack(m0_ack),
.tend(m0_end)
);
wire m1_end;
master #(
.id(1)
) m1 (
.sys_clk(sys_clk),
.sys_rst(sys_rst),
.dat_w(m1_dat_w),
.dat_r(m1_dat_r),
.adr(m1_adr),
.cti(m1_cti),
.we(m1_we),
.sel(m1_sel),
.cyc(m1_cyc),
.stb(m1_stb),
.ack(m1_ack),
.tend(m1_end)
);
wire m2_end;
master #(
.id(2)
) m2 (
.sys_clk(sys_clk),
.sys_rst(sys_rst),
.dat_w(m2_dat_w),
.dat_r(m2_dat_r),
.adr(m2_adr),
.cti(m2_cti),
.we(m2_we),
.sel(m2_sel),
.cyc(m2_cyc),
.stb(m2_stb),
.ack(m2_ack),
.tend(m2_end)
);
wire m3_end;
master #(
.id(3)
) m3 (
.sys_clk(sys_clk),
.sys_rst(sys_rst),
.dat_w(m3_dat_w),
.dat_r(m3_dat_r),
.adr(m3_adr),
.cti(m3_cti),
.we(m3_we),
.sel(m3_sel),
.cyc(m3_cyc),
.stb(m3_stb),
.ack(m3_ack),
.tend(m3_end)
);
wire m4_end;
master #(
.id(4)
) m4 (
.sys_clk(sys_clk),
.sys_rst(sys_rst),
.dat_w(m4_dat_w),
.dat_r(m4_dat_r),
.adr(m4_adr),
.cti(m4_cti),
.we(m4_we),
.sel(m4_sel),
.cyc(m4_cyc),
.stb(m4_stb),
.ack(m4_ack),
.tend(m4_end)
);
//---------------------------------------------------------------------------
// Slaves
//---------------------------------------------------------------------------
slave #(
.id(0)
) s0 (
.sys_clk(sys_clk),
.sys_rst(sys_rst),
.dat_w(s0_dat_w),
.dat_r(s0_dat_r),
.adr(s0_adr),
.cti(s0_cti),
.we(s0_we),
.sel(s0_sel),
.cyc(s0_cyc),
.stb(s0_stb),
.ack(s0_ack)
);
slave #(
.id(1)
) s1 (
.sys_clk(sys_clk),
.sys_rst(sys_rst),
.dat_w(s1_dat_w),
.dat_r(s1_dat_r),
.adr(s1_adr),
.cti(s1_cti),
.we(s1_we),
.sel(s1_sel),
.cyc(s1_cyc),
.stb(s1_stb),
.ack(s1_ack)
);
slave #(
.id(2)
) s2 (
.sys_clk(sys_clk),
.sys_rst(sys_rst),
.dat_w(s2_dat_w),
.dat_r(s2_dat_r),
.adr(s2_adr),
.cti(s2_cti),
.we(s2_we),
.sel(s2_sel),
.cyc(s2_cyc),
.stb(s2_stb),
.ack(s2_ack)
);
slave #(
.id(3)
) s3 (
.sys_clk(sys_clk),
.sys_rst(sys_rst),
.dat_w(s3_dat_w),
.dat_r(s3_dat_r),
.adr(s3_adr),
.cti(s3_cti),
.we(s3_we),
.sel(s3_sel),
.cyc(s3_cyc),
.stb(s3_stb),
.ack(s3_ack)
);
slave #(
.id(4)
) s4 (
.sys_clk(sys_clk),
.sys_rst(sys_rst),
.dat_w(s4_dat_w),
.dat_r(s4_dat_r),
.adr(s4_adr),
.cti(s4_cti),
.we(s4_we),
.sel(s4_sel),
.cyc(s4_cyc),
.stb(s4_stb),
.ack(s4_ack)
);
initial sys_clk = 1'b0;
always #5 sys_clk = ~sys_clk;
wire all_end = m0_end & m1_end & m2_end & m3_end & m4_end;
always begin
sys_rst = 1'b1;
@(posedge sys_clk);
#1 sys_rst = 1'b0;
@(posedge all_end);
$finish;
end
endmodule
/*
* Milkymist VJ SoC
* Copyright (C) 2007, 2008, 2009 Sebastien Bourdeauducq
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, version 3 of the License.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
module csrbrg(
input sys_clk,
input sys_rst,
/* WB */
input [31:0] wb_adr_i,
input [31:0] wb_dat_i,
output reg [31:0] wb_dat_o,
input wb_cyc_i,
input wb_stb_i,
input wb_we_i,
output reg wb_ack_o,
/* CSR */
output reg [13:0] csr_a,
output reg csr_we,
output reg [31:0] csr_do,
input [31:0] csr_di
);
/* Datapath: WB <- CSR */
always @(posedge sys_clk) begin
wb_dat_o <= csr_di;
end
/* Datapath: CSR -> WB */
reg next_csr_we;
always @(posedge sys_clk) begin
csr_a <= wb_adr_i[15:2];
csr_we <= next_csr_we;
csr_do <= wb_dat_i;
end
/* Controller */
reg [1:0] state;
reg [1:0] next_state;
parameter IDLE = 2'd0;
parameter DELAYACK1 = 2'd1;
parameter DELAYACK2 = 2'd2;
parameter ACK = 2'd3;
always @(posedge sys_clk) begin
if(sys_rst)
state <= IDLE;
else
state <= next_state;
end
always @(*) begin
next_state = state;
wb_ack_o = 1'b0;
next_csr_we = 1'b0;
case(state)
IDLE: begin
if(wb_cyc_i & wb_stb_i) begin
/* We have a request for us */
next_csr_we = wb_we_i;
if(wb_we_i)
next_state = ACK;
else
next_state = DELAYACK1;
end
end
DELAYACK1: next_state = DELAYACK2;
DELAYACK2: next_state = ACK;
ACK: begin
wb_ack_o = 1'b1;
next_state = IDLE;
end
endcase
end
endmodule
SOURCES=tb_csrbrg.v $(wildcard ../rtl/*.v)
all: sim
sim:
cver $(SOURCES)
clean:
rm -f verilog.log
.PHONY: clean sim
/*
* Milkymist VJ SoC
* Copyright (C) 2007, 2008, 2009 Sebastien Bourdeauducq
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, version 3 of the License.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
module tb_csrbrg();
reg sys_clk;
reg sys_rst;
reg [31:0] wb_adr_i;
reg [31:0] wb_dat_i;
wire [31:0] wb_dat_o;
reg wb_cyc_i;
reg wb_stb_i;
reg wb_we_i;
wire wb_ack_o;
wire [13:0] csr_a;
wire csr_we;
wire [31:0] csr_do;
reg [31:0] csr_di;
/* 100MHz system clock */
initial sys_clk = 1'b0;
always #5 sys_clk = ~sys_clk;
csrbrg dut(
.sys_clk(sys_clk),
.sys_rst(sys_rst),
.wb_adr_i(wb_adr_i),
.wb_dat_i(wb_dat_i),
.wb_dat_o(wb_dat_o),
.wb_cyc_i(wb_cyc_i),
.wb_stb_i(wb_stb_i),
.wb_we_i(wb_we_i),
.wb_ack_o(wb_ack_o),
/* CSR bus master */
.csr_a(csr_a),
.csr_we(csr_we),
.csr_do(csr_do),
.csr_di(csr_di)
);
task waitclock;
begin
@(posedge sys_clk);
#1;
end
endtask
task wbwrite;
input [31:0] address;
input [31:0] data;
integer i;
begin
wb_adr_i = address;
wb_dat_i = data;
wb_cyc_i = 1'b1;
wb_stb_i = 1'b1;
wb_we_i = 1'b1;
i = 0;
while(~wb_ack_o) begin
i = i+1;
waitclock;
end
waitclock;
$display("WB Write: %x=%x acked in %d clocks", address, data, i);
wb_cyc_i = 1'b0;
wb_stb_i = 1'b0;
wb_we_i = 1'b0;
end
endtask
task wbread;
input [31:0] address;
integer i;
begin
wb_adr_i = address;
wb_cyc_i = 1'b1;
wb_stb_i = 1'b1;
wb_we_i = 1'b0;
i = 0;
while(~wb_ack_o) begin
i = i+1;
waitclock;
end
$display("WB Read : %x=%x acked in %d clocks", address, wb_dat_o, i);
waitclock;
wb_cyc_i = 1'b0;
wb_stb_i = 1'b0;
wb_we_i = 1'b0;
end
endtask
/* Simulate CSR slave */
reg [31:0] csr1;
reg [31:0] csr2;
wire csr_selected = (csr_a[13:10] == 4'ha);
always @(posedge sys_clk) begin
if(csr_selected) begin
if(csr_we) begin
$display("Writing %x to CSR %x", csr_do, csr_a[0]);
case(csr_a[0])
1'b0: csr1 <= csr_do;
1'b1: csr2 <= csr_do;
endcase
end
case(csr_a[0])
1'b0: csr_di <= csr1;
1'b1: csr_di <= csr2;
endcase
end else
/* we must set data to 0 to be able to use a distributed OR topology
* in the slaves->master datapath.
*/
csr_di <= 32'd0;
end
always begin
/* Reset / Initialize our logic */
sys_rst = 1'b1;
wb_adr_i = 32'd0;
wb_dat_i = 32'd0;
wb_cyc_i = 1'b0;
wb_stb_i = 1'b0;
wb_we_i = 1'b0;
waitclock;
sys_rst = 1'b0;
waitclock;
/* Try some transfers */
wbwrite(32'h0000a000, 32'hcafebabe);
wbwrite(32'h0000a004, 32'habadface);
wbread(32'h0000a000);
wbread(32'h0000a004);
$finish;
end
endmodule
* 2009-12-21 Upgrade to LatticeMico32 3.5.
* 2009-11-12 Active-high interrupts (lekernel)
* 2009-07-01 Based on LatticeMico32 core from mico32_72_linux.tar.
(LatticeMico32 v3.3)
H1 {
font-weight:bold;
border-top-style:none;
font-family:Arial, helvetica, sans-serif;
color:#ea6d23;
margin-left:15px;
margin-top:3px;
margin-bottom:10px;
border-bottom-style:Solid;
border-bottom-width:2px;
border-bottom-color:#dbdbdb;
margin-right:0px;
line-height:Normal;
font-size:1em; }
LI.kadov-H1 {
font-weight:bold;
font-family:Arial, helvetica, sans-serif;
color:#ea6d23;
line-height:Normal;
font-size:1em; }
H2 {
font-weight:bold;
x-text-underline:Off;
border-top-style:none;
border-bottom-style:none;
font-family:Arial, helvetica, sans-serif;
color:#ea6d23;
margin-left:15px;
margin-top:12px;
margin-bottom:5px;
font-size:0.84em;
margin-right:0px;
text-decoration:none; }
LI.kadov-H2 {
font-weight:bold;
x-text-underline:Off;
font-family:Arial, helvetica, sans-serif;
color:#ea6d23;
font-size:0.84em;
text-decoration:none; }
P {
margin-top:0pt;
font-family:Verdana, Arial, helvetica, sans-serif;
color:#323232;
font-size:71%;
margin-bottom:8px;
line-height:1.4em;
margin-right:0px;
margin-left:15px; }
LI.kadov-P {
font-family:Verdana, Arial, helvetica, sans-serif;
color:#323232;
font-size:71%;
line-height:1.4em; }
p.Step {
list-style:decimal;
margin-left:0px;
font-size:100%;
margin-bottom:7px;
margin-top:0px; }
LI.kadov-p-CStep {
list-style:decimal;
font-size:100%; }
P.Bullet {
font-size:100%;
list-style:url("image/top-bullet.gif");
margin-bottom:7px;
margin-left:0px;
margin-top:0px; }
LI.kadov-P-CBullet {
font-size:100%;
list-style:url("image/top-bullet.gif"); }
P.NormalIndent {
margin-left:40px; }
LI.kadov-P-CNormalIndent { }
P.BulletIndent {
margin-bottom:2px;
font-size:100%;
margin-left:15pt;
list-style:url("image/secondary-bullet.gif"); }
LI.kadov-P-CBulletIndent {
font-size:100%;
list-style:url("image/secondary-bullet.gif"); }
P.Procedure {
font-style:italic;
font-weight:normal;
x-next-class:Step;
x-next-type:p;
margin-top:12pt;
margin-bottom:5px; }
LI.kadov-P-CProcedure {
font-style:italic;
font-weight:normal; }
P.Note {
margin-top:8pt;
margin-bottom:8pt;
border-top-style:Solid;
border-bottom-style:Solid;
padding-top:4px;
padding-bottom:4px;
border-top-width:1px;
border-bottom-width:1px;
background-color:#ffffff; }
LI.kadov-P-CNote { }
P.NoteIndent {
margin-top:8pt;
margin-bottom:8pt;
border-top-style:Solid;
border-bottom-style:Solid;
padding-top:4px;
padding-bottom:4px;
border-top-width:1px;
border-bottom-width:1px;
background-color:#ffffff;
margin-left:40px; }
LI.kadov-P-CNoteIndent { }
P.Table {
margin-top:4px;
margin-bottom:4px;
margin-right:4px;
margin-left:4px; }
LI.kadov-P-CTable { }
P.Code {
margin-bottom:0px;
line-height:Normal;
font-family:"Courier New" , Courier, monospace; }
LI.kadov-P-CCode {
line-height:Normal;
font-family:"Courier New" , Courier, monospace; }
P.StepBulletFirst {
font-size:100%;
margin-left:15px;
margin-bottom:2px;
list-style:url("image/secondary-bullet.gif"); }
LI.kadov-P-CStepBulletFirst {
font-size:100%;
list-style:url("image/secondary-bullet.gif"); }
BODY {
background-color:#ffffff;
color:#000080;
font-family:Arial, sans-serif; }
P.SeeAlso {
font-weight:bold;
font-style:normal;
x-next-type:P;
color:#ea6d23;
font-family:Arial, helvetica, sans-serif;
margin-left:15px;
margin-top:12px;
margin-bottom:5px;
font-size:0.84em; }
LI.kadov-P-CSeeAlso {
font-weight:bold;
font-style:normal;
color:#ea6d23;
font-family:Arial, helvetica, sans-serif;
font-size:0.84em; }
A:link {
font-weight:bold;
font-style:normal;
color:#003a98;
x-text-underline:Off;
text-decoration:none; }
A:hover {
x-text-underline:Normal;
color:#59add3;
text-decoration:underline; }
A:active {
color:#59add3; }
A:visited {
x-text-underline:Off;
color:#385689;
font-weight:bold;
font-style:normal;
text-decoration:none; }
H1.Home {
x-next-type:P;
border-top-style:none;
border-bottom-style:none;
x-text-underline:Off;
font-size:15pt;
color:#ea6d23;
text-decoration:none; }
LI.kadov-H1-CHome {
x-text-underline:Off;
font-size:15pt;
color:#ea6d23;
text-decoration:none; }
H3 {
margin-left:15px;
margin-top:12px;
margin-bottom:5px;
color:#323232;
font-size:71%;
font-family:Verdana, Arial, helvetica, sans-serif;
margin-right:0px; }
LI.kadov-H3 {
color:#323232;
font-size:71%;
font-family:Verdana, Arial, helvetica, sans-serif; }
P.Title {
font-weight:bold;
font-style:normal;
x-next-type:P;
font-family:Arial, helvetica, sans-serif;
color:#ea6d23;
margin-bottom:10px;
font-size:1.4em;
line-height:Normal;
border-bottom-style:Solid;
border-bottom-width:2px;
border-bottom-color:#dbdbdb;
margin-top:0px; }
LI.kadov-P-CTitle {
font-weight:bold;
font-style:normal;
font-family:Arial, helvetica, sans-serif;
color:#ea6d23;
font-size:1.4em;
line-height:Normal; }
P.Supra {
font-weight:bold;
font-style:normal;
margin-bottom:6pt;
font-family:Arial, helvetica, sans-serif; }
LI.kadov-P-CSupra {
font-weight:bold;
font-style:normal;
font-family:Arial, helvetica, sans-serif; }
OL {
font-size:71%;
font-family:Verdana, Arial, helvetica, sans-serif;
color:#323232; }
UL {
font-size:71%;
font-family:Verdana, Arial, helvetica, sans-serif;
color:#323232; }
P.CodeIndent {
font-family:"Courier New" , Courier, monospace;
margin-left:40px;
margin-bottom:0px;
line-height:Normal; }
LI.kadov-P-CCodeIndent {
font-family:"Courier New" , Courier, monospace;
line-height:Normal; }
H1 {
font-weight:bold;
border-top-style:none;
font-family:Arial, helvetica, sans-serif;
color:#ea6d23;
margin-left:15px;
margin-top:3px;
margin-bottom:10px;
border-bottom-style:Solid;
border-bottom-width:2px;
border-bottom-color:#dbdbdb;
margin-right:1pt;
line-height:Normal;
font-size:1em; }
LI.kadov-H1 {
font-weight:bold;
font-family:Arial, helvetica, sans-serif;
color:#ea6d23;
line-height:Normal;
font-size:1em; }
H2 {
font-weight:bold;
x-text-underline:Off;
border-top-style:none;
border-bottom-style:none;
font-family:Arial, helvetica, sans-serif;
color:#ea6d23;
margin-left:15px;
margin-top:12px;
margin-bottom:5px;
font-size:0.84em;
margin-right:1pt;
text-decoration:none; }
LI.kadov-H2 {
font-weight:bold;
x-text-underline:Off;
font-family:Arial, helvetica, sans-serif;
color:#ea6d23;
font-size:0.84em;
text-decoration:none; }
P {
margin-top:1pt;
font-family:Verdana, Arial, helvetica, sans-serif;
color:#323232;
font-size:71%;
margin-bottom:8px;
line-height:1.4em;
margin-right:1pt;
margin-left:15px; }
LI.kadov-P {
font-family:Verdana, Arial, helvetica, sans-serif;
color:#323232;
font-size:71%;
line-height:1.4em; }
p.Step {
list-style:decimal;
margin-left:1pt;
font-size:100%;
margin-bottom:7px;
margin-top:1pt; }
LI.kadov-p-CStep {
list-style:decimal;
font-size:100%; }
P.Bullet {
font-size:100%;
margin-bottom:7px;
margin-left:1pt;
margin-top:1pt; }
LI.kadov-P-CBullet {
font-size:100%; }
P.NormalIndent {
margin-left:40px; }
LI.kadov-P-CNormalIndent { }
P.BulletIndent {
margin-bottom:2px;
font-size:100%;
margin-left:15pt; }
LI.kadov-P-CBulletIndent {
font-size:100%; }
P.Procedure {
font-style:italic;
font-weight:normal;
x-next-class:Step;
x-next-type:p;
margin-top:12pt;
margin-bottom:5px; }
LI.kadov-P-CProcedure {
font-style:italic;
font-weight:normal; }
P.Note {
margin-top:8pt;
margin-bottom:8pt;
border-top-style:Solid;
border-bottom-style:Solid;
padding-top:4px;
padding-bottom:4px;
border-top-width:1px;
border-bottom-width:1px;
background-color:#ffffff; }
LI.kadov-P-CNote { }
P.NoteIndent {
margin-top:8pt;
margin-bottom:8pt;
border-top-style:Solid;
border-bottom-style:Solid;
padding-top:4px;
padding-bottom:4px;
border-top-width:1px;
border-bottom-width:1px;
background-color:#ffffff;
margin-left:40px; }
LI.kadov-P-CNoteIndent { }
P.Table {
margin-top:4px;
margin-bottom:4px;
margin-right:4px;
margin-left:4px; }
LI.kadov-P-CTable { }
P.Code {
margin-bottom:1pt;
line-height:Normal;
font-family:"Courier New" , Courier, monospace; }
LI.kadov-P-CCode {
line-height:Normal;
font-family:"Courier New" , Courier, monospace; }
P.StepBulletFirst {
font-size:100%;
margin-left:15px;
margin-bottom:2px; }
LI.kadov-P-CStepBulletFirst {
font-size:100%; }
BODY {
background-color:#ffffff;
color:#000080;
font-family:Arial, sans-serif; }
P.SeeAlso {
font-weight:bold;
font-style:normal;
x-next-type:P;
color:#ea6d23;
font-family:Arial, helvetica, sans-serif;
margin-left:15px;
margin-top:12px;
margin-bottom:5px;
font-size:0.84em; }
LI.kadov-P-CSeeAlso {
font-weight:bold;
font-style:normal;
color:#ea6d23;
font-family:Arial, helvetica, sans-serif;
font-size:0.84em; }
A:link {
font-weight:bold;
font-style:normal;
color:#003a98;
x-text-underline:Off;
text-decoration:none; }
A:hover {
x-text-underline:Normal;
color:#59add3;
text-decoration:underline; }
A:active {
color:#59add3; }
A:visited {
x-text-underline:Off;
color:#385689;
font-weight:bold;
font-style:normal;
text-decoration:none; }
H1.Home {
x-next-type:P;
border-top-style:none;
border-bottom-style:none;
x-text-underline:Off;
font-size:15pt;
color:#ea6d23;
text-decoration:none; }
LI.kadov-H1-CHome {
x-text-underline:Off;
font-size:15pt;
color:#ea6d23;
text-decoration:none; }
H3 {
margin-left:15px;
margin-top:12px;
margin-bottom:5px;
color:#323232;
font-size:71%;
font-family:Verdana, Arial, helvetica, sans-serif;
margin-right:1pt;
font-weight:bold; }
LI.kadov-H3 {
color:#323232;
font-size:71%;
font-family:Verdana, Arial, helvetica, sans-serif; }
P.Title {
font-weight:bold;
font-style:normal;
x-next-type:P;
font-family:Arial, helvetica, sans-serif;
color:#ea6d23;
margin-bottom:10px;
font-size:1.4em;
line-height:Normal;
border-bottom-style:Solid;
border-bottom-width:2px;
border-bottom-color:#dbdbdb;
margin-top:1pt; }
LI.kadov-P-CTitle {
font-weight:bold;
font-style:normal;
font-family:Arial, helvetica, sans-serif;
color:#ea6d23;
font-size:1.4em;
line-height:Normal; }
P.Supra {
font-weight:bold;
font-style:normal;
margin-bottom:6pt;
font-family:Arial, helvetica, sans-serif; }
LI.kadov-P-CSupra {
font-weight:bold;
font-style:normal;
font-family:Arial, helvetica, sans-serif; }
OL {
font-size:71%;
font-family:Verdana, Arial, helvetica, sans-serif;
color:#323232; }
UL {
font-size:71%;
font-family:Verdana, Arial, helvetica, sans-serif;
color:#323232; }
P.CodeIndent {
font-family:"Courier New" , Courier, monospace;
margin-left:40px;
margin-bottom:1pt;
line-height:Normal; }
LI.kadov-P-CCodeIndent {
font-family:"Courier New" , Courier, monospace;
line-height:Normal; }
ol ol {
margin-top:1px; }
ol ul {
margin-top:1px; }
ul ul {
margin-top:1px; }
ul ol {
margin-top:1px; }
This diff is collapsed.
// =============================================================================
// COPYRIGHT NOTICE
// Copyright 2006 (c) Lattice Semiconductor Corporation
// ALL RIGHTS RESERVED
// This confidential and proprietary software may be used only as authorised by
// a licensing agreement from Lattice Semiconductor Corporation.
// The entire notice above must be reproduced on all authorized copies and
// copies may only be made to the extent permitted by a licensing agreement from
// Lattice Semiconductor Corporation.
//
// Lattice Semiconductor Corporation TEL : 1-800-Lattice (USA and Canada)
// 5555 NE Moore Court 408-826-6000 (other locations)
// Hillsboro, OR 97124 web : http://www.latticesemi.com/
// U.S.A email: techsupport@latticesemi.com
// =============================================================================/
// FILE DETAILS
// Project : LatticeMico32
// File : JTAGB.v
// Title : JTAGB Black Box
// Dependencies : None
// Version : 6.0.14
// : Initial Release
// Version : 7.0SP2, 3.0
// : No Change
// Version : 3.1
// : No Change
// =============================================================================
module JTAGB (
output JTCK,
output JRTI1,
output JRTI2,
output JTDI,
output JSHIFT,
output JUPDATE,
output JRSTN,
output JCE1,
output JCE2,
input JTDO1,
input JTDO2
) /*synthesis syn_black_box */;
endmodule
// =============================================================================
// COPYRIGHT NOTICE
// Copyright 2006 (c) Lattice Semiconductor Corporation
// ALL RIGHTS RESERVED
// This confidential and proprietary software may be used only as authorised by
// a licensing agreement from Lattice Semiconductor Corporation.
// The entire notice above must be reproduced on all authorized copies and
// copies may only be made to the extent permitted by a licensing agreement from
// Lattice Semiconductor Corporation.
//
// Lattice Semiconductor Corporation TEL : 1-800-Lattice (USA and Canada)
// 5555 NE Moore Court 408-826-6000 (other locations)
// Hillsboro, OR 97124 web : http://www.latticesemi.com/
// U.S.A email: techsupport@latticesemi.com
// =============================================================================/
// FILE DETAILS
// Project : LatticeMico32
// File : er1.v
// Description:
// This module is where the ER1 register implemented. ER1 and ER2 registers
// can be registers implemented in Lattice FPGAs using normal FPGA's
// programmable logic resources. Once they are implemented, they can be
// accessed as if they are JTAG data registers through the FPGA JTAG port.
// In order to accessing these registers, JTAG instructions ER1(0x32) or
// ER2(0x38) needs to be written to the JTAG IR register for enabling the
// ER1/ER2 accessing logic. The ER1 or ER2 accessing logic can only be
// enabled one at a time. Once they are enabled, they will be disabled if
// another JTAG instruction is written into the JTAG instruction register.
// The registers allow dynamically accessing the FPGA internal information
// even when the device is running. Therefore, they are very useful for some
// of the IP cores. In order to let ER1/ER2 registers shared by multiple IP
// cores or other designs, there is a ER1/ER2 structure patterned by Lattice.
// The ER1/ER2 structure allows only one ER1 register but more than one ER2
// registers in an FPGA device. Please refer to the related document for
// this patterned ER1/ER2 structure.
// Dependencies : None
// Version : 6.0.14
// : Initial Version
// Version : 7.0SP2, 3.0
// : No Change
// Version : 3.1
// : No Change
// =============================================================================
module ER1 (input JTCK,
input JTDI,
output JTDO1,
output reg JTDO2,
input JSHIFT,
input JUPDATE,
input JRSTN,
input JCE1,
input [14:0] ER2_TDO,
output reg [14:0] IP_ENABLE,
input ISPTRACY_ER2_TDO,
output ISPTRACY_ENABLE,
output CONTROL_DATAN)/* synthesis syn_hier = hard */;
wire controlDataNBit;
wire ispTracyEnableBit;
wire [3:0] encodedIpEnableBits;
wire [9:0] er1TdiBit;
wire captureDrER1;
assign JTDO1 = er1TdiBit[0];
TYPEB BIT0 (.CLK(JTCK),
.RESET_N(JRSTN),
.CLKEN(JCE1),
.TDI(er1TdiBit[1]),
.TDO(er1TdiBit[0]),
.DATA_IN(1'b0),
.CAPTURE_DR(captureDrER1));
TYPEB BIT1 (.CLK(JTCK),
.RESET_N(JRSTN),
.CLKEN(JCE1),
.TDI(er1TdiBit[2]),
.TDO(er1TdiBit[1]),
.DATA_IN(1'b0),
.CAPTURE_DR(captureDrER1));
TYPEB BIT2 (.CLK(JTCK),
.RESET_N(JRSTN),
.CLKEN(JCE1),
.TDI(er1TdiBit[3]),
.TDO(er1TdiBit[2]),
.DATA_IN(1'b1),
.CAPTURE_DR(captureDrER1));
TYPEA BIT3 (.CLK(JTCK),
.RESET_N(JRSTN),
.CLKEN(JCE1),
.TDI(er1TdiBit[4]),
.TDO(er1TdiBit[3]),
.DATA_OUT(controlDataNBit),
.DATA_IN(controlDataNBit),
.CAPTURE_DR(captureDrER1),
.UPDATE_DR(JUPDATE));
assign CONTROL_DATAN = controlDataNBit;
TYPEA BIT4 (.CLK(JTCK),
.RESET_N(JRSTN),
.CLKEN(JCE1),
.TDI(er1TdiBit[5]),
.TDO(er1TdiBit[4]),
.DATA_OUT(ispTracyEnableBit),
.DATA_IN(ispTracyEnableBit),
.CAPTURE_DR(captureDrER1),
.UPDATE_DR(JUPDATE)
);
assign ISPTRACY_ENABLE = ispTracyEnableBit;
TYPEA BIT5 (.CLK(JTCK),
.RESET_N(JRSTN),
.CLKEN(JCE1),
.TDI(er1TdiBit[6]),
.TDO(er1TdiBit[5]),
.DATA_OUT(encodedIpEnableBits[0]),
.DATA_IN(encodedIpEnableBits[0]),
.CAPTURE_DR(captureDrER1),
.UPDATE_DR(JUPDATE));
TYPEA BIT6 (.CLK(JTCK),
.RESET_N(JRSTN),
.CLKEN(JCE1),
.TDI(er1TdiBit[7]),
.TDO(er1TdiBit[6]),
.DATA_OUT(encodedIpEnableBits[1]),
.DATA_IN(encodedIpEnableBits[1]),
.CAPTURE_DR(captureDrER1),
.UPDATE_DR(JUPDATE));
TYPEA BIT7 (.CLK(JTCK),
.RESET_N(JRSTN),
.CLKEN(JCE1),
.TDI(er1TdiBit[8]),
.TDO(er1TdiBit[7]),
.DATA_OUT(encodedIpEnableBits[2]),
.DATA_IN(encodedIpEnableBits[2]),
.CAPTURE_DR(captureDrER1),
.UPDATE_DR(JUPDATE));
TYPEA BIT8 (.CLK(JTCK),
.RESET_N(JRSTN),
.CLKEN(JCE1),
.TDI(er1TdiBit[9]),
.TDO(er1TdiBit[8]),
.DATA_OUT(encodedIpEnableBits[3]),
.DATA_IN(encodedIpEnableBits[3]),
.CAPTURE_DR(captureDrER1),
.UPDATE_DR(JUPDATE)
);
assign er1TdiBit[9] = JTDI;
assign captureDrER1 = !JSHIFT & JCE1;
always @ (encodedIpEnableBits,ISPTRACY_ER2_TDO, ER2_TDO)
begin
case (encodedIpEnableBits)
4'h0: begin
IP_ENABLE <= 15'b000000000000000;
JTDO2 <= ISPTRACY_ER2_TDO;
end
4'h1: begin
IP_ENABLE <= 15'b000000000000001;
JTDO2 <= ER2_TDO[0];
end
4'h2: begin
IP_ENABLE <= 15'b000000000000010;
JTDO2 <= ER2_TDO[1];
end
4'h3: begin
IP_ENABLE <= 15'b000000000000100;
JTDO2 <= ER2_TDO[2];
end
4'h4: begin
IP_ENABLE <= 15'b000000000001000;
JTDO2 <= ER2_TDO[3];
end
4'h5: begin
IP_ENABLE <= 15'b000000000010000;
JTDO2 <= ER2_TDO[4];
end
4'h6: begin
IP_ENABLE <= 15'b000000000100000;
JTDO2 <= ER2_TDO[5];
end
4'h7: begin
IP_ENABLE <= 15'b000000001000000;
JTDO2 <= ER2_TDO[6];
end
4'h8: begin
IP_ENABLE <= 15'b000000010000000;
JTDO2 <= ER2_TDO[7];
end
4'h9: begin
IP_ENABLE <= 15'b000000100000000;
JTDO2 <= ER2_TDO[8];
end
4'hA: begin
IP_ENABLE <= 15'b000001000000000;
JTDO2 <= ER2_TDO[9];
end
4'hB: begin
IP_ENABLE <= 15'b000010000000000;
JTDO2 <= ER2_TDO[10];
end
4'hC: begin
IP_ENABLE <= 15'b000100000000000;
JTDO2 <= ER2_TDO[11];
end
4'hD: begin
IP_ENABLE <= 15'b001000000000000;
JTDO2 <= ER2_TDO[12];
end
4'hE: begin
IP_ENABLE <= 15'b010000000000000;
JTDO2 <= ER2_TDO[13];
end
4'hF: begin
IP_ENABLE <= 15'b100000000000000;
JTDO2 <= ER2_TDO[14];
end
endcase
end
endmodule
// ============================================================================
// COPYRIGHT NOTICE
// Copyright 2006 (c) Lattice Semiconductor Corporation
// ALL RIGHTS RESERVED
// This confidential and proprietary software may be used only as authorised by
// a licensing agreement from Lattice Semiconductor Corporation.
// The entire notice above must be reproduced on all authorized copies and
// copies may only be made to the extent permitted by a licensing agreement from
// Lattice Semiconductor Corporation.
//
// Lattice Semiconductor Corporation TEL : 1-800-Lattice (USA and Canada)
// 5555 NE Moore Court 408-826-6000 (other locations)
// Hillsboro, OR 97124 web : http://www.latticesemi.com/
// U.S.A email: techsupport@latticesemi.com
// ============================================================================/
// FILE DETAILS
// Project : LatticeMico32
// File : jtag_cores.v
// Title : Instantiates all IP cores on JTAG chain.
// Dependencies : system_conf.v
// Version : 6.0.14
// : modified to use jtagconn for LM32,
// : all technologies 7/10/07
// Version : 7.0SP2, 3.0
// : No Change
// Version : 3.1
// : No Change
// ============================================================================
`include "system_conf.v"
/////////////////////////////////////////////////////
// jtagconn16 Module Definition
/////////////////////////////////////////////////////
module jtagconn16 (er2_tdo, jtck, jtdi, jshift, jupdate, jrstn, jce2, ip_enable) ;
input er2_tdo ;
output jtck ;
output jtdi ;
output jshift ;
output jupdate ;
output jrstn ;
output jce2 ;
output ip_enable ;
endmodule
/////////////////////////////////////////////////////
// Module interface
/////////////////////////////////////////////////////
(* syn_hier="hard" *) module jtag_cores (
// ----- Inputs -------
reg_d,
reg_addr_d,
// ----- Outputs -------
reg_update,
reg_q,
reg_addr_q,
jtck,
jrstn
);
/////////////////////////////////////////////////////
// Inputs
/////////////////////////////////////////////////////
input [7:0] reg_d;
input [2:0] reg_addr_d;
/////////////////////////////////////////////////////
// Outputs
/////////////////////////////////////////////////////
output reg_update;
wire reg_update;
output [7:0] reg_q;
wire [7:0] reg_q;
output [2:0] reg_addr_q;
wire [2:0] reg_addr_q;
output jtck;
wire jtck; /* synthesis syn_keep=1 */
output jrstn;
wire jrstn; /* synthesis syn_keep=1 */
/////////////////////////////////////////////////////
// Instantiations
/////////////////////////////////////////////////////
wire jtdi; /* synthesis syn_keep=1 */
wire er2_tdo2; /* synthesis syn_keep=1 */
wire jshift; /* synthesis syn_keep=1 */
wire jupdate; /* synthesis syn_keep=1 */
wire jce2; /* synthesis syn_keep=1 */
wire ip_enable; /* synthesis syn_keep=1 */
(* JTAG_IP="LM32", IP_ID="0", HUB_ID="0", syn_noprune=1 *) jtagconn16 jtagconn16_lm32_inst (
.er2_tdo (er2_tdo2),
.jtck (jtck),
.jtdi (jtdi),
.jshift (jshift),
.jupdate (jupdate),
.jrstn (jrstn),
.jce2 (jce2),
.ip_enable (ip_enable)
);
(* syn_noprune=1 *) jtag_lm32 jtag_lm32_inst (
.JTCK (jtck),
.JTDI (jtdi),
.JTDO2 (er2_tdo2),
.JSHIFT (jshift),
.JUPDATE (jupdate),
.JRSTN (jrstn),
.JCE2 (jce2),
.JTAGREG_ENABLE (ip_enable),
.CONTROL_DATAN (),
.REG_UPDATE (reg_update),
.REG_D (reg_d),
.REG_ADDR_D (reg_addr_d),
.REG_Q (reg_q),
.REG_ADDR_Q (reg_addr_q)
);
endmodule
// =============================================================================
// COPYRIGHT NOTICE
// Copyright 2006 (c) Lattice Semiconductor Corporation
// ALL RIGHTS RESERVED
// This confidential and proprietary software may be used only as authorised by
// a licensing agreement from Lattice Semiconductor Corporation.
// The entire notice above must be reproduced on all authorized copies and
// copies may only be made to the extent permitted by a licensing agreement from
// Lattice Semiconductor Corporation.
//
// Lattice Semiconductor Corporation TEL : 1-800-Lattice (USA and Canada)
// 5555 NE Moore Court 408-826-6000 (other locations)
// Hillsboro, OR 97124 web : http://www.latticesemi.com/
// U.S.A email: techsupport@latticesemi.com
// =============================================================================/
// FILE DETAILS
// Project : LatticeMico32
// File : jtag_lm32.v
// Title : JTAG data register for LM32 CPU debug interface
// Version : 6.0.13
// : Initial Release
// Version : 7.0SP2, 3.0
// : No Change
// Version : 3.1
// : No Change
// =============================================================================
/////////////////////////////////////////////////////
// Module interface
/////////////////////////////////////////////////////
module jtag_lm32 (
input JTCK,
input JTDI,
output JTDO2,
input JSHIFT,
input JUPDATE,
input JRSTN,
input JCE2,
input JTAGREG_ENABLE,
input CONTROL_DATAN,
output REG_UPDATE,
input [7:0] REG_D,
input [2:0] REG_ADDR_D,
output [7:0] REG_Q,
output [2:0] REG_ADDR_Q
);
/////////////////////////////////////////////////////
// Internal nets and registers
/////////////////////////////////////////////////////
wire [9:0] tdibus;
/////////////////////////////////////////////////////
// Instantiations
/////////////////////////////////////////////////////
TYPEA DATA_BIT0 (
.CLK(JTCK),
.RESET_N(JRSTN),
.CLKEN(clk_enable),
.TDI(JTDI),
.TDO(tdibus[0]),
.DATA_OUT(REG_Q[0]),
.DATA_IN(REG_D[0]),
.CAPTURE_DR(captureDr),
.UPDATE_DR(JUPDATE)
);
TYPEA DATA_BIT1 (
.CLK(JTCK),
.RESET_N(JRSTN),
.CLKEN(clk_enable),
.TDI(tdibus[0]),
.TDO(tdibus[1]),
.DATA_OUT(REG_Q[1]),
.DATA_IN(REG_D[1]),
.CAPTURE_DR(captureDr),
.UPDATE_DR(JUPDATE)
);
TYPEA DATA_BIT2 (
.CLK(JTCK),
.RESET_N(JRSTN),
.CLKEN(clk_enable),
.TDI(tdibus[1]),
.TDO(tdibus[2]),
.DATA_OUT(REG_Q[2]),
.DATA_IN(REG_D[2]),
.CAPTURE_DR(captureDr),
.UPDATE_DR(JUPDATE)
);
TYPEA DATA_BIT3 (
.CLK(JTCK),
.RESET_N(JRSTN),
.CLKEN(clk_enable),
.TDI(tdibus[2]),
.TDO(tdibus[3]),
.DATA_OUT(REG_Q[3]),
.DATA_IN(REG_D[3]),
.CAPTURE_DR(captureDr),
.UPDATE_DR(JUPDATE)
);
TYPEA DATA_BIT4 (
.CLK(JTCK),
.RESET_N(JRSTN),
.CLKEN(clk_enable),
.TDI(tdibus[3]),
.TDO(tdibus[4]),
.DATA_OUT(REG_Q[4]),
.DATA_IN(REG_D[4]),
.CAPTURE_DR(captureDr),
.UPDATE_DR(JUPDATE)
);
TYPEA DATA_BIT5 (
.CLK(JTCK),
.RESET_N(JRSTN),
.CLKEN(clk_enable),
.TDI(tdibus[4]),
.TDO(tdibus[5]),
.DATA_OUT(REG_Q[5]),
.DATA_IN(REG_D[5]),
.CAPTURE_DR(captureDr),
.UPDATE_DR(JUPDATE)
);
TYPEA DATA_BIT6 (
.CLK(JTCK),
.RESET_N(JRSTN),
.CLKEN(clk_enable),
.TDI(tdibus[5]),
.TDO(tdibus[6]),
.DATA_OUT(REG_Q[6]),
.DATA_IN(REG_D[6]),
.CAPTURE_DR(captureDr),
.UPDATE_DR(JUPDATE)
);
TYPEA DATA_BIT7 (
.CLK(JTCK),
.RESET_N(JRSTN),
.CLKEN(clk_enable),
.TDI(tdibus[6]),
.TDO(tdibus[7]),
.DATA_OUT(REG_Q[7]),
.DATA_IN(REG_D[7]),
.CAPTURE_DR(captureDr),
.UPDATE_DR(JUPDATE)
);
TYPEA ADDR_BIT0 (
.CLK(JTCK),
.RESET_N(JRSTN),
.CLKEN(clk_enable),
.TDI(tdibus[7]),
.TDO(tdibus[8]),
.DATA_OUT(REG_ADDR_Q[0]),
.DATA_IN(REG_ADDR_D[0]),
.CAPTURE_DR(captureDr),
.UPDATE_DR(JUPDATE)
);
TYPEA ADDR_BIT1 (
.CLK(JTCK),
.RESET_N(JRSTN),
.CLKEN(clk_enable),
.TDI(tdibus[8]),
.TDO(tdibus[9]),
.DATA_OUT(REG_ADDR_Q[1]),
.DATA_IN(REG_ADDR_D[1]),
.CAPTURE_DR(captureDr),
.UPDATE_DR(JUPDATE)
);
TYPEA ADDR_BIT2 (
.CLK(JTCK),
.RESET_N(JRSTN),
.CLKEN(clk_enable),
.TDI(tdibus[9]),
.TDO(JTDO2),
.DATA_OUT(REG_ADDR_Q[2]),
.DATA_IN(REG_ADDR_D[2]),
.CAPTURE_DR(captureDr),
.UPDATE_DR(JUPDATE)
);
/////////////////////////////////////////////////////
// Combinational logic
/////////////////////////////////////////////////////
assign clk_enable = JTAGREG_ENABLE & JCE2;
assign captureDr = !JSHIFT & JCE2;
// JCE2 is only active during shift
assign REG_UPDATE = JTAGREG_ENABLE & JUPDATE;
endmodule
// =============================================================================
// COPYRIGHT NOTICE
// Copyright 2006 (c) Lattice Semiconductor Corporation
// ALL RIGHTS RESERVED
// This confidential and proprietary software may be used only as authorised by
// a licensing agreement from Lattice Semiconductor Corporation.
// The entire notice above must be reproduced on all authorized copies and
// copies may only be made to the extent permitted by a licensing agreement from
// Lattice Semiconductor Corporation.
//
// Lattice Semiconductor Corporation TEL : 1-800-Lattice (USA and Canada)
// 5555 NE Moore Court 408-826-6000 (other locations)
// Hillsboro, OR 97124 web : http://www.latticesemi.com/
// U.S.A email: techsupport@latticesemi.com
// ============================================================================/
// FILE DETAILS
// Project : LatticeMico32
// File : lm32_adder.v
// Title : Integer adder / subtractor with comparison flag generation
// Dependencies : lm32_include.v
// Version : 6.1.17
// : Initial Release
// Version : 7.0SP2, 3.0
// : No Change
// Version : 3.1
// : No Change
// =============================================================================
`include "lm32_include.v"
/////////////////////////////////////////////////////
// Module interface
/////////////////////////////////////////////////////
module lm32_adder (
// ----- Inputs -------
adder_op_x,
adder_op_x_n,
operand_0_x,
operand_1_x,
// ----- Outputs -------
adder_result_x,
adder_carry_n_x,
adder_overflow_x
);
/////////////////////////////////////////////////////
// Inputs
/////////////////////////////////////////////////////
input adder_op_x; // Operating to perform, 0 for addition, 1 for subtraction
input adder_op_x_n; // Inverted version of adder_op_x
input [`LM32_WORD_RNG] operand_0_x; // Operand to add, or subtract from
input [`LM32_WORD_RNG] operand_1_x; // Opearnd to add, or subtract by
/////////////////////////////////////////////////////
// Outputs
/////////////////////////////////////////////////////
output [`LM32_WORD_RNG] adder_result_x; // Result of addition or subtraction
wire [`LM32_WORD_RNG] adder_result_x;
output adder_carry_n_x; // Inverted carry
wire adder_carry_n_x;
output adder_overflow_x; // Indicates if overflow occured, only valid for subtractions
reg adder_overflow_x;
/////////////////////////////////////////////////////
// Internal nets and registers
/////////////////////////////////////////////////////
wire a_sign; // Sign (i.e. positive or negative) of operand 0
wire b_sign; // Sign of operand 1
wire result_sign; // Sign of result
/////////////////////////////////////////////////////
// Instantiations
/////////////////////////////////////////////////////
lm32_addsub addsub (
// ----- Inputs -----
.DataA (operand_0_x),
.DataB (operand_1_x),
.Cin (adder_op_x),
.Add_Sub (adder_op_x_n),
// ----- Ouputs -----
.Result (adder_result_x),
.Cout (adder_carry_n_x)
);
/////////////////////////////////////////////////////
// Combinational Logic
/////////////////////////////////////////////////////
// Extract signs of operands and result
assign a_sign = operand_0_x[`LM32_WORD_WIDTH-1];
assign b_sign = operand_1_x[`LM32_WORD_WIDTH-1];
assign result_sign = adder_result_x[`LM32_WORD_WIDTH-1];
// Determine whether an overflow occured when performing a subtraction
always @(*)
begin
// +ve - -ve = -ve -> overflow
// -ve - +ve = +ve -> overflow
if ( (!a_sign & b_sign & result_sign)
|| (a_sign & !b_sign & !result_sign)
)
adder_overflow_x = `TRUE;
else
adder_overflow_x = `FALSE;
end
endmodule
// =============================================================================
// COPYRIGHT NOTICE
// Copyright 2006 (c) Lattice Semiconductor Corporation
// ALL RIGHTS RESERVED
// This confidential and proprietary software may be used only as authorised by
// a licensing agreement from Lattice Semiconductor Corporation.
// The entire notice above must be reproduced on all authorized copies and
// copies may only be made to the extent permitted by a licensing agreement from
// Lattice Semiconductor Corporation.
//
// Lattice Semiconductor Corporation TEL : 1-800-Lattice (USA and Canada)
// 5555 NE Moore Court 408-826-6000 (other locations)
// Hillsboro, OR 97124 web : http://www.latticesemi.com/
// U.S.A email: techsupport@latticesemi.com
// =============================================================================/
// FILE DETAILS
// Project : LatticeMico32
// File : lm32_addsub.v
// Title : PMI adder/subtractor.
// Version : 6.1.17
// : Initial Release
// Version : 7.0SP2, 3.0
// : No Change
// Version : 3.1
// : No Change
// =============================================================================
`include "lm32_include.v"
/////////////////////////////////////////////////////
// Module interface
/////////////////////////////////////////////////////
module lm32_addsub (
// ----- Inputs -------
DataA,
DataB,
Cin,
Add_Sub,
// ----- Outputs -------
Result,
Cout
);
/////////////////////////////////////////////////////
// Inputs
/////////////////////////////////////////////////////
input [31:0] DataA;
input [31:0] DataB;
input Cin;
input Add_Sub;
/////////////////////////////////////////////////////
// Outputs
/////////////////////////////////////////////////////
output [31:0] Result;
wire [31:0] Result;
output Cout;
wire Cout;
/////////////////////////////////////////////////////
// Instantiations
/////////////////////////////////////////////////////
// Modified for Milkymist: removed non-portable instantiated block
wire [32:0] tmp_addResult = DataA + DataB + Cin;
wire [32:0] tmp_subResult = DataA - DataB - !Cin;
assign Result = (Add_Sub == 1) ? tmp_addResult[31:0] : tmp_subResult[31:0];
assign Cout = (Add_Sub == 1) ? tmp_addResult[32] : !tmp_subResult[32];
endmodule
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
// =============================================================================
// COPYRIGHT NOTICE
// Copyright 2006 (c) Lattice Semiconductor Corporation
// ALL RIGHTS RESERVED
// This confidential and proprietary software may be used only as authorised by
// a licensing agreement from Lattice Semiconductor Corporation.
// The entire notice above must be reproduced on all authorized copies and
// copies may only be made to the extent permitted by a licensing agreement from
// Lattice Semiconductor Corporation.
//
// Lattice Semiconductor Corporation TEL : 1-800-Lattice (USA and Canada)
// 5555 NE Moore Court 408-826-6000 (other locations)
// Hillsboro, OR 97124 web : http://www.latticesemi.com/
// U.S.A email: techsupport@latticesemi.com
// =============================================================================/
// FILE DETAILS
// Project : LatticeMico32
// File : lm32_functions.v
// Title : Common functions
// Version : 6.1.17
// : Initial Release
// Version : 7.0SP2, 3.0
// : No Change
// Version : 3.5
// : Added function to generate log-of-two that rounds-up to
// : power-of-two
// =============================================================================
function integer clogb2;
input [31:0] value;
begin
for (clogb2 = 0; value > 0; clogb2 = clogb2 + 1)
value = value >> 1;
end
endfunction
function integer clogb2_v1;
input [31:0] value;
reg [31:0] i;
reg [31:0] temp;
begin
temp = 0;
i = 0;
for (i = 0; temp < value; i = i + 1)
temp = 1<<i;
clogb2_v1 = i-1;
end
endfunction
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
// =============================================================================
// COPYRIGHT NOTICE
// Copyright 2006 (c) Lattice Semiconductor Corporation
// ALL RIGHTS RESERVED
// This confidential and proprietary software may be used only as authorised by
// a licensing agreement from Lattice Semiconductor Corporation.
// The entire notice above must be reproduced on all authorized copies and
// copies may only be made to the extent permitted by a licensing agreement from
// Lattice Semiconductor Corporation.
//
// Lattice Semiconductor Corporation TEL : 1-800-Lattice (USA and Canada)
// 5555 NE Moore Court 408-826-6000 (other locations)
// Hillsboro, OR 97124 web : http://www.latticesemi.com/
// U.S.A email: techsupport@latticesemi.com
// =============================================================================/
// FILE DETAILS
// Project : LatticeMico32
// File : lm32_logic_op.v
// Title : Logic operations (and / or / not etc)
// Dependencies : lm32_include.v
// Version : 6.1.17
// : Initial Release
// Version : 7.0SP2, 3.0
// : No Change
// Version : 3.1
// : No Change
// =============================================================================
`include "lm32_include.v"
/////////////////////////////////////////////////////
// Module interface
/////////////////////////////////////////////////////
module lm32_logic_op (
// ----- Inputs -------
logic_op_x,
operand_0_x,
operand_1_x,
// ----- Outputs -------
logic_result_x
);
/////////////////////////////////////////////////////
// Inputs
/////////////////////////////////////////////////////
input [`LM32_LOGIC_OP_RNG] logic_op_x;
input [`LM32_WORD_RNG] operand_0_x;
input [`LM32_WORD_RNG] operand_1_x;
/////////////////////////////////////////////////////
// Outputs
/////////////////////////////////////////////////////
output [`LM32_WORD_RNG] logic_result_x;
reg [`LM32_WORD_RNG] logic_result_x;
/////////////////////////////////////////////////////
// Internal nets and registers
/////////////////////////////////////////////////////
integer logic_idx;
/////////////////////////////////////////////////////
// Combinational Logic
/////////////////////////////////////////////////////
always @(*)
begin
for(logic_idx = 0; logic_idx < `LM32_WORD_WIDTH; logic_idx = logic_idx + 1)
logic_result_x[logic_idx] = logic_op_x[{operand_1_x[logic_idx], operand_0_x[logic_idx]}];
end
endmodule
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
// =============================================================================
// COPYRIGHT NOTICE
// Copyright 2006 (c) Lattice Semiconductor Corporation
// ALL RIGHTS RESERVED
// This confidential and proprietary software may be used only as authorised by
// a licensing agreement from Lattice Semiconductor Corporation.
// The entire notice above must be reproduced on all authorized copies and
// copies may only be made to the extent permitted by a licensing agreement from
// Lattice Semiconductor Corporation.
//
// Lattice Semiconductor Corporation TEL : 1-800-Lattice (USA and Canada)
// 5555 NE Moore Court 408-826-6000 (other locations)
// Hillsboro, OR 97124 web : http://www.latticesemi.com/
// U.S.A email: techsupport@latticesemi.com
// =============================================================================/
// FILE DETAILS
// Project : LatticeMico32
// File : TYPEB.v
// Description:
// This is one of the two types of cells that are used to create ER1/ER2
// register bits.
// Dependencies : None
// Version : 6.1.17
// Modified typeb module to remove redundant DATA_OUT port.
// Version : 7.0SP2, 3.0
// : No Change
// Version : 3.1
// : No Change
// =============================================================================
module TYPEB
(
input CLK,
input RESET_N,
input CLKEN,
input TDI,
output TDO,
input DATA_IN,
input CAPTURE_DR
);
reg tdoInt;
always @ (negedge CLK or negedge RESET_N)
begin
if (RESET_N== 1'b0)
tdoInt <= 1'b0;
else if (CLK == 1'b0)
if (CLKEN==1'b1)
if (CAPTURE_DR==1'b0)
tdoInt <= TDI;
else
tdoInt <= DATA_IN;
end
assign TDO = tdoInt;
endmodule
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
#ifndef __VERSION_H
#define __VERSION_H
#define VERSION "0.2-tdc"
#endif /* __VERSION_H */
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
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