Initial commit

This commit is contained in:
2025-06-17 00:35:40 +08:00
commit 07c0b18e4c
33 changed files with 2300 additions and 0 deletions

66
Hardware/.gitignore vendored Normal file
View File

@@ -0,0 +1,66 @@
### Vivado ###
#########################################################################################################
## This is an example .gitignore file for Vivado, please treat it as an example as
## it might not be complete. In addition, XAPP 1165 should be followed.
#########
#Exclude all
*
!*/
!.gitignore
###########################################################################
## VIVADO
#Source files:
#Do NOT ignore VHDL, Verilog, block diagrams or EDIF files.
!*.vhd
!*.v
!*.sv
!*.bd
!*.edif
#IP files
#.xci: synthesis and implemented not possible - you need to return back to the previous version to generate output products
#.xci + .dcp: implementation possible but not re-synthesis
#*.xci(www.spiritconsortium.org)
!*.xci
#.xcix: Core container file
#.xcix: https://www.xilinx.com/support/documentation/sw_manuals/xilinx2016_2/ug896-vivado-ip.pdf (Page 41)
!*.xcix
#*.dcp(checkpoint files)
!*.dcp
!*.vds
!*.pb
#All bd comments and layout coordinates are stored within .ui
!*.ui
!*.ooc
#System Generator
!*.mdl
!*.slx
!*.bxml
#Simulation logic analyzer
!*.wcfg
!*.coe
#MIG
!*.prj
!*.mem
#Project files
#XPR + *.XML ? XPR (Files are merged into a single XPR file for 2014.1 version)
#Do NOT ignore *.xpr files
!*.xpr
#Include *.xml files for 2013.4 or earlier version
!*.xml
#Constraint files
#Do NOT ignore *.xdc files
!*.xdc
#TCL - files
!*.tcl
#Journal - files
!*.jou
#Reports
!*.rpt
!*.txt
!*.vdi
#C-files
!*.c
!*.h
!*.elf
!*.bmm
!*.xmp

View File

@@ -0,0 +1,60 @@
<?xml version="1.0" encoding="UTF-8" ?>
<document>
<!--The data in this file is primarily intended for consumption by Xilinx tools.
The structure and the elements are likely to change over the next few releases.
This means code written to parse this file will need to be revisited each subsequent release.-->
<application name="pa" timeStamp="Mon Jun 16 23:42:35 2025">
<section name="Project Information" visible="false">
<property name="ProjectID" value="bf8c3145fb1f463a9279744865a6650a" type="ProjectID"/>
<property name="ProjectIteration" value="1" type="ProjectIteration"/>
</section>
<section name="PlanAhead Usage" visible="true">
<item name="Project Data">
<property name="SrcSetCount" value="1" type="SrcSetCount"/>
<property name="ConstraintSetCount" value="1" type="ConstraintSetCount"/>
<property name="DesignMode" value="RTL" type="DesignMode"/>
<property name="SynthesisStrategy" value="Vivado Synthesis Defaults" type="SynthesisStrategy"/>
<property name="ImplStrategy" value="Vivado Implementation Defaults" type="ImplStrategy"/>
</item>
<item name="Java Command Handlers">
<property name="AddSources" value="2" type="JavaHandler"/>
<property name="NewProject" value="1" type="JavaHandler"/>
<property name="OpenProject" value="1" type="JavaHandler"/>
<property name="SetTopNode" value="1" type="JavaHandler"/>
<property name="SimulationRun" value="6" type="JavaHandler"/>
</item>
<item name="Gui Handlers">
<property name="AbstractCombinedPanel_REMOVE_SELECTED_ELEMENTS" value="1" type="GuiHandlerData"/>
<property name="AbstractFileView_RELOAD" value="2" type="GuiHandlerData"/>
<property name="AddSrcWizard_SPECIFY_SIMULATION_SPECIFIC_HDL_FILES" value="1" type="GuiHandlerData"/>
<property name="BaseDialog_CANCEL" value="1" type="GuiHandlerData"/>
<property name="BaseDialog_OK" value="12" type="GuiHandlerData"/>
<property name="ConfirmSaveTextEditsDialog_NO" value="1" type="GuiHandlerData"/>
<property name="CreateSrcFileDialog_FILE_NAME" value="10" type="GuiHandlerData"/>
<property name="FPGAChooser_FPGA_TABLE" value="1" type="GuiHandlerData"/>
<property name="FileSetPanel_FILE_SET_PANEL_TREE" value="15" type="GuiHandlerData"/>
<property name="FlowNavigatorTreePanel_FLOW_NAVIGATOR_TREE" value="9" type="GuiHandlerData"/>
<property name="GettingStartedView_CREATE_NEW_PROJECT" value="1" type="GuiHandlerData"/>
<property name="GettingStartedView_OPEN_PROJECT" value="1" type="GuiHandlerData"/>
<property name="PACommandNames_AUTO_UPDATE_HIER" value="5" type="GuiHandlerData"/>
<property name="PACommandNames_SET_AS_TOP" value="4" type="GuiHandlerData"/>
<property name="PACommandNames_SIMULATION_RUN_BEHAVIORAL" value="6" type="GuiHandlerData"/>
<property name="PAViews_CODE" value="1" type="GuiHandlerData"/>
<property name="ProjectNameChooser_CREATE_PROJECT_SUBDIRECTORY" value="1" type="GuiHandlerData"/>
<property name="ProjectNameChooser_PROJECT_NAME" value="1" type="GuiHandlerData"/>
<property name="SrcChooserPanel_ADD_HDL_AND_NETLIST_FILES_TO_YOUR_PROJECT" value="1" type="GuiHandlerData"/>
<property name="SrcChooserPanel_CREATE_FILE" value="10" type="GuiHandlerData"/>
<property name="SrcChooserTable_SRC_CHOOSER_TABLE" value="3" type="GuiHandlerData"/>
<property name="SrcMenu_IP_HIERARCHY" value="3" type="GuiHandlerData"/>
<property name="TclConsoleView_COPY" value="2" type="GuiHandlerData"/>
<property name="TclConsoleView_TCL_CONSOLE_CODE_EDITOR" value="35" type="GuiHandlerData"/>
<property name="WaveformNameTree_WAVEFORM_NAME_TREE" value="2" type="GuiHandlerData"/>
</item>
<item name="Other">
<property name="GuiMode" value="7" type="GuiMode"/>
<property name="BatchMode" value="0" type="BatchMode"/>
<property name="TclMode" value="3" type="TclMode"/>
</item>
</section>
</application>
</document>

