diff --git a/doc/getting_started.rst b/doc/getting_started.rst index 21c59396..c58407a5 100644 --- a/doc/getting_started.rst +++ b/doc/getting_started.rst @@ -8,7 +8,6 @@ This page discusses initial steps and requirements to start using Ibex in your d Register File ------------- -Ibex comes with two different register file implementations. -Depending on the target technology, either the implementation in ``ibex_register_file_ff.sv`` or the one in ``ibex_register_file_latch.sv`` should be selected. -For more information about the two register file implementations and their trade-offs, check out :ref:`register-file`. - +Ibex comes with three different register file implementations that can be selected using the enumerated parameter ``RegFile`` defined in :file:`rtl/ibex_pkg.sv`. +Depending on the target technology, either the flip-flop-based ("ibex_pkg::RegFileFF", default), the latch-based ("ibex_pkg::RegFileLatch") or an FPGA-targeted ("ibex_pkg::RegFileFPGA") implementation should be selected. +For more information about the three register file implementations and their trade-offs, check out :ref:`register-file`. diff --git a/doc/instruction_decode_execute.rst b/doc/instruction_decode_execute.rst index b7a80fb3..b79d5e43 100644 --- a/doc/instruction_decode_execute.rst +++ b/doc/instruction_decode_execute.rst @@ -42,7 +42,7 @@ The decoder takes uncompressed instruction data and issues appropriate control s Register File ------------- -Source Files: :file:`rtl/ibex_register_file_ff.sv` :file:`rtl/ibex_register_file_latch.sv` +Source Files: :file:`rtl/ibex_register_file_ff.sv` :file:`rtl/ibex_register_file_fpga.sv` :file:`rtl/ibex_register_file_latch.sv` See :ref:`register-file` for more details. diff --git a/doc/integration.rst b/doc/integration.rst index 254d3f47..fc6be2f4 100644 --- a/doc/integration.rst +++ b/doc/integration.rst @@ -20,6 +20,7 @@ Instantiation Template .RV32E ( 0 ), .RV32M ( ibex_pkg::RV32MFast ), .RV32B ( ibex_pkg::RV32BNone ), + .RegFile ( ibex_pkg::RegFileFF ), .ICache ( 0 ), .ICacheECC ( 0 ), .SecureIbex ( 0 ), @@ -75,53 +76,58 @@ Instantiation Template Parameters ---------- -+------------------------------+-------------------+------------+-----------------------------------------------------------------------+ -| Name | Type/Range | Default | Description | -+==============================+===================+============+=======================================================================+ -| ``PMPEnable`` | bit | 0 | Enable PMP support | -+------------------------------+-------------------+------------+-----------------------------------------------------------------------+ -| ``PMPGranularity`` | int (0..31) | 0 | Minimum granularity of PMP address matching | -+------------------------------+-------------------+------------+-----------------------------------------------------------------------+ -| ``PMPNumRegions`` | int (1..16) | 4 | Number implemented PMP regions (ignored if PMPEnable == 0) | -+------------------------------+-------------------+------------+-----------------------------------------------------------------------+ -| ``MHPMCounterNum`` | int (0..10) | 0 | Number of performance monitor event counters | -+------------------------------+-------------------+------------+-----------------------------------------------------------------------+ -| ``MHPMCounterWidth`` | int (64..1) | 40 | Bit width of performance monitor event counters | -+------------------------------+-------------------+------------+-----------------------------------------------------------------------+ -| ``RV32E`` | bit | 0 | RV32E mode enable (16 integer registers only) | -+------------------------------+-------------------+------------+-----------------------------------------------------------------------+ -| ``RV32M`` | ibex_pkg::rv32m_e | RV32MFast | M(ultiply) extension select: | -| | | | "ibex_pkg::RV32MNone": No M-extension | -| | | | "ibex_pkg::RV32MSlow": Slow multi-cycle multiplier, iterative divider | -| | | | "ibex_pkg::RV32MFast": 3-4 cycle multiplier, iterative divider | -| | | | "ibex_pkg::RV32MSingleCycle": 1-2 cycle multiplier, iterative divider | -+------------------------------+-------------------+------------+-----------------------------------------------------------------------+ -| ``RV32B`` | ibex_pkg::rv32b_e | RV32BNone | B(itmanipulation) extension select: | -| | | | "ibex_pkg::RV32BNone": No B-extension | -| | | | "ibex_pkg::RV32BBalanced": Sub-extensions Zbb, Zbs, Zbf and Zbt | -| | | | "ibex_pkg::RV32Full": All sub-extensions | -+------------------------------+-------------------+------------+-----------------------------------------------------------------------+ -| ``BranchTargetALU`` | bit | 0 | *EXPERIMENTAL* - Enables branch target ALU removing a stall | -| | | | cycle from taken branches | -+------------------------------+-------------------+------------+-----------------------------------------------------------------------+ -| ``WritebackStage`` | bit | 0 | *EXPERIMENTAL* - Enables third pipeline stage (writeback) | -| | | | improving performance of loads and stores | -+------------------------------+-------------------+------------+-----------------------------------------------------------------------+ -| ``ICache`` | bit | 0 | *EXPERIMENTAL* Enable instruction cache instead of prefetch | -| | | | buffer | -+------------------------------+-------------------+------------+-----------------------------------------------------------------------+ -| ``ICacheECC`` | bit | 0 | *EXPERIMENTAL* Enable SECDED ECC protection in ICache (if | -| | | | ICache == 1) | -+------------------------------+-------------------+------------+-----------------------------------------------------------------------+ -| ``SecureIbex`` | bit | 0 | *EXPERIMENTAL* Enable various additional features targeting | -| | | | secure code execution. | -+------------------------------+-------------------+------------+-----------------------------------------------------------------------+ -| ``DbgTriggerEn`` | bit | 0 | Enable debug trigger support (one trigger only) | -+------------------------------+-------------------+------------+-----------------------------------------------------------------------+ -| ``DmHaltAddr`` | int | 0x1A110800 | Address to jump to when entering Debug Mode | -+------------------------------+-------------------+------------+-----------------------------------------------------------------------+ -| ``DmExceptionAddr`` | int | 0x1A110808 | Address to jump to when an exception occurs while in Debug Mode | -+------------------------------+-------------------+------------+-----------------------------------------------------------------------+ ++------------------------------+---------------------+------------+-----------------------------------------------------------------------+ +| Name | Type/Range | Default | Description | ++==============================+=====================+============+=======================================================================+ +| ``PMPEnable`` | bit | 0 | Enable PMP support | ++------------------------------+---------------------+------------+-----------------------------------------------------------------------+ +| ``PMPGranularity`` | int (0..31) | 0 | Minimum granularity of PMP address matching | ++------------------------------+---------------------+------------+-----------------------------------------------------------------------+ +| ``PMPNumRegions`` | int (1..16) | 4 | Number implemented PMP regions (ignored if PMPEnable == 0) | ++------------------------------+---------------------+------------+-----------------------------------------------------------------------+ +| ``MHPMCounterNum`` | int (0..10) | 0 | Number of performance monitor event counters | ++------------------------------+---------------------+------------+-----------------------------------------------------------------------+ +| ``MHPMCounterWidth`` | int (64..1) | 40 | Bit width of performance monitor event counters | ++------------------------------+---------------------+------------+-----------------------------------------------------------------------+ +| ``RV32E`` | bit | 0 | RV32E mode enable (16 integer registers only) | ++------------------------------+---------------------+------------+-----------------------------------------------------------------------+ +| ``RV32M`` | ibex_pkg::rv32m_e | RV32MFast | M(ultiply) extension select: | +| | | | "ibex_pkg::RV32MNone": No M-extension | +| | | | "ibex_pkg::RV32MSlow": Slow multi-cycle multiplier, iterative divider | +| | | | "ibex_pkg::RV32MFast": 3-4 cycle multiplier, iterative divider | +| | | | "ibex_pkg::RV32MSingleCycle": 1-2 cycle multiplier, iterative divider | ++------------------------------+---------------------+------------+-----------------------------------------------------------------------+ +| ``RV32B`` | ibex_pkg::rv32b_e | RV32BNone | B(itmanipulation) extension select: | +| | | | "ibex_pkg::RV32BNone": No B-extension | +| | | | "ibex_pkg::RV32BBalanced": Sub-extensions Zbb, Zbs, Zbf and Zbt | +| | | | "ibex_pkg::RV32Full": All sub-extensions | ++------------------------------+---------------------+------------+-----------------------------------------------------------------------+ +| ``RegFile`` | ibex_pkg::regfile_e | RegFileFF | Register file implementation select: | +| | | | "ibex_pkg::RegFileFF": Generic flip-flop-based register file | +| | | | "ibex_pkg::RegFileFPGA": Register file for FPGA targets | +| | | | "ibex_pkg::RegFileLatch": Latch-based register file for ASIC targets | ++------------------------------+---------------------+------------+-----------------------------------------------------------------------+ +| ``BranchTargetALU`` | bit | 0 | *EXPERIMENTAL* - Enables branch target ALU removing a stall | +| | | | cycle from taken branches | ++------------------------------+---------------------+------------+-----------------------------------------------------------------------+ +| ``WritebackStage`` | bit | 0 | *EXPERIMENTAL* - Enables third pipeline stage (writeback) | +| | | | improving performance of loads and stores | ++------------------------------+---------------------+------------+-----------------------------------------------------------------------+ +| ``ICache`` | bit | 0 | *EXPERIMENTAL* Enable instruction cache instead of prefetch | +| | | | buffer | ++------------------------------+---------------------+------------+-----------------------------------------------------------------------+ +| ``ICacheECC`` | bit | 0 | *EXPERIMENTAL* Enable SECDED ECC protection in ICache (if | +| | | | ICache == 1) | ++------------------------------+---------------------+------------+-----------------------------------------------------------------------+ +| ``SecureIbex`` | bit | 0 | *EXPERIMENTAL* Enable various additional features targeting | +| | | | secure code execution. | ++------------------------------+---------------------+------------+-----------------------------------------------------------------------+ +| ``DbgTriggerEn`` | bit | 0 | Enable debug trigger support (one trigger only) | ++------------------------------+---------------------+------------+-----------------------------------------------------------------------+ +| ``DmHaltAddr`` | int | 0x1A110800 | Address to jump to when entering Debug Mode | ++------------------------------+---------------------+------------+-----------------------------------------------------------------------+ +| ``DmExceptionAddr`` | int | 0x1A110808 | Address to jump to when an exception occurs while in Debug Mode | ++------------------------------+---------------------+------------+-----------------------------------------------------------------------+ Any parameter marked *EXPERIMENTAL* when enabled is not verified to the same standard as the rest of the Ibex core. diff --git a/doc/register_file.rst b/doc/register_file.rst index c5c4c0fb..0cf00992 100644 --- a/doc/register_file.rst +++ b/doc/register_file.rst @@ -2,7 +2,7 @@ Register File ============= -Source FIles: :file:`rtl/ibex_register_file_ff.sv` :file:`rtl/ibex_register_file_latch.sv` +Source Files: :file:`rtl/ibex_register_file_ff.sv` :file:`rtl/ibex_register_file_fpga.sv` :file:`rtl/ibex_register_file_latch.sv` Ibex has either 31 or 15 32-bit registers if the RV32E extension is disabled or enabled, respectively. Register ``x0`` is statically bound to 0 and can only be read, it does not contain any sequential logic. @@ -10,7 +10,8 @@ Register ``x0`` is statically bound to 0 and can only be read, it does not conta The register file has two read ports and one write port, register file data is available the same cycle a read is requested. There is no write to read forwarding path so if one register is being both read and written the read will return the current value rather than the value being written. -There are two flavors of register file available, both having their own benefits and trade-offs. +There are three flavors of register file available, each having their own benefits and trade-offs. +The register file flavor is selected via the enumerated parameter ``RegFile`` defined in :file:`rtl/ibex_pkg.sv`. Flip-Flop-Based Register File ----------------------------- @@ -19,10 +20,11 @@ The flip-flop-based register file uses regular, positive-edge-triggered flip-flo This makes it the **first choice when simulating the design using Verilator**. -To select the flip-flop-based register file, make sure to use the source file ``ibex_register_file_ff.sv`` in your project. +This implementation can be selected by setting the ``RegFile`` parameter to "ibex_pkg::RegFileFF". +It is the default selection. FPGA Register File --------------------------- +------------------ The FPGA register file leverages synchronous-write / asynchronous-read RAM design elements, where available on FPGA targets. @@ -30,7 +32,7 @@ For Xilinx FPGAs, synthesis results in an implementation using RAM32M primitives This makes it the **first choice for FPGA synthesis**. -To select the FPGA register file, make sure to use the source file ``ibex_register_file_fpga.sv`` in your project. +To select the FPGA register file, set the ``RegFile`` parameter to "ibex_pkg::RegFileFPGA". Latch-Based Register File ------------------------- @@ -44,7 +46,7 @@ Simulation of the latch-based register file is possible using commercial tools. The latch-based register file can also be used for FPGA synthesis, but this is not recommended as FPGAs usually do not well support latches. -To select the latch-based register file, make sure to use the source file ``ibex_register_file_latch.sv`` in your project. +To select the latch-based register file, set the ``RegFile`` parameter to "ibex_pkg::RegFileLatch". In addition, a technology-specific clock gating cell must be provided to keep the clock inactive when the latches are not written. This cell must be wrapped in a module called ``prim_clock_gating``. For more information regarding the clock gating cell, checkout :ref:`getting-started`. diff --git a/dv/riscv_compliance/ibex_riscv_compliance.core b/dv/riscv_compliance/ibex_riscv_compliance.core index 1432b8a2..400f438d 100644 --- a/dv/riscv_compliance/ibex_riscv_compliance.core +++ b/dv/riscv_compliance/ibex_riscv_compliance.core @@ -42,6 +42,12 @@ parameters: paramtype: vlogdefine description: "Bitmanip implementation parameter enum. See the ibex_pkg::rv32b_e enum in ibex_pkg.sv for permitted values." + RegFile: + datatype: str + default: ibex_pkg::RegFileFF + paramtype: vlogdefine + description: "Register file implementation parameter enum. See the ibex_pkg::regfile_e enum in ibex_pkg.sv for permitted values." + BranchTargetALU: datatype: int paramtype: vlogparam @@ -82,6 +88,7 @@ targets: - RV32E - RV32M - RV32B + - RegFile - BranchTargetALU - WritebackStage - PMPEnable diff --git a/dv/riscv_compliance/rtl/ibex_riscv_compliance.sv b/dv/riscv_compliance/rtl/ibex_riscv_compliance.sv index 88ce7e73..55301739 100644 --- a/dv/riscv_compliance/rtl/ibex_riscv_compliance.sv +++ b/dv/riscv_compliance/rtl/ibex_riscv_compliance.sv @@ -15,14 +15,15 @@ module ibex_riscv_compliance ( input IO_RST_N ); - parameter bit PMPEnable = 1'b0; - parameter int unsigned PMPGranularity = 0; - parameter int unsigned PMPNumRegions = 4; - parameter bit RV32E = 1'b0; - parameter ibex_pkg::rv32m_e RV32M = ibex_pkg::RV32MFast; - parameter ibex_pkg::rv32b_e RV32B = ibex_pkg::RV32BNone; - parameter bit BranchTargetALU = 1'b0; - parameter bit WritebackStage = 1'b0; + parameter bit PMPEnable = 1'b0; + parameter int unsigned PMPGranularity = 0; + parameter int unsigned PMPNumRegions = 4; + parameter bit RV32E = 1'b0; + parameter ibex_pkg::rv32m_e RV32M = ibex_pkg::RV32MFast; + parameter ibex_pkg::rv32b_e RV32B = ibex_pkg::RV32BNone; + parameter ibex_pkg::regfile_e RegFile = ibex_pkg::RegFileFF; + parameter bit BranchTargetALU = 1'b0; + parameter bit WritebackStage = 1'b0; logic clk_sys, rst_sys_n; @@ -115,6 +116,7 @@ module ibex_riscv_compliance ( .RV32E (RV32E ), .RV32M (RV32M ), .RV32B (RV32B ), + .RegFile (RegFile ), .BranchTargetALU (BranchTargetALU ), .WritebackStage (WritebackStage ), .DmHaltAddr (32'h00000000 ), diff --git a/dv/uvm/core_ibex/ibex_dv.f b/dv/uvm/core_ibex/ibex_dv.f index ffb2060b..0c7bcf75 100644 --- a/dv/uvm/core_ibex/ibex_dv.f +++ b/dv/uvm/core_ibex/ibex_dv.f @@ -51,6 +51,8 @@ ${PRJ_DIR}/rtl/ibex_multdiv_fast.sv ${PRJ_DIR}/rtl/ibex_prefetch_buffer.sv ${PRJ_DIR}/rtl/ibex_fetch_fifo.sv ${PRJ_DIR}/rtl/ibex_register_file_ff.sv +${PRJ_DIR}/rtl/ibex_register_file_fpga.sv +${PRJ_DIR}/rtl/ibex_register_file_latch.sv ${PRJ_DIR}/rtl/ibex_pmp.sv ${PRJ_DIR}/rtl/ibex_core.sv ${PRJ_DIR}/rtl/ibex_core_tracing.sv diff --git a/dv/uvm/core_ibex/tb/core_ibex_tb_top.sv b/dv/uvm/core_ibex/tb/core_ibex_tb_top.sv index 6581369b..6c6f39bc 100644 --- a/dv/uvm/core_ibex/tb/core_ibex_tb_top.sv +++ b/dv/uvm/core_ibex/tb/core_ibex_tb_top.sv @@ -41,12 +41,17 @@ module core_ibex_tb_top; `define IBEX_CFG_RV32B ibex_pkg::RV32BNone `endif + `ifndef IBEX_CFG_RegFile + `define IBEX_CFG_RegFile ibex_pkg::RegFileFF + `endif + parameter bit PMPEnable = 1'b0; parameter int unsigned PMPGranularity = 0; parameter int unsigned PMPNumRegions = 4; parameter bit RV32E = 1'b0; parameter ibex_pkg::rv32m_e RV32M = `IBEX_CFG_RV32M; parameter ibex_pkg::rv32b_e RV32B = `IBEX_CFG_RV32B; + parameter ibex_pkg::regfile_e RegFile = `IBEX_CFG_RegFile; parameter bit BranchTargetALU = 1'b0; parameter bit WritebackStage = 1'b0; @@ -59,6 +64,7 @@ module core_ibex_tb_top; .RV32E (RV32E ), .RV32M (RV32M ), .RV32B (RV32B ), + .RegFile (RegFile ), .BranchTargetALU (BranchTargetALU ), .WritebackStage (WritebackStage ) ) dut ( diff --git a/examples/fpga/artya7/rtl/top_artya7.sv b/examples/fpga/artya7/rtl/top_artya7.sv index 37304b46..a6faecc6 100644 --- a/examples/fpga/artya7/rtl/top_artya7.sv +++ b/examples/fpga/artya7/rtl/top_artya7.sv @@ -43,6 +43,7 @@ module top_artya7 ( ibex_core #( + .RegFile(RegFileFPGA), .DmHaltAddr(32'h00000000), .DmExceptionAddr(32'h00000000) ) u_core ( diff --git a/examples/simple_system/ibex_simple_system.core b/examples/simple_system/ibex_simple_system.core index 8b1d95ff..318b5ad3 100644 --- a/examples/simple_system/ibex_simple_system.core +++ b/examples/simple_system/ibex_simple_system.core @@ -22,6 +22,10 @@ filesets: - ibex_simple_system.cc: { file_type: cppSource } - lint/verilator_waiver.vlt: {file_type: vlt} + files_lint_verible: + files: + - lint/verible_waiver.vbw: {file_type: veribleLintWaiver} + parameters: RV32E: datatype: int @@ -41,6 +45,12 @@ parameters: paramtype: vlogdefine description: "Bitmanip implementation parameter enum. See the ibex_pkg::rv32b_e enum in ibex_pkg.sv for permitted values." + RegFile: + datatype: str + default: ibex_pkg::RegFileFF + paramtype: vlogdefine + description: "Register file implementation parameter enum. See the ibex_pkg::regfile_e enum in ibex_pkg.sv for permitted values." + SRAMInitFile: datatype: str paramtype: vlogparam @@ -86,12 +96,14 @@ targets: default: &default_target filesets: - tool_verilator ? (files_verilator) + - tool_veriblelint ? (files_lint_verible) - files_sim toplevel: ibex_simple_system parameters: - RV32E - RV32M - RV32B + - RegFile - BranchTargetALU - WritebackStage - SecureIbex diff --git a/examples/simple_system/lint/verible_waiver.vbw b/examples/simple_system/lint/verible_waiver.vbw new file mode 100644 index 00000000..4a1696f0 --- /dev/null +++ b/examples/simple_system/lint/verible_waiver.vbw @@ -0,0 +1 @@ +waive --rule=macro-name-style --location="ibex_simple_system.sv" --regex="RegFile" \ No newline at end of file diff --git a/examples/simple_system/rtl/ibex_simple_system.sv b/examples/simple_system/rtl/ibex_simple_system.sv index 6a4769a3..39a3c0c4 100644 --- a/examples/simple_system/rtl/ibex_simple_system.sv +++ b/examples/simple_system/rtl/ibex_simple_system.sv @@ -14,6 +14,10 @@ `define RV32B ibex_pkg::RV32BNone `endif +`ifndef RegFile + `define RegFile ibex_pkg::RegFileFF +`endif + /** * Ibex simple system * @@ -31,16 +35,17 @@ module ibex_simple_system ( input IO_RST_N ); - parameter bit SecureIbex = 1'b0; - parameter bit PMPEnable = 1'b0; - parameter int unsigned PMPGranularity = 0; - parameter int unsigned PMPNumRegions = 4; - parameter bit RV32E = 1'b0; - parameter ibex_pkg::rv32m_e RV32M = `RV32M; - parameter ibex_pkg::rv32b_e RV32B = `RV32B; - parameter bit BranchTargetALU = 1'b0; - parameter bit WritebackStage = 1'b0; - parameter SRAMInitFile = ""; + parameter bit SecureIbex = 1'b0; + parameter bit PMPEnable = 1'b0; + parameter int unsigned PMPGranularity = 0; + parameter int unsigned PMPNumRegions = 4; + parameter bit RV32E = 1'b0; + parameter ibex_pkg::rv32m_e RV32M = `RV32M; + parameter ibex_pkg::rv32b_e RV32B = `RV32B; + parameter ibex_pkg::regfile_e RegFile = `RegFile; + parameter bit BranchTargetALU = 1'b0; + parameter bit WritebackStage = 1'b0; + parameter SRAMInitFile = ""; logic clk_sys = 1'b0, rst_sys_n; @@ -162,6 +167,7 @@ module ibex_simple_system ( .RV32E ( RV32E ), .RV32M ( RV32M ), .RV32B ( RV32B ), + .RegFile ( RegFile ), .BranchTargetALU ( BranchTargetALU ), .WritebackStage ( WritebackStage ), .DmHaltAddr ( 32'h00100000 ), diff --git a/ibex_configs.yaml b/ibex_configs.yaml index 9ccd4fa3..d7fca6ab 100644 --- a/ibex_configs.yaml +++ b/ibex_configs.yaml @@ -11,6 +11,7 @@ small: RV32E : 0 RV32M : "ibex_pkg::RV32MFast" RV32B : "ibex_pkg::RV32BNone" + RegFile : "ibex_pkg::RegFileFF" BranchTargetALU : 0 WritebackStage : 0 PMPEnable : 0 @@ -28,6 +29,7 @@ experimental-maxperf: RV32E : 0 RV32M : "ibex_pkg::RV32MSingleCycle" RV32B : "ibex_pkg::RV32BNone" + RegFile : "ibex_pkg::RegFileFF" BranchTargetALU : 1 WritebackStage : 1 PMPEnable : 0 @@ -39,6 +41,7 @@ experimental-maxperf-pmp: RV32E : 0 RV32M : "ibex_pkg::RV32MSingleCycle" RV32B : "ibex_pkg::RV32BNone" + RegFile : "ibex_pkg::RegFileFF" BranchTargetALU : 1 WritebackStage : 1 PMPEnable : 1 @@ -50,6 +53,7 @@ experimental-maxperf-pmp-bmbalanced: RV32E : 0 RV32M : "ibex_pkg::RV32MSingleCycle" RV32B : "ibex_pkg::RV32BBalanced" + RegFile : "ibex_pkg::RegFileFF" BranchTargetALU : 1 WritebackStage : 1 PMPEnable : 1 @@ -61,6 +65,7 @@ experimental-maxperf-pmp-bmfull: RV32E : 0 RV32M : "ibex_pkg::RV32MSingleCycle" RV32B : "ibex_pkg::RV32BFull" + RegFile : "ibex_pkg::RegFileFF" BranchTargetALU : 1 WritebackStage : 1 PMPEnable : 1 diff --git a/ibex_core.core b/ibex_core.core index 83c4c61a..25c6dc5d 100644 --- a/ibex_core.core +++ b/ibex_core.core @@ -31,11 +31,9 @@ filesets: - rtl/ibex_pmp.sv - rtl/ibex_wb_stage.sv - rtl/ibex_dummy_instr.sv - # XXX: Figure out the best way to switch these two implementations - # dynamically on the target. -# - rtl/ibex_register_file_latch.sv # ASIC -# - rtl/ibex_register_file_fpga.sv # FPGA - rtl/ibex_register_file_ff.sv # generic FF-based + - rtl/ibex_register_file_fpga.sv # FPGA + - rtl/ibex_register_file_latch.sv # ASIC - rtl/ibex_core.sv file_type: systemVerilogSource @@ -83,6 +81,12 @@ parameters: paramtype: vlogdefine description: "Bitmanip implementation parameter enum. See the ibex_pkg::rv32b_e enum in ibex_pkg.sv for permitted values." + RegFile: + datatype: str + default: ibex_pkg::RegFileFF + paramtype: vlogdefine + description: "Register file implementation parameter enum. See the ibex_pkg::regfile_e enum in ibex_pkg.sv for permitted values." + ICache: datatype: int default: 0 diff --git a/ibex_core_tracing.core b/ibex_core_tracing.core index c45088f8..2ec843db 100644 --- a/ibex_core_tracing.core +++ b/ibex_core_tracing.core @@ -41,6 +41,12 @@ parameters: paramtype: vlogdefine description: "Bitmanip implementation parameter enum. See the ibex_pkg::rv32b_e enum in ibex_pkg.sv for permitted values." + RegFile: + datatype: str + default: ibex_pkg::RegFileFF + paramtype: vlogdefine + description: "Register file implementation parameter enum. See the ibex_pkg::regfile_e enum in ibex_pkg.sv for permitted values." + ICache: datatype: int default: 0 @@ -105,6 +111,7 @@ targets: - RV32E - RV32M - RV32B + - RegFile - BranchTargetALU - WritebackStage - SecureIbex diff --git a/lint/verible_waiver.vbw b/lint/verible_waiver.vbw index 8ed90c5e..e69de29b 100644 --- a/lint/verible_waiver.vbw +++ b/lint/verible_waiver.vbw @@ -1 +0,0 @@ -waive --rule=module-filename --location="ibex_register_file_.+" diff --git a/lint/verilator_waiver.vlt b/lint/verilator_waiver.vlt index 8049d659..2e026c37 100644 --- a/lint/verilator_waiver.vlt +++ b/lint/verilator_waiver.vlt @@ -22,13 +22,6 @@ lint_off -rule WIDTH -file "*/rtl/ibex_core_tracing.sv" -match "*'WritebackStage lint_off -rule WIDTH -file "*/rtl/ibex_core_tracing.sv" -match "*'SecureIbex'*" lint_off -rule WIDTH -file "*/rtl/ibex_core_tracing.sv" -match "*'PMPEnable'*" -// Filename 'ibex_register_file_ff' does not match MODULE name: ibex_register_file -// ibex_register_file_ff and ibex_register_file_latch provide two -// implementation choices for the same module. -lint_off -rule DECLFILENAME -file "*/rtl/ibex_register_file_ff.sv" -lint_off -rule DECLFILENAME -file "*/rtl/ibex_register_file_latch.sv" -lint_off -rule DECLFILENAME -file "*/rtl/ibex_register_file_fpga.sv" - // Bits of signal are not used: shift_amt_compl[5] // cleaner to write all bits even if not all are used lint_off -rule UNUSED -file "*/rtl/ibex_alu.sv" -match "*'shift_amt_compl'[5]*" diff --git a/rtl/ibex_core.sv b/rtl/ibex_core.sv index 96439d09..bda3da00 100644 --- a/rtl/ibex_core.sv +++ b/rtl/ibex_core.sv @@ -13,22 +13,23 @@ * Top level module of the ibex RISC-V core */ module ibex_core #( - parameter bit PMPEnable = 1'b0, - parameter int unsigned PMPGranularity = 0, - parameter int unsigned PMPNumRegions = 4, - parameter int unsigned MHPMCounterNum = 0, - parameter int unsigned MHPMCounterWidth = 40, - parameter bit RV32E = 1'b0, - parameter ibex_pkg::rv32m_e RV32M = ibex_pkg::RV32MFast, - parameter ibex_pkg::rv32b_e RV32B = ibex_pkg::RV32BNone, - parameter bit BranchTargetALU = 1'b0, - parameter bit WritebackStage = 1'b0, - parameter bit ICache = 1'b0, - parameter bit ICacheECC = 1'b0, - parameter bit DbgTriggerEn = 1'b0, - parameter bit SecureIbex = 1'b0, - parameter int unsigned DmHaltAddr = 32'h1A110800, - parameter int unsigned DmExceptionAddr = 32'h1A110808 + parameter bit PMPEnable = 1'b0, + parameter int unsigned PMPGranularity = 0, + parameter int unsigned PMPNumRegions = 4, + parameter int unsigned MHPMCounterNum = 0, + parameter int unsigned MHPMCounterWidth = 40, + parameter bit RV32E = 1'b0, + parameter ibex_pkg::rv32m_e RV32M = ibex_pkg::RV32MFast, + parameter ibex_pkg::rv32b_e RV32B = ibex_pkg::RV32BNone, + parameter ibex_pkg::regfile_e RegFile = ibex_pkg::RegFileFF, + parameter bit BranchTargetALU = 1'b0, + parameter bit WritebackStage = 1'b0, + parameter bit ICache = 1'b0, + parameter bit ICacheECC = 1'b0, + parameter bit DbgTriggerEn = 1'b0, + parameter bit SecureIbex = 1'b0, + parameter int unsigned DmHaltAddr = 32'h1A110800, + parameter int unsigned DmExceptionAddr = 32'h1A110808 ) ( // Clock and Reset input logic clk_i, @@ -809,28 +810,67 @@ module ibex_core #( assign rf_ecc_err_comb = 1'b0; end - ibex_register_file #( - .RV32E (RV32E), - .DataWidth (RegFileDataWidth), - .DummyInstructions (DummyInstructions) - ) register_file_i ( - .clk_i ( clk_i ), - .rst_ni ( rst_ni ), + if (RegFile == RegFileFF) begin : gen_regfile_ff + ibex_register_file_ff #( + .RV32E ( RV32E ), + .DataWidth ( RegFileDataWidth ), + .DummyInstructions ( DummyInstructions ) + ) register_file_i ( + .clk_i ( clk_i ), + .rst_ni ( rst_ni ), - .test_en_i ( test_en_i ), - .dummy_instr_id_i ( dummy_instr_id ), + .test_en_i ( test_en_i ), + .dummy_instr_id_i ( dummy_instr_id ), - // Read port a - .raddr_a_i ( rf_raddr_a ), - .rdata_a_o ( rf_rdata_a_ecc ), - // Read port b - .raddr_b_i ( rf_raddr_b ), - .rdata_b_o ( rf_rdata_b_ecc ), - // write port - .waddr_a_i ( rf_waddr_wb ), - .wdata_a_i ( rf_wdata_wb_ecc ), - .we_a_i ( rf_we_wb ) - ); + .raddr_a_i ( rf_raddr_a ), + .rdata_a_o ( rf_rdata_a_ecc ), + .raddr_b_i ( rf_raddr_b ), + .rdata_b_o ( rf_rdata_b_ecc ), + .waddr_a_i ( rf_waddr_wb ), + .wdata_a_i ( rf_wdata_wb_ecc ), + .we_a_i ( rf_we_wb ) + ); + end else if (RegFile == RegFileFPGA) begin : gen_regfile_fpga + ibex_register_file_fpga #( + .RV32E ( RV32E ), + .DataWidth ( RegFileDataWidth ), + .DummyInstructions ( DummyInstructions ) + ) register_file_i ( + .clk_i ( clk_i ), + .rst_ni ( rst_ni ), + + .test_en_i ( test_en_i ), + .dummy_instr_id_i ( dummy_instr_id ), + + .raddr_a_i ( rf_raddr_a ), + .rdata_a_o ( rf_rdata_a_ecc ), + .raddr_b_i ( rf_raddr_b ), + .rdata_b_o ( rf_rdata_b_ecc ), + .waddr_a_i ( rf_waddr_wb ), + .wdata_a_i ( rf_wdata_wb_ecc ), + .we_a_i ( rf_we_wb ) + ); + end else if (RegFile == RegFileLatch) begin : gen_regfile_latch + ibex_register_file_latch #( + .RV32E ( RV32E ), + .DataWidth ( RegFileDataWidth ), + .DummyInstructions ( DummyInstructions ) + ) register_file_i ( + .clk_i ( clk_i ), + .rst_ni ( rst_ni ), + + .test_en_i ( test_en_i ), + .dummy_instr_id_i ( dummy_instr_id ), + + .raddr_a_i ( rf_raddr_a ), + .rdata_a_o ( rf_rdata_a_ecc ), + .raddr_b_i ( rf_raddr_b ), + .rdata_b_o ( rf_rdata_b_ecc ), + .waddr_a_i ( rf_waddr_wb ), + .wdata_a_i ( rf_wdata_wb_ecc ), + .we_a_i ( rf_we_wb ) + ); + end /////////////////// // Alert outputs // diff --git a/rtl/ibex_core_tracing.sv b/rtl/ibex_core_tracing.sv index 836e4fb8..3cb79fad 100644 --- a/rtl/ibex_core_tracing.sv +++ b/rtl/ibex_core_tracing.sv @@ -7,22 +7,23 @@ */ module ibex_core_tracing #( - parameter bit PMPEnable = 1'b0, - parameter int unsigned PMPGranularity = 0, - parameter int unsigned PMPNumRegions = 4, - parameter int unsigned MHPMCounterNum = 0, - parameter int unsigned MHPMCounterWidth = 40, - parameter bit RV32E = 1'b0, - parameter ibex_pkg::rv32m_e RV32M = ibex_pkg::RV32MFast, - parameter ibex_pkg::rv32b_e RV32B = ibex_pkg::RV32BNone, - parameter bit BranchTargetALU = 1'b0, - parameter bit WritebackStage = 1'b0, - parameter bit ICache = 1'b0, - parameter bit ICacheECC = 1'b0, - parameter bit DbgTriggerEn = 1'b0, - parameter bit SecureIbex = 1'b0, - parameter int unsigned DmHaltAddr = 32'h1A110800, - parameter int unsigned DmExceptionAddr = 32'h1A110808 + parameter bit PMPEnable = 1'b0, + parameter int unsigned PMPGranularity = 0, + parameter int unsigned PMPNumRegions = 4, + parameter int unsigned MHPMCounterNum = 0, + parameter int unsigned MHPMCounterWidth = 40, + parameter bit RV32E = 1'b0, + parameter ibex_pkg::rv32m_e RV32M = ibex_pkg::RV32MFast, + parameter ibex_pkg::rv32b_e RV32B = ibex_pkg::RV32BNone, + parameter ibex_pkg::regfile_e RegFile = ibex_pkg::RegFileFF, + parameter bit BranchTargetALU = 1'b0, + parameter bit WritebackStage = 1'b0, + parameter bit ICache = 1'b0, + parameter bit ICacheECC = 1'b0, + parameter bit DbgTriggerEn = 1'b0, + parameter bit SecureIbex = 1'b0, + parameter int unsigned DmHaltAddr = 32'h1A110800, + parameter int unsigned DmExceptionAddr = 32'h1A110808 ) ( // Clock and Reset input logic clk_i, @@ -110,6 +111,7 @@ module ibex_core_tracing #( .RV32E ( RV32E ), .RV32M ( RV32M ), .RV32B ( RV32B ), + .RegFile ( RegFile ), .BranchTargetALU ( BranchTargetALU ), .ICache ( ICache ), .ICacheECC ( ICacheECC ), diff --git a/rtl/ibex_pkg.sv b/rtl/ibex_pkg.sv index fbffb9d6..5abbcc61 100644 --- a/rtl/ibex_pkg.sv +++ b/rtl/ibex_pkg.sv @@ -12,6 +12,12 @@ package ibex_pkg; // Parameter Enums // ///////////////////// +typedef enum integer { + RegFileFF = 0, + RegFileFPGA = 1, + RegFileLatch = 2 +} regfile_e; + typedef enum integer { RV32MNone = 0, RV32MSlow = 1, diff --git a/rtl/ibex_register_file_ff.sv b/rtl/ibex_register_file_ff.sv index fe42fe9d..05892492 100644 --- a/rtl/ibex_register_file_ff.sv +++ b/rtl/ibex_register_file_ff.sv @@ -10,7 +10,7 @@ * This register file is based on flip flops. Use this register file when * targeting FPGA synthesis or Verilator simulation. */ -module ibex_register_file #( +module ibex_register_file_ff #( parameter bit RV32E = 0, parameter int unsigned DataWidth = 32, parameter bit DummyInstructions = 0 diff --git a/rtl/ibex_register_file_fpga.sv b/rtl/ibex_register_file_fpga.sv index aa88cdc4..50655451 100644 --- a/rtl/ibex_register_file_fpga.sv +++ b/rtl/ibex_register_file_fpga.sv @@ -11,7 +11,7 @@ * This register file is designed to make FPGA synthesis tools infer RAM primitives. For Xilinx * FPGA architectures, it will produce RAM32M primitives. Other vendors have not yet been tested. */ -module ibex_register_file #( +module ibex_register_file_fpga #( parameter bit RV32E = 0, parameter int unsigned DataWidth = 32, parameter bit DummyInstructions = 0 @@ -64,4 +64,4 @@ module ibex_register_file #( logic unused_dummy_instr; assign unused_dummy_instr = dummy_instr_id_i; -endmodule : ibex_register_file +endmodule diff --git a/rtl/ibex_register_file_latch.sv b/rtl/ibex_register_file_latch.sv index 0feb7a6e..8c5fb35b 100644 --- a/rtl/ibex_register_file_latch.sv +++ b/rtl/ibex_register_file_latch.sv @@ -11,7 +11,7 @@ * based RF. It requires a target technology-specific clock gating cell. Use this * register file when targeting ASIC synthesis or event-based simulators. */ -module ibex_register_file #( +module ibex_register_file_latch #( parameter bit RV32E = 0, parameter int unsigned DataWidth = 32, parameter bit DummyInstructions = 0 diff --git a/syn/lec_sv2v.sh b/syn/lec_sv2v.sh index 089f4283..ba89dc39 100755 --- a/syn/lec_sv2v.sh +++ b/syn/lec_sv2v.sh @@ -64,12 +64,6 @@ printf "\n\nLEC RESULTS:\n" for file in *.v; do export LEC_TOP=`basename -s .v $file` - # special case is file ibex_register_file_ff.sv, whose module has a - # different name than its file name - if [[ $LEC_TOP == "ibex_register_file_ff" ]]; then - export LEC_TOP="ibex_register_file" - fi - # run Conformal LEC lec -xl -nogui -nobanner \ -dofile ../lec_sv2v.do \ diff --git a/syn/tcl/lr_synth_flow_var_setup.tcl b/syn/tcl/lr_synth_flow_var_setup.tcl index d6fb96fa..8e2dd105 100644 --- a/syn/tcl/lr_synth_flow_var_setup.tcl +++ b/syn/tcl/lr_synth_flow_var_setup.tcl @@ -17,6 +17,7 @@ set_flow_bool_var ibex_branch_target_alu 0 "Enable branch target ALU in Ibex" set_flow_bool_var ibex_writeback_stage 0 "Enable writeback stage in Ibex" set_flow_var ibex_bitmanip 0 "Bitmanip extenion setting for Ibex (see ibex_pkg::rv32b_e for permitted values. Enum names are not supported in Yosys.)" set_flow_var ibex_multiplier 2 "Multiplier extension setting for Ibex (see ibex_pkg::rv32m_e for permitted values. Enum names are not supported in Yosys.)" +set_flow_var ibex_regfile 2 "Register file implementation selection for Ibex (see ibex_pkg::regfile_e for permitted values. Enum names are not supported in Yosys.)" source $lr_synth_config_file diff --git a/syn/tcl/yosys_run_synth.tcl b/syn/tcl/yosys_run_synth.tcl index 377ec925..7986f327 100644 --- a/syn/tcl/yosys_run_synth.tcl +++ b/syn/tcl/yosys_run_synth.tcl @@ -28,6 +28,8 @@ yosys "chparam -set RV32B $lr_synth_ibex_bitmanip ibex_core" yosys "chparam -set RV32M $lr_synth_ibex_multiplier ibex_core" +yosys "chparam -set RegFile $lr_synth_ibex_regfile ibex_core" + yosys "synth $flatten_opt -top $lr_synth_top_module" yosys "opt -purge"