View File

@@ -0,0 +1 @@
The files in this directory structure are automatically generated and managed by Vivado. Editing these files is not recommended.

View File

@@ -0,0 +1,11 @@
set curr_wave [current_wave_config]
if { [string length $curr_wave] == 0 } {
if { [llength [get_objects]] > 0} {
add_wave /
set_property needs_save false [current_wave_config]
} else {
send_msg_id Add_Wave-1 WARNING "No top level signals found. Simulator will start without a wave window. If you want to open a wave window go to 'File->New Waveform Configuration' or type 'create_wave_config' in the TCL console."
}
}
run 1000ns

View File

@@ -0,0 +1,17 @@
# compile verilog/system verilog design source files
verilog xil_defaultlib \
"../../../../LA32R.srcs/sources_1/new/alu.v" \
"../../../../LA32R.srcs/sources_1/new/control_unit.v" \
"../../../../LA32R.srcs/sources_1/new/cpu_top.v" \
"../../../../LA32R.srcs/sources_1/new/data_memory.v" \
"../../../../LA32R.srcs/sources_1/new/imm_extender.v" \
"../../../../LA32R.srcs/sources_1/new/instruction_memory.v" \
"../../../../LA32R.srcs/sources_1/new/pc.v" \
"../../../../LA32R.srcs/sources_1/new/register_file.v" \
"../../../../LA32R.srcs/sim_1/new/cpu_tb.v" \
# compile glbl module
verilog xil_defaultlib "glbl.v"
# Do not sort compile order
nosort

View File

@@ -0,0 +1,71 @@
// $Header: /devl/xcs/repo/env/Databases/CAEInterfaces/verunilibs/data/glbl.v,v 1.14 2010/10/28 20:44:00 fphillip Exp $
`ifndef GLBL
`define GLBL
`timescale 1 ps / 1 ps
module glbl ();
parameter ROC_WIDTH = 100000;
parameter TOC_WIDTH = 0;
//-------- STARTUP Globals --------------
wire GSR;
wire GTS;
wire GWE;
wire PRLD;
tri1 p_up_tmp;
tri (weak1, strong0) PLL_LOCKG = p_up_tmp;
wire PROGB_GLBL;
wire CCLKO_GLBL;
wire FCSBO_GLBL;
wire [3:0] DO_GLBL;
wire [3:0] DI_GLBL;
reg GSR_int;
reg GTS_int;
reg PRLD_int;
//-------- JTAG Globals --------------
wire JTAG_TDO_GLBL;
wire JTAG_TCK_GLBL;
wire JTAG_TDI_GLBL;
wire JTAG_TMS_GLBL;
wire JTAG_TRST_GLBL;
reg JTAG_CAPTURE_GLBL;
reg JTAG_RESET_GLBL;
reg JTAG_SHIFT_GLBL;
reg JTAG_UPDATE_GLBL;
reg JTAG_RUNTEST_GLBL;
reg JTAG_SEL1_GLBL = 0;
reg JTAG_SEL2_GLBL = 0 ;
reg JTAG_SEL3_GLBL = 0;
reg JTAG_SEL4_GLBL = 0;
reg JTAG_USER_TDO1_GLBL = 1'bz;
reg JTAG_USER_TDO2_GLBL = 1'bz;
reg JTAG_USER_TDO3_GLBL = 1'bz;
reg JTAG_USER_TDO4_GLBL = 1'bz;
assign (strong1, weak0) GSR = GSR_int;
assign (strong1, weak0) GTS = GTS_int;
assign (weak1, weak0) PRLD = PRLD_int;
initial begin
GSR_int = 1'b1;
PRLD_int = 1'b1;
#(ROC_WIDTH)
GSR_int = 1'b0;
PRLD_int = 1'b0;
end
initial begin
GTS_int = 1'b1;
#(TOC_WIDTH)
GTS_int = 1'b0;
end
endmodule
`endif

View File

@@ -0,0 +1,12 @@
#-----------------------------------------------------------
# Webtalk v2018.1 (64-bit)
# SW Build 2188600 on Wed Apr 4 18:40:38 MDT 2018
# IP Build 2185939 on Wed Apr 4 20:55:05 MDT 2018
# Start of session at: Tue Jun 17 00:19:34 2025
# Process ID: 36764
# Current directory: D:/Schoolwork/ComputerComposition/LA32R/Hardware/LA32R.sim/sim_1/behav/xsim
# Command line: wbtcv.exe -mode batch -source D:/Schoolwork/ComputerComposition/LA32R/Hardware/LA32R.sim/sim_1/behav/xsim/xsim.dir/cpu_tb_snapshot/webtalk/xsim_webtalk.tcl -notrace
# Log file: D:/Schoolwork/ComputerComposition/LA32R/Hardware/LA32R.sim/sim_1/behav/xsim/webtalk.log
# Journal file: D:/Schoolwork/ComputerComposition/LA32R/Hardware/LA32R.sim/sim_1/behav/xsim\webtalk.jou
#-----------------------------------------------------------
source D:/Schoolwork/ComputerComposition/LA32R/Hardware/LA32R.sim/sim_1/behav/xsim/xsim.dir/cpu_tb_snapshot/webtalk/xsim_webtalk.tcl -notrace

View File

@@ -0,0 +1,12 @@
#-----------------------------------------------------------
# Webtalk v2018.1 (64-bit)
# SW Build 2188600 on Wed Apr 4 18:40:38 MDT 2018
# IP Build 2185939 on Wed Apr 4 20:55:05 MDT 2018
# Start of session at: Tue Jun 17 00:19:31 2025
# Process ID: 16180
# Current directory: D:/Schoolwork/ComputerComposition/LA32R/Hardware/LA32R.sim/sim_1/behav/xsim
# Command line: wbtcv.exe -mode batch -source D:/Schoolwork/ComputerComposition/LA32R/Hardware/LA32R.sim/sim_1/behav/xsim/xsim.dir/cpu_tb_snapshot/webtalk/xsim_webtalk.tcl -notrace
# Log file: D:/Schoolwork/ComputerComposition/LA32R/Hardware/LA32R.sim/sim_1/behav/xsim/webtalk.log
# Journal file: D:/Schoolwork/ComputerComposition/LA32R/Hardware/LA32R.sim/sim_1/behav/xsim\webtalk.jou
#-----------------------------------------------------------
source D:/Schoolwork/ComputerComposition/LA32R/Hardware/LA32R.sim/sim_1/behav/xsim/xsim.dir/cpu_tb_snapshot/webtalk/xsim_webtalk.tcl -notrace

Binary file not shown.

View File

@@ -0,0 +1 @@
--debug "typical" --snapshot "cpu_tb_snapshot" "xil_defaultlib.cpu_tb" -log "elaborate.log"

View File

@@ -0,0 +1 @@
Breakpoint File Version 1.0

View File

@@ -0,0 +1 @@
xsim {cpu_tb_snapshot} -autoloadwcfg -runall

View File

@@ -0,0 +1,13 @@
#-----------------------------------------------------------
# xsim v2018.1 (64-bit)
# SW Build 2188600 on Wed Apr 4 18:40:38 MDT 2018
# IP Build 2185939 on Wed Apr 4 20:55:05 MDT 2018
# Start of session at: Tue Jun 17 00:19:32 2025
# Process ID: 35112
# Current directory: D:/Schoolwork/ComputerComposition/LA32R/Hardware/LA32R.sim/sim_1/behav/xsim
# Command line: xsim.exe -log ..\..\..\..\..\simulation.log -mode tcl -source {xsim.dir/cpu_tb_snapshot/xsim_script.tcl}
# Log file: D:/Schoolwork/ComputerComposition/LA32R/Hardware/LA32R.sim/sim_1/behav/xsim/../../../../../simulation.log
# Journal file: D:/Schoolwork/ComputerComposition/LA32R/Hardware/LA32R.sim/sim_1/behav/xsim\xsim.jou
#-----------------------------------------------------------
source xsim.dir/cpu_tb_snapshot/xsim_script.tcl
run -all

Binary file not shown.

View File

@@ -0,0 +1,101 @@
`timescale 1ns / 1ps
/*******************************************************************************
** Company: Nantong University
** Engineer: あやせももこ
**
** Create Date: 2025-06-16
** Design Name: LA32R Single Cycle CPU Testbench
** Module Name: cpu_tb
** Project Name: Computer Architecture Course Design
** Target Devices: Any
** Tool Versions: Vivado 2018.1
** Description:
** A self-checking testbench for the LA32R single-cycle CPU.
** - Generates clock and reset signals.
** - Instantiates the cpu_top module.
** - The instruction_memory module (instantiated within cpu_top) will load
** the machine code from "program.hex".
** - Monitors and displays the state of the PC and register file.
**
** Revision:
** Revision 0.01 - File Created
** Additional Comments:
** - Place this file and "program.hex" in the simulation directory.
**
*******************************************************************************/
`timescale 1ns / 1ps
module cpu_tb;
// --- 信号声明 (Signal Declarations) ---
reg clk;
reg rst;
// --- 实例化待测设计 (Instantiate the Design Under Test) ---
cpu_top uut (
.clk(clk),
.rst(rst)
);
// --- 时钟生成器 (Clock Generator) ---
localparam CLK_PERIOD = 10; // 时钟周期为10ns (Clock period is 10ns)
initial begin
clk = 0;
forever #(CLK_PERIOD / 2) clk = ~clk;
end
// --- 仿真控制 (Simulation Control) ---
initial begin
// 1. 复位CPU (Reset the CPU)
rst = 1;
#(CLK_PERIOD * 2); // 保持复位2个周期 (Hold reset for 2 cycles)
rst = 0;
$display("------------------------------------------------------------");
$display(" CPU Simulation Started. Reset is released. ");
$display("------------------------------------------------------------");
// 2. 运行一段时间后停止仿真
// Stop the simulation after a certain amount of time.
// The test program has an infinite loop at the end,
// so we need to manually stop the simulation.
#500; // 运行500ns (Run for 500ns)
// 3. 打印最终的寄存器状态
// Print the final state of the registers
$display("\n------------------------------------------------------------");
$display(" Simulation Finished. Final Register State: ");
$display("------------------------------------------------------------");
// 使用$display来显示寄存器的值注意路径需要正确
// Use $display to show register values. Note the path must be correct.
for (integer i = 0; i < 32; i = i + 1) begin
// 检查寄存器值是否非零以简化输出
// Check if register value is non-zero to simplify output
if (uut.u_reg_file.registers[i] != 32'h00000000) begin
$display("Register R%0d: 0x%08h", i, uut.u_reg_file.registers[i]);
end
end
$display("※Please note that registers with value zero are hidden.※");
$display("------------------------------------------------------------");
$finish; // 结束仿真 (End simulation)
end
// --- 监控和显示 (Monitoring and Display) ---
// 在每个时钟周期的下降沿打印信息确保所有信号稳定
// Display info at the falling edge of the clock to ensure all signals are stable.
always @(negedge clk) begin
if (!rst) begin
$display("Time: %0t ns | PC: 0x%08h | Instruction: 0x%08h | R4=0x%h R5=0x%h R6=0x%h",
$time,
uut.pc_out,
uut.instr,
uut.u_reg_file.registers[4],
uut.u_reg_file.registers[5],
uut.u_reg_file.registers[6]
);
end
end
endmodule

View File

@@ -0,0 +1,80 @@
`timescale 1ns / 1ps
/*******************************************************************************
** Company: Nantong University
** Engineer: あやせももこ
**
** Create Date: 2025-06-16
** Design Name: LA32R Single Cycle CPU
** Module Name: alu
** Project Name: Computer Architecture Course Design
** Target Devices: Any FPGA
** Tool Versions: Vivado 2018.1
** Description:
** This module implements the Arithmetic Logic Unit (ALU) for the LA32R CPU.
**
** [FIXED] The implementation of SLT now uses the $signed() system function
** to correctly handle comparisons that could cause overflow, such as
** comparing a positive and a negative number.
**
** Revision:
** Revision 0.02 - Corrected SLT implementation using $signed().
** Revision 0.01 - File Created
**
*******************************************************************************/
module alu (
input wire [31:0] a, // 操作数 A (Operand A)
input wire [31:0] b, // 操作数 B (Operand B)
input wire [3:0] alu_op, // ALU 操作控制码 (ALU Operation Control Code)
output reg [31:0] result, // 运算结果 (Result)
output wire zero, // 零标志位 (Zero Flag)
output wire lt // 小于标志位 (Less Than Flag for BLT)
);
// 定义ALU操作码的参数增强可读性
// Define parameters for ALU operations to enhance readability
localparam ALU_ADD = 4'b0000;
localparam ALU_SUB = 4'b0001;
localparam ALU_AND = 4'b0010;
localparam ALU_OR = 4'b0011;
localparam ALU_NOR = 4'b0100;
localparam ALU_SLT = 4'b0101;
localparam ALU_SLTU = 4'b0110;
// 减法结果的临时线网
// Temporary wire for subtraction result
wire [31:0] sub_result = a - b;
// [FIX] 使用$signed()进行稳健的有符号比较
// [FIX] Use $signed() for robust signed comparison
wire slt_res = ($signed(a) < $signed(b));
// 无符号比较
// Unsigned comparison
wire sltu_res = (a < b);
// 主组合逻辑: 根据alu_op计算结果
// Main combinational logic: calculate result based on alu_op
always @(*) begin
case (alu_op)
ALU_ADD: result = a + b; // 加法 (Addition)
ALU_SUB: result = sub_result; // 减法 (Subtraction)
ALU_AND: result = a & b; // 与 (AND)
ALU_OR: result = a | b; // 或 (OR)
ALU_NOR: result = ~(a | b); // 或非 (NOR)
ALU_SLT: result = {31'b0, slt_res}; // 有符号小于比较 (Set on Less Than, Signed)
ALU_SLTU: result = {31'b0, sltu_res}; // 无符号小于比较 (Set on Less Than, Unsigned)
default: result = 32'hxxxxxxxx; // 默认情况,输出不定态 (Default case, output undefined)
endcase
end
// 零标志位输出: 当减法结果为0时置1用于BEQ指令
// Zero flag output: set to 1 when the subtraction result is zero, for BEQ instruction
assign zero = (sub_result == 32'h00000000);
// 小于标志位输出: 用于BLT指令
// Less Than flag output: for BLT instruction
assign lt = slt_res;
endmodule

View File

@@ -0,0 +1,166 @@
`timescale 1ns / 1ps
/*******************************************************************************
** Company: Nantong University
** Engineer: あやせももこ
**
** Create Date: 2025-06-16
** Design Name: LA32R Single Cycle CPU
** Module Name: control_unit
** Project Name: Computer Architecture Course Design
** Target Devices: Any FPGA
** Tool Versions: Vivado 2018.1
** Description:
** This is the main control unit for the single-cycle LA32R CPU. It decodes
** the instruction's opcode and function fields to generate all necessary
** control signals for the datapath.
**
** [FIXED] Restructured the case statement to correctly handle instructions
** that share the same opcode, such as LD.W and ST.W.
**
** Revision:
** Revision 0.02 - Corrected case statement logic for shared opcodes.
** Revision 0.01 - File Created
**
*******************************************************************************/
module control_unit (
input wire [31:0] instr, // 指令输入 (Instruction Input)
input wire zero_flag, // 来自ALU的零标志位 (Zero flag from ALU)
input wire lt_flag, // 来自ALU的小于标志位 (Less-than flag from ALU)
output reg reg_write_en, // 寄存器写使能 (Register Write Enable)
output reg mem_to_reg, // 选择写回寄存器的数据源 (Selects data source for register write-back)
output reg mem_write_en, // 存储器写使能 (Memory Write Enable)
output reg alu_src, // 选择ALU的第二操作数源 (Selects ALU's second operand source)
output reg src_reg, // 选择寄存器堆的第二读地址源 (Selects Register File's second read address source)
output reg [2:0] ext_op, // 立即数扩展控制 (Immediate extender control)
output reg [3:0] alu_op, // ALU操作控制 (ALU operation control)
output wire pcsource // PC下一个地址来源选择 (PC next address source selection)
);
// 提取指令中的关键字段
// Extract key fields from the instruction
wire [5:0] opcode = instr[31:26];
wire [1:0] func2 = instr[21:20]; // for 3R-type per ISA document
wire [4:0] func5 = instr[19:15]; // for 3R-type per ISA document
wire [3:0] func4 = instr[25:22]; // for 2RI12-type
// 定义指令操作码 (Opcode Definitions)
localparam OP_GROUP_00 = 6'b000000; // Contains 3R instructions
localparam OP_ADDI_W = 6'b000010;
localparam OP_LUI12I = 6'b000101;
localparam OP_GROUP_0A = 6'b001010; // Contains LD.W, ST.W
localparam OP_B = 6'b010100;
localparam OP_BEQ = 6'b010110;
localparam OP_BLT = 6'b011000;
// 定义ALU操作码 (ALU Operation Definitions)
localparam ALU_ADD = 4'b0000;
localparam ALU_SUB = 4'b0001;
localparam ALU_AND = 4'b0010;
localparam ALU_OR = 4'b0011;
localparam ALU_NOR = 4'b0100;
localparam ALU_SLT = 4'b0101;
localparam ALU_SLTU = 4'b0110;
// 定义立即数扩展类型 (Immediate Extension Type Definitions)
localparam EXT_SI12 = 3'b001;
localparam EXT_SI16 = 3'b010;
localparam EXT_UI20 = 3'b011;
localparam EXT_SI26 = 3'b100;
// 主译码逻辑 (Main Decoding Logic)
always @(*) begin
// --- 控制信号默认值,防止生成锁存器 ---
// Default values for control signals to prevent latches
reg_write_en = 1'b0;
mem_to_reg = 1'b0;
mem_write_en = 1'b0;
alu_src = 1'b0;
src_reg = 1'b0;
ext_op = 3'bxxx;
alu_op = 4'bxxxx;
case (opcode)
OP_GROUP_00: begin
// Differentiate based on func2 field
if (func2 == 2'b01) begin // This is a 3R-type arithmetic/logic instruction
reg_write_en = 1'b1;
alu_src = 1'b0; // B operand comes from register
src_reg = 1'b0; // Second read address comes from rk field
// Further decode based on func5
case(func5)
5'b00000: alu_op = ALU_ADD;
5'b00010: alu_op = ALU_SUB;
5'b00100: alu_op = ALU_SLT;
5'b00101: alu_op = ALU_SLTU;
5'b01000: alu_op = ALU_NOR;
5'b01001: alu_op = ALU_AND;
5'b01010: alu_op = ALU_OR;
default: alu_op = 4'bxxxx;
endcase
end
end
OP_ADDI_W: begin
// ADDI.W has its own opcode
reg_write_en = 1'b1;
alu_src = 1'b1; // B operand comes from immediate
ext_op = EXT_SI12;
alu_op = ALU_ADD;
end
OP_LUI12I: begin
reg_write_en = 1'b1;
alu_src = 1'b1;
mem_to_reg = 1'b0; // ALU result writes back
ext_op = EXT_UI20;
alu_op = ALU_ADD; // ALU adds immediate to zero
end
OP_GROUP_0A: begin
// Differentiate LD.W and ST.W based on func4
if (func4 == 4'b0010) begin // LD.W
reg_write_en = 1'b1;
mem_to_reg = 1'b1; // Data from memory writes back
alu_src = 1'b1;
ext_op = EXT_SI12;
alu_op = ALU_ADD; // Calculate address
end
else if (func4 == 4'b0110) begin // ST.W
mem_write_en = 1'b1;
alu_src = 1'b1;
src_reg = 1'b1; // Second read address comes from rd field
ext_op = EXT_SI12;
alu_op = ALU_ADD; // Calculate address
end
end
OP_B: begin
// Unconditional branch
ext_op = EXT_SI26;
end
OP_BEQ: begin
alu_src = 1'b0;
src_reg = 1'b1; // Second read address comes from rd field
ext_op = EXT_SI16;
alu_op = ALU_SUB; // Compare
end
OP_BLT: begin
alu_src = 1'b0;
src_reg = 1'b1; // Second read address comes from rd field
ext_op = EXT_SI16;
alu_op = ALU_SUB; // Compare
end
default: begin
// All signals keep their default values
end
endcase
end
// PC下一个地址来源的逻辑
// Logic for PC's next address source
wire beq_cond = (opcode == OP_BEQ) && zero_flag;
wire blt_cond = (opcode == OP_BLT) && lt_flag;
wire b_cond = (opcode == OP_B);
assign pcsource = beq_cond || blt_cond || b_cond;
endmodule

View File

@@ -0,0 +1,144 @@
`timescale 1ns / 1ps
/*******************************************************************************
** Company: Nantong University
** Engineer: あやせももこ
**
** Create Date: 2025-06-16
** Design Name: LA32R Single Cycle CPU
** Module Name: cpu_top
** Project Name: Computer Architecture Course Design
** Target Devices: Any FPGA
** Tool Versions: Vivado 2018.1
** Description:
** This is the top-level module of the single-cycle LA32R CPU. It instantiates
** and connects all sub-modules including PC, memories, register file, ALU,
** immediate extender, and the control unit. The connections follow the
** datapath diagram provided in the course design guide.
**
** Revision:
** Revision 0.01 - File Created
** Additional Comments:
** - This file integrates the entire design.
**
*******************************************************************************/
`timescale 1ns / 1ps
module cpu_top (
input wire clk,
input wire rst
);
// --- 内部连线声明 (Internal Wire Declarations) ---
wire [31:0] pc_out;
wire [31:0] instr;
wire [31:0] imm_ext;
wire [31:0] read_data1;
wire [31:0] read_data2;
wire [31:0] alu_result;
wire [31:0] mem_read_data;
wire [31:0] write_back_data;
wire [31:0] alu_b_operand;
wire [4:0] reg_write_addr;
wire [4:0] reg_read_addr1;
wire [4:0] reg_read_addr2;
wire [4:0] reg_read_addr2_final;
// 控制信号
// Control Signals
wire reg_write_en;
wire mem_to_reg;
wire mem_write_en;
wire alu_src;
wire src_reg;
wire pcsource;
wire zero_flag;
wire lt_flag;
wire [2:0] ext_op;
wire [3:0] alu_op;
// --- 模块实例化 (Module Instantiation) ---
// PC (程序计数器)
pc u_pc (
.clk (clk),
.rst (rst),
.pcsource (pcsource),
.imm_ext (imm_ext),
.pc_out (pc_out)
);
// Instruction Memory (指令存储器)
instruction_memory u_inst_mem (
.addr (pc_out),
.instr (instr)
);
// Control Unit (控制单元)
control_unit u_ctrl_unit (
.instr (instr),
.zero_flag (zero_flag),
.lt_flag (lt_flag),
.reg_write_en (reg_write_en),
.mem_to_reg (mem_to_reg),
.mem_write_en (mem_write_en),
.alu_src (alu_src),
.src_reg (src_reg),
.ext_op (ext_op),
.alu_op (alu_op),
.pcsource (pcsource)
);
// Immediate Extender (立即数扩展单元)
imm_extender u_imm_ext (
.instr (instr),
.ext_op (ext_op),
.imm_ext (imm_ext)
);
// MUX for Register File's second read address (src_reg_mux)
assign reg_read_addr2_final = src_reg ? instr[4:0] : instr[14:10];
// Register File (寄存器堆)
register_file u_reg_file (
.clk (clk),
.rst (rst),
.reg_write_en (reg_write_en),
.read_addr1 (instr[9:5]),
.read_addr2 (reg_read_addr2_final),
.write_addr (instr[4:0]),
.write_data (write_back_data),
.read_data1 (read_data1),
.read_data2 (read_data2)
);
// MUX for ALU's second operand (alu_src_mux)
assign alu_b_operand = alu_src ? imm_ext : read_data2;
// ALU (算术逻辑单元)
alu u_alu (
.a (read_data1),
.b (alu_b_operand),
.alu_op (alu_op),
.result (alu_result),
.zero (zero_flag),
.lt (lt_flag)
);
// Data Memory (数据存储器)
data_memory u_data_mem (
.clk (clk),
.mem_write_en (mem_write_en),
.addr (alu_result),
.write_data (read_data2), // ST.W指令的数据来自第二个读端口(rd)
.read_data (mem_read_data)
);
// MUX for write-back data (mem_to_reg_mux)
assign write_back_data = mem_to_reg ? mem_read_data : alu_result;
endmodule

View File

@@ -0,0 +1,32 @@
`timescale 1ns / 1ps
/*******************************************************************************
** Data Memory Module
*******************************************************************************/
module data_memory (
input wire clk, // 时钟 (Clock)
input wire mem_write_en, // 写使能 (Write Enable)
input wire [31:0] addr, // 地址输入 (Address input)
input wire [31:0] write_data, // 待写数据 (Write data)
output wire [31:0] read_data // 读出数据 (Read data)
);
// 在FPGA中这会综合成一个同步写的RAM
// In an FPGA, this synthesizes into a synchronous-write RAM.
reg [31:0] mem [0:1023]; // 示例: 1KB数据空间 (Example: 1KB data space)
// 同步写
// Synchronous write
always @(posedge clk) begin
if (mem_write_en) begin
mem[addr[11:2]] <= write_data;
end
end
// 异步读
// Asynchronous read
assign read_data = mem[addr[11:2]];
endmodule

View File

@@ -0,0 +1,76 @@
`timescale 1ns / 1ps
/*******************************************************************************
** Company: Nantong University
** Engineer: あやせももこ
**
** Create Date: 2025-06-16
** Design Name: LA32R Single Cycle CPU
** Module Name: imm_extender
** Project Name: Computer Architecture Course Design
** Target Devices: Any FPGA
** Tool Versions: Vivado 2018.1
** Description:
** This module handles the sign/zero extension of immediate values found in
** various instruction formats of the LA32R architecture. It generates a 32-bit
** immediate value based on the instruction and the control signal `ext_op`.
**
** Supported Extensions:
** - 12-bit signed immediate (si12) for ADDI.W, LD.W, ST.W
** - 20-bit immediate (si20) for LUI12I.W (zero-extended low)
** - 16-bit signed offset for BEQ, BLT
** - 26-bit signed offset for B
**
** Revision:
** Revision 0.01 - File Created
** Additional Comments:
** - This is a purely combinational logic module.
**
*******************************************************************************/
module imm_extender (
input wire [31:0] instr, // 32位指令输入 (32-bit instruction input)
input wire [2:0] ext_op, // 扩展操作控制信号 (Extension operation control signal)
output reg [31:0] imm_ext // 32位扩展后的立即数输出 (32-bit extended immediate output)
);
// 定义立即数扩展类型的参数
// Define parameters for immediate extension types
localparam EXT_SI12 = 3'b001; // 12-bit signed immediate for I-type
localparam EXT_SI16 = 3'b010; // 16-bit signed offset for branches
localparam EXT_UI20 = 3'b011; // 20-bit immediate for LUI
localparam EXT_SI26 = 3'b100; // 26-bit signed offset for jump
// 提取指令中不同格式的立即数
// Extract immediate values from different instruction formats
wire [11:0] si12 = instr[21:10];
wire [15:0] si16 = instr[25:10];
wire [19:0] si20 = instr[24:5];
wire [25:0] si26 = {instr[9:0], instr[25:10]}; // B指令的offs[25:16][9:0], offs[15:0][25:10]
// 组合逻辑: 根据ext_op选择不同的扩展方式
// Combinational logic: select extension method based on ext_op
always @(*) begin
case (ext_op)
EXT_SI12:
// 对si12进行符号位扩展
// Sign-extend si12
imm_ext = {{20{si12[11]}}, si12};
EXT_SI16:
// 对si16进行符号位扩展并左移两位
// Sign-extend si16 and shift left by 2
imm_ext = {{14{si16[15]}}, si16, 2'b00};
EXT_UI20:
// 对si20进行高位加载低12位补0
// Load si20 to high bits, pad low 12 bits with 0
imm_ext = {si20, 12'b0};
EXT_SI26:
// 对si26进行符号位扩展并左移两位
// Sign-extend si26 and shift left by 2
imm_ext = {{4{si26[25]}}, si26, 2'b00};
default:
imm_ext = 32'hxxxxxxxx; // 默认情况,输出不定态
endcase
end
endmodule

View File

@@ -0,0 +1,31 @@
`timescale 1ns / 1ps
/*******************************************************************************
** Instruction Memory Module
*******************************************************************************/
module instruction_memory (
input wire [31:0] addr, // 地址输入 (Address input)
output wire [31:0] instr // 指令输出 (Instruction output)
);
// 指令存储器通常是只读的 (Instruction memory is typically read-only)
// 在FPGA中这会综合成一个ROM
// In an FPGA, this synthesizes into a ROM.
// 仿真时使用reg数组和$readmemh加载程序
// For simulation, use a reg array and $readmemh to load the program.
reg [31:0] mem [0:1023]; // 示例: 1024条指令空间 (Example: 1024 instruction space)
initial begin
// 从文件中加载指令
// Load instructions from a file.
// 你需要创建一个名为 "program.hex" 的文件
// You need to create a file named "program.hex".
$readmemh("../../../../../Software/program.hex", mem);
end
// 字节地址转换为字地址
// Convert byte address to word address.
assign instr = mem[addr[11:2]];
endmodule

View File

@@ -0,0 +1,56 @@
`timescale 1ns / 1ps
/*******************************************************************************
** Company: Nantong University
** Engineer: あやせももこ
**
** Create Date: 2025-06-16
** Design Name: LA32R Single Cycle CPU
** Module Name: pc
** Project Name: Computer Architecture Course Design
** Target Devices: Any FPGA
** Tool Versions: Vivado 2018.1
** Description:
** This module implements the Program Counter (PC) and its update logic.
** The PC is a 32-bit register that holds the address of the instruction
** to be fetched. It updates on every clock cycle.
**
** Update Logic:
** - If no branch/jump: PC_next = PC_current + 4
** - If branch/jump taken: PC_next = Branch/Jump Target Address
**
** Revision:
** Revision 0.01 - File Created
**
*******************************************************************************/
module pc (
input wire clk, // 时钟 (Clock)
input wire rst, // 复位 (Reset)
input wire pcsource, // PC下一个地址来源选择 (PC next address source selection)
input wire [31:0] imm_ext, // 来自立即数扩展单元的偏移量 (Offset from immediate extender)
output reg [31:0] pc_out // 当前PC值 (Current PC value)
);
wire [31:0] pc_plus_4;
wire [31:0] pc_branch;
wire [31:0] pc_next;
// PC寄存器
// PC register
always @(posedge clk or posedge rst) begin
if (rst) begin
pc_out <= 32'h00000000; // 复位到0地址
end else begin
pc_out <= pc_next;
end
end
// PC更新逻辑
// PC update logic
assign pc_plus_4 = pc_out + 32'd4;
assign pc_branch = pc_out + imm_ext; // 偏移量已经左移两位
assign pc_next = pcsource ? pc_branch : pc_plus_4;
endmodule

View File

@@ -0,0 +1,79 @@
`timescale 1ns / 1ps
/*******************************************************************************
** Company: Nantong University
** Engineer: あやせももこ
**
** Create Date: 2025-06-16
** Design Name: LA32R Single Cycle CPU
** Module Name: register_file
** Project Name: Computer Architecture Course Design
** Target Devices: Any FPGA
** Tool Versions: Vivado 2018.1
** Description:
** This module implements the 32x32-bit Register File for the LA32R CPU.
** It features two asynchronous read ports and one synchronous write port.
** A defensive design is implemented to ensure R0 is always zero.
**
** Features:
** - 32 general-purpose registers, each 32 bits wide.
** - Asynchronous read: Read ports reflect content immediately.
** - Synchronous write: Write operation occurs on the rising edge of the clock.
** - R0 Hardwired to Zero: Cannot be written to, and reading it always returns 0.
**
** Revision:
** Revision 0.01 - File Created
** Additional Comments:
** - Reset logic is included to initialize all registers to zero, which is good practice for simulation and synthesis.
**
*******************************************************************************/
module register_file (
input wire clk, // 时钟 (Clock)
input wire rst, // 复位 (Reset)
input wire reg_write_en, // 写使能 (Write Enable)
input wire [4:0] read_addr1, // 读地址1 (Read Address 1)
input wire [4:0] read_addr2, // 读地址2 (Read Address 2)
input wire [4:0] write_addr, // 写地址 (Write Address)
input wire [31:0] write_data, // 写数据 (Write Data)
output wire [31:0] read_data1, // 读数据1 (Read Data 1)
output wire [31:0] read_data2 // 读数据2 (Read Data 2)
);
// 声明32个32位的寄存器阵列
// Declare an array of 32 registers, each 32 bits wide.
reg [31:0] registers[0:31];
integer i;
// 同步写操作 (时钟上升沿触发)
// Synchronous write operation (triggered on the rising edge of the clock)
always @(posedge clk or posedge rst) begin
if (rst) begin
// 复位时将所有寄存器清零
// On reset, clear all registers to zero.
for (i = 0; i < 32; i = i + 1) begin
registers[i] <= 32'b0;
end
end else if (reg_write_en) begin
// 写使能有效时执行写操作
// When write enable is active, perform the write operation.
// 防御性设计确保不写入0号寄存器
// Defensive design: ensure register R0 is not written to.
if (write_addr != 5'd0) begin
registers[write_addr] <= write_data;
end
end
end
// 异步读操作1
// Asynchronous read port 1
// 防御性设计确保读取0号寄存器时返回0
// Defensive design: ensure reading from R0 always returns zero.
assign read_data1 = (read_addr1 == 5'd0) ? 32'b0 : registers[read_addr1];
// 异步读操作2
// Asynchronous read port 2
assign read_data2 = (read_addr2 == 5'd0) ? 32'b0 : registers[read_addr2];
endmodule

190
Hardware/LA32R.xpr Normal file
View File

@@ -0,0 +1,190 @@
<?xml version="1.0" encoding="UTF-8"?>
<!-- Product Version: Vivado v2018.1 (64-bit) -->
<!-- -->
<!-- Copyright 1986-2018 Xilinx, Inc. All Rights Reserved. -->
<Project Version="7" Minor="36" Path="D:/Schoolwork/ComputerComposition/LA32R/Hardware/LA32R.xpr">
<DefaultLaunch Dir="$PRUNDIR"/>
<Configuration>
<Option Name="Id" Val="f596246c226e443bb1e5f3be0fda7a89"/>
<Option Name="Part" Val="xc7a35tcsg324-1"/>
<Option Name="CompiledLibDir" Val="$PCACHEDIR/compile_simlib"/>
<Option Name="CompiledLibDirXSim" Val=""/>
<Option Name="CompiledLibDirModelSim" Val="$PCACHEDIR/compile_simlib/modelsim"/>
<Option Name="CompiledLibDirQuesta" Val="$PCACHEDIR/compile_simlib/questa"/>
<Option Name="CompiledLibDirIES" Val="$PCACHEDIR/compile_simlib/ies"/>
<Option Name="CompiledLibDirXcelium" Val="$PCACHEDIR/compile_simlib/xcelium"/>
<Option Name="CompiledLibDirVCS" Val="$PCACHEDIR/compile_simlib/vcs"/>
<Option Name="CompiledLibDirRiviera" Val="$PCACHEDIR/compile_simlib/riviera"/>
<Option Name="CompiledLibDirActivehdl" Val="$PCACHEDIR/compile_simlib/activehdl"/>
<Option Name="BoardPart" Val=""/>
<Option Name="ActiveSimSet" Val="sim_1"/>
<Option Name="DefaultLib" Val="xil_defaultlib"/>
<Option Name="ProjectType" Val="Default"/>
<Option Name="IPOutputRepo" Val="$PCACHEDIR/ip"/>
<Option Name="IPCachePermission" Val="read"/>
<Option Name="IPCachePermission" Val="write"/>
<Option Name="EnableCoreContainer" Val="FALSE"/>
<Option Name="CreateRefXciForCoreContainers" Val="FALSE"/>
<Option Name="IPUserFilesDir" Val="$PIPUSERFILESDIR"/>
<Option Name="IPStaticSourceDir" Val="$PIPUSERFILESDIR/ipstatic"/>
<Option Name="EnableBDX" Val="FALSE"/>
<Option Name="DSAVendor" Val="xilinx"/>
<Option Name="DSANumComputeUnits" Val="60"/>
<Option Name="WTXSimLaunchSim" Val="5"/>
<Option Name="WTModelSimLaunchSim" Val="0"/>
<Option Name="WTQuestaLaunchSim" Val="0"/>
<Option Name="WTIesLaunchSim" Val="0"/>
<Option Name="WTVcsLaunchSim" Val="0"/>
<Option Name="WTRivieraLaunchSim" Val="0"/>
<Option Name="WTActivehdlLaunchSim" Val="0"/>
<Option Name="WTXSimExportSim" Val="0"/>
<Option Name="WTModelSimExportSim" Val="0"/>
<Option Name="WTQuestaExportSim" Val="0"/>
<Option Name="WTIesExportSim" Val="0"/>
<Option Name="WTVcsExportSim" Val="0"/>
<Option Name="WTRivieraExportSim" Val="0"/>
<Option Name="WTActivehdlExportSim" Val="0"/>
<Option Name="GenerateIPUpgradeLog" Val="TRUE"/>
<Option Name="XSimRadix" Val="hex"/>
<Option Name="XSimTimeUnit" Val="ns"/>
<Option Name="XSimArrayDisplayLimit" Val="1024"/>
<Option Name="XSimTraceLimit" Val="65536"/>
<Option Name="SimTypes" Val="rtl"/>
</Configuration>
<FileSets Version="1" Minor="31">
<FileSet Name="sources_1" Type="DesignSrcs" RelSrcDir="$PSRCDIR/sources_1">
<Filter Type="Srcs"/>
<File Path="$PSRCDIR/sources_1/new/alu.v">
<FileInfo>
<Attr Name="UsedIn" Val="synthesis"/>
<Attr Name="UsedIn" Val="implementation"/>
<Attr Name="UsedIn" Val="simulation"/>
</FileInfo>
</File>
<File Path="$PSRCDIR/sources_1/new/control_unit.v">
<FileInfo>
<Attr Name="UsedIn" Val="synthesis"/>
<Attr Name="UsedIn" Val="implementation"/>
<Attr Name="UsedIn" Val="simulation"/>
</FileInfo>
</File>
<File Path="$PSRCDIR/sources_1/new/data_memory.v">
<FileInfo>
<Attr Name="UsedIn" Val="synthesis"/>
<Attr Name="UsedIn" Val="implementation"/>
<Attr Name="UsedIn" Val="simulation"/>
</FileInfo>
</File>
<File Path="$PSRCDIR/sources_1/new/imm_extender.v">
<FileInfo>
<Attr Name="UsedIn" Val="synthesis"/>
<Attr Name="UsedIn" Val="implementation"/>
<Attr Name="UsedIn" Val="simulation"/>
</FileInfo>
</File>
<File Path="$PSRCDIR/sources_1/new/instruction_memory.v">
<FileInfo>
<Attr Name="UsedIn" Val="synthesis"/>
<Attr Name="UsedIn" Val="implementation"/>
<Attr Name="UsedIn" Val="simulation"/>
</FileInfo>
</File>
<File Path="$PSRCDIR/sources_1/new/pc.v">
<FileInfo>
<Attr Name="UsedIn" Val="synthesis"/>
<Attr Name="UsedIn" Val="implementation"/>
<Attr Name="UsedIn" Val="simulation"/>
</FileInfo>
</File>
<File Path="$PSRCDIR/sources_1/new/register_file.v">
<FileInfo>
<Attr Name="UsedIn" Val="synthesis"/>
<Attr Name="UsedIn" Val="implementation"/>
<Attr Name="UsedIn" Val="simulation"/>
</FileInfo>
</File>
<File Path="$PSRCDIR/sources_1/new/cpu_top.v">
<FileInfo>
<Attr Name="UsedIn" Val="synthesis"/>
<Attr Name="UsedIn" Val="implementation"/>
<Attr Name="UsedIn" Val="simulation"/>
</FileInfo>
</File>
<Config>
<Option Name="DesignMode" Val="RTL"/>
<Option Name="TopModule" Val="cpu_top"/>
</Config>
</FileSet>
<FileSet Name="constrs_1" Type="Constrs" RelSrcDir="$PSRCDIR/constrs_1">
<Filter Type="Constrs"/>
<Config>
<Option Name="ConstrsType" Val="XDC"/>
</Config>
</FileSet>
<FileSet Name="sim_1" Type="SimulationSrcs" RelSrcDir="$PSRCDIR/sim_1">
<Filter Type="Srcs"/>
<File Path="$PSRCDIR/sim_1/new/cpu_tb.v">
<FileInfo>
<Attr Name="UsedIn" Val="synthesis"/>
<Attr Name="UsedIn" Val="implementation"/>
<Attr Name="UsedIn" Val="simulation"/>
</FileInfo>
</File>
<Config>
<Option Name="DesignMode" Val="RTL"/>
<Option Name="TopModule" Val="cpu_tb"/>
<Option Name="TopLib" Val="xil_defaultlib"/>
<Option Name="TopAutoSet" Val="TRUE"/>
<Option Name="TransportPathDelay" Val="0"/>
<Option Name="TransportIntDelay" Val="0"/>
<Option Name="SrcSet" Val="sources_1"/>
</Config>
</FileSet>
</FileSets>
<Simulators>
<Simulator Name="XSim">
<Option Name="Description" Val="Vivado Simulator"/>
<Option Name="CompiledLib" Val="0"/>
</Simulator>
<Simulator Name="ModelSim">
<Option Name="Description" Val="ModelSim Simulator"/>
</Simulator>
<Simulator Name="Questa">
<Option Name="Description" Val="Questa Advanced Simulator"/>
</Simulator>
<Simulator Name="Riviera">
<Option Name="Description" Val="Riviera-PRO Simulator"/>
</Simulator>
<Simulator Name="ActiveHDL">
<Option Name="Description" Val="Active-HDL Simulator"/>
</Simulator>
</Simulators>
<Runs Version="1" Minor="10">
<Run Id="synth_1" Type="Ft3:Synth" SrcSet="sources_1" Part="xc7a35tcsg324-1" ConstrsSet="constrs_1" Description="Vivado Synthesis Defaults" WriteIncrSynthDcp="false" State="current" IncludeInArchive="true">
<Strategy Version="1" Minor="2">
<StratHandle Name="Vivado Synthesis Defaults" Flow="Vivado Synthesis 2018"/>
<Step Id="synth_design"/>
</Strategy>
<ReportStrategy Name="Vivado Synthesis Default Reports" Flow="Vivado Synthesis 2018"/>
<Report Name="ROUTE_DESIGN.REPORT_METHODOLOGY" Enabled="1"/>
</Run>
<Run Id="impl_1" Type="Ft2:EntireDesign" Part="xc7a35tcsg324-1" ConstrsSet="constrs_1" Description="Default settings for Implementation." WriteIncrSynthDcp="false" State="current" SynthRun="synth_1" IncludeInArchive="true">
<Strategy Version="1" Minor="2">
<StratHandle Name="Vivado Implementation Defaults" Flow="Vivado Implementation 2018"/>
<Step Id="init_design"/>
<Step Id="opt_design"/>
<Step Id="power_opt_design"/>
<Step Id="place_design"/>
<Step Id="post_place_power_opt_design"/>
<Step Id="phys_opt_design"/>
<Step Id="route_design"/>
<Step Id="post_route_phys_opt_design"/>
<Step Id="write_bitstream"/>
</Strategy>
<ReportStrategy Name="Vivado Implementation Default Reports" Flow="Vivado Implementation 2018"/>
<Report Name="ROUTE_DESIGN.REPORT_METHODOLOGY" Enabled="1"/>
</Run>
</Runs>
<Board/>
</Project>