URL
https://opencores.org/ocsvn/yifive/yifive/trunk
Subversion Repositories yifive
Compare Revisions
- This comparison shows the changes necessary to convert path
/
- from Rev 21 to Rev 22
- ↔ Reverse comparison
Rev 21 → Rev 22
/yifive/trunk/caravel_yifive/verilog/dv/io_ports/Makefile
25,7 → 25,9
## User Project Pointers |
UPRJ_VERILOG_PATH ?= ../../../verilog |
UPRJ_RTL_PATH = $(UPRJ_VERILOG_PATH)/rtl |
UPRJ_BEHAVIOURAL_MODELS = ../ |
UPRJ_BEHAVIOURAL_MODELS = ../model |
UPRJ_INCLUDE_PATH1 = $(UPRJ_RTL_PATH)/syntacore/scr1/src/includes |
UPRJ_INCLUDE_PATH2 = $(UPRJ_RTL_PATH)/sdram_ctrl/src/defs |
|
## RISCV GCC |
GCC_PATH?=/ef/apps/bin |
43,11 → 45,14
|
hex: ${PATTERN:=.hex} |
|
vvp: ${PATTERN:=.vvp} |
|
%.vvp: %_tb.v %.hex |
ifeq ($(SIM),RTL) |
iverilog -DFUNCTIONAL -DSIM -I $(PDK_PATH) \ |
iverilog -g2005-sv -DFUNCTIONAL -DSIM -I $(PDK_PATH) \ |
-I $(CARAVEL_BEHAVIOURAL_MODELS) -I $(CARAVEL_RTL_PATH) \ |
-I $(UPRJ_BEHAVIOURAL_MODELS) -I $(UPRJ_RTL_PATH) \ |
-I $(UPRJ_INCLUDE_PATH1) -I $(UPRJ_INCLUDE_PATH2) \ |
$< -o $@ |
else |
iverilog -DFUNCTIONAL -DSIM -DGL -I $(PDK_PATH) \ |
/yifive/trunk/caravel_yifive/verilog/dv/io_ports/io_ports_tb.v
49,8 → 49,10
end |
|
initial begin |
$dumpfile("io_ports.vcd"); |
$dumpvars(0, io_ports_tb); |
`ifdef WFDUMP |
$dumpfile("io_ports.vcd"); |
$dumpvars(0, io_ports_tb); |
`endif |
|
// Repeat cycles of 1000 clock edges as needed to complete testbench |
repeat (25) begin |
/yifive/trunk/caravel_yifive/verilog/dv/io_ports/mgmt_core.sv
0,0 → 1,153
// SPDX-FileCopyrightText: 2020 Efabless Corporation |
// |
// Licensed under the Apache License, Version 2.0 (the "License"); |
// you may not use this file except in compliance with the License. |
// You may obtain a copy of the License at |
// |
// http://www.apache.org/licenses/LICENSE-2.0 |
// |
// Unless required by applicable law or agreed to in writing, software |
// distributed under the License is distributed on an "AS IS" BASIS, |
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
// See the License for the specific language governing permissions and |
// limitations under the License. |
// SPDX-License-Identifier: Apache-2.0 |
|
`default_nettype none |
module mgmt_core ( |
`ifdef USE_POWER_PINS |
inout VPWR, |
inout VGND, |
`endif |
// GPIO (dedicated pad) |
output gpio_out_pad, // Connect to out on gpio pad |
input gpio_in_pad, // Connect to in on gpio pad |
output gpio_mode0_pad, // Connect to dm[0] on gpio pad |
output gpio_mode1_pad, // Connect to dm[2] on gpio pad |
output gpio_outenb_pad, // Connect to oe_n on gpio pad |
output gpio_inenb_pad, // Connect to inp_dis on gpio pad |
// Flash memory control (SPI master) |
output flash_csb, |
output flash_clk, |
output flash_csb_oeb, |
output flash_clk_oeb, |
output flash_io0_oeb, |
output flash_io1_oeb, |
output flash_io2_oeb, // through GPIO 36 |
output flash_io3_oeb, // through GPIO 37 |
output flash_csb_ieb, |
output flash_clk_ieb, |
output flash_io0_ieb, |
output flash_io1_ieb, |
output flash_io0_do, |
output flash_io1_do, |
output flash_io2_do, // through GPIO 36 |
output flash_io3_do, // through GPIO 37 |
input flash_io0_di, |
input flash_io1_di, |
// Master reset |
input resetb, |
input porb, |
// Clocking |
input clock, |
// LA signals |
input [127:0] la_input, // From User Project to cpu |
output [127:0] la_output, // From CPU to User Project |
output [127:0] la_oenb, // LA output enable |
output [127:0] la_iena, // LA input enable |
// Housekeeping SPI |
output sdo_out, |
output sdo_outenb, |
// JTAG |
output jtag_out, |
output jtag_outenb, |
// User Project Control Signals |
input [`MPRJ_IO_PADS-1:0] mgmt_in_data, |
output [`MPRJ_IO_PADS-1:0] mgmt_out_data, |
output [`MPRJ_PWR_PADS-1:0] pwr_ctrl_out, |
input mprj_vcc_pwrgood, |
input mprj2_vcc_pwrgood, |
input mprj_vdd_pwrgood, |
input mprj2_vdd_pwrgood, |
output mprj_io_loader_resetn, |
output mprj_io_loader_clock, |
output mprj_io_loader_data_1, |
output mprj_io_loader_data_2, |
// WB MI A (User project) |
input mprj_ack_i, |
input [31:0] mprj_dat_i, |
output mprj_cyc_o, |
output mprj_stb_o, |
output mprj_we_o, |
output [3:0] mprj_sel_o, |
output [31:0] mprj_adr_o, |
output [31:0] mprj_dat_o, |
|
output core_clk, |
output user_clk, |
output core_rstn, |
input [2:0] user_irq, |
output [2:0] user_irq_ena, |
|
// Metal programmed user ID / mask revision vector |
input [31:0] mask_rev, |
|
// MGMT area R/W interface for mgmt RAM |
output [`RAM_BLOCKS-1:0] mgmt_ena, |
output [(`RAM_BLOCKS*4)-1:0] mgmt_wen_mask, |
output [`RAM_BLOCKS-1:0] mgmt_wen, |
output [7:0] mgmt_addr, |
output [31:0] mgmt_wdata, |
input [(`RAM_BLOCKS*32)-1:0] mgmt_rdata, |
|
// MGMT area RO interface for user RAM |
output mgmt_ena_ro, |
output [7:0] mgmt_addr_ro, |
input [31:0] mgmt_rdata_ro |
); |
wire ext_clk_sel; |
wire pll_clk, pll_clk90; |
wire ext_reset; |
wire hk_connect; |
wire trap; |
wire irq_spi; |
|
// JTAG (to be implemented) |
wire jtag_out; |
wire jtag_out_pre = 1'b0; |
wire jtag_outenb = 1'b1; |
wire jtag_oenb_state; |
|
// SDO |
wire sdo_out; |
wire sdo_out_pre; |
wire sdo_oenb_state; |
|
// Housekeeping SPI vectors |
wire [4:0] spi_pll_div; |
wire [2:0] spi_pll_sel; |
wire [2:0] spi_pll90_sel; |
wire [25:0] spi_pll_trim; |
|
// Override default function for SDO and JTAG outputs if purposely |
// set for override by the management SoC. |
assign sdo_out = (sdo_oenb_state == 1'b0) ? mgmt_out_data[1] : sdo_out_pre; |
assign jtag_out = (jtag_oenb_state == 1'b0) ? mgmt_out_data[0] : jtag_out_pre; |
|
caravel_clocking clocking1( |
.ext_clk_sel(ext_clk_sel), |
.ext_clk(clock), |
.pll_clk(pll_clk), |
.pll_clk90(pll_clk90), |
.resetb(resetb), |
.sel(spi_pll_sel), |
.sel2(spi_pll90_sel), |
.ext_reset(ext_reset), // From housekeeping SPI |
.core_clk(core_clk), |
.user_clk(user_clk), |
.resetb_sync(core_rstn) |
); |
|
|
endmodule |
`default_nettype wire |
/yifive/trunk/caravel_yifive/verilog/dv/la_test1/Makefile
25,7 → 25,9
## User Project Pointers |
UPRJ_VERILOG_PATH ?= ../../../verilog |
UPRJ_RTL_PATH = $(UPRJ_VERILOG_PATH)/rtl |
UPRJ_BEHAVIOURAL_MODELS = ../ |
UPRJ_BEHAVIOURAL_MODELS = ../model |
UPRJ_INCLUDE_PATH1 = $(UPRJ_RTL_PATH)/syntacore/scr1/src/includes |
UPRJ_INCLUDE_PATH2 = $(UPRJ_RTL_PATH)/sdram_ctrl/src/defs |
|
## RISCV GCC |
GCC_PATH?=/ef/apps/bin |
43,11 → 45,14
|
hex: ${PATTERN:=.hex} |
|
vvp: ${PATTERN:=.vvp} |
|
%.vvp: %_tb.v %.hex |
ifeq ($(SIM),RTL) |
iverilog -DFUNCTIONAL -DSIM -I $(PDK_PATH) \ |
iverilog -g2005-sv -DFUNCTIONAL -DSIM -I $(PDK_PATH) \ |
-I $(CARAVEL_BEHAVIOURAL_MODELS) -I $(CARAVEL_RTL_PATH) \ |
-I $(UPRJ_BEHAVIOURAL_MODELS) -I $(UPRJ_RTL_PATH) \ |
-I $(UPRJ_INCLUDE_PATH1) -I $(UPRJ_INCLUDE_PATH2) \ |
$< -o $@ |
else |
iverilog -DFUNCTIONAL -DSIM -DGL -I $(PDK_PATH) \ |
/yifive/trunk/caravel_yifive/verilog/dv/la_test2/Makefile
25,7 → 25,9
## User Project Pointers |
UPRJ_VERILOG_PATH ?= ../../../verilog |
UPRJ_RTL_PATH = $(UPRJ_VERILOG_PATH)/rtl |
UPRJ_BEHAVIOURAL_MODELS = ../ |
UPRJ_BEHAVIOURAL_MODELS = ../model |
UPRJ_INCLUDE_PATH1 = $(UPRJ_RTL_PATH)/syntacore/scr1/src/includes |
UPRJ_INCLUDE_PATH2 = $(UPRJ_RTL_PATH)/sdram_ctrl/src/defs |
|
## RISCV GCC |
GCC_PATH?=/ef/apps/bin |
43,11 → 45,14
|
hex: ${PATTERN:=.hex} |
|
vvp: ${PATTERN:=.vvp} |
|
%.vvp: %_tb.v %.hex |
ifeq ($(SIM),RTL) |
iverilog -DFUNCTIONAL -DSIM -I $(PDK_PATH) \ |
iverilog -g2005-sv -DFUNCTIONAL -DSIM -I $(PDK_PATH) \ |
-I $(CARAVEL_BEHAVIOURAL_MODELS) -I $(CARAVEL_RTL_PATH) \ |
-I $(UPRJ_BEHAVIOURAL_MODELS) -I $(UPRJ_RTL_PATH) \ |
-I $(UPRJ_INCLUDE_PATH1) -I $(UPRJ_INCLUDE_PATH2) \ |
$< -o $@ |
else |
iverilog -DFUNCTIONAL -DSIM -DGL -I $(PDK_PATH) \ |
/yifive/trunk/caravel_yifive/verilog/dv/model/mt48lc8m8a2.v
0,0 → 1,964
/**************************************************************************************** |
* |
* File Name: MT48LC8M8A2.V |
* Version: 0.0f |
* Date: July 8th, 1999 |
* Model: BUS Functional |
* Simulator: Model Technology (PC version 5.2e PE) |
* |
* Dependencies: None |
* |
* Author: Son P. Huynh |
* Email: sphuynh@micron.com |
* Phone: (208) 368-3825 |
* Company: Micron Technology, Inc. |
* Model: MT48LC8M16A2 (2Meg x 8 x 4 Banks) |
* |
* Description: Micron 128Mb SDRAM Verilog model |
* |
* Limitation: - Doesn't check for 4096 cycle refresh |
* |
* Note: - Set simulator resolution to "ps" accuracy |
* - Set Debug = 0 to disable $display messages |
* |
* Disclaimer: THESE DESIGNS ARE PROVIDED "AS IS" WITH NO WARRANTY |
* WHATSOEVER AND MICRON SPECIFICALLY DISCLAIMS ANY |
* IMPLIED WARRANTIES OF MERCHANTABILITY, FITNESS FOR |
* A PARTICULAR PURPOSE, OR AGAINST INFRINGEMENT. |
* |
|
* All rights researved |
* |
* Rev Author Phone Date Changes |
* ---- ---------------------------- ---------- --------------------------------------- |
* 0.0f Son Huynh 208-368-3825 07/08/1999 - Fix tWR = 1 Clk + 7.5 ns (Auto) |
* Micron Technology Inc. - Fix tWR = 15 ns (Manual) |
* - Fix tRP (Autoprecharge to AutoRefresh) |
* |
* 0.0a Son Huynh 208-368-3825 05/13/1998 - First Release (from 64Mb rev 0.0e) |
* Micron Technology Inc. |
****************************************************************************************/ |
|
`timescale 1ns / 100ps |
|
module mt48lc8m8a2 (Dq, Addr, Ba, Clk, Cke, Cs_n, Ras_n, Cas_n, We_n, Dqm); |
|
parameter addr_bits = 12; |
parameter data_bits = 8; |
parameter col_bits = 9; |
parameter mem_sizes = 2097151; // 2 Meg |
|
inout [data_bits - 1 : 0] Dq; |
input [addr_bits - 1 : 0] Addr; |
input [1 : 0] Ba; |
input Clk; |
input Cke; |
input Cs_n; |
input Ras_n; |
input Cas_n; |
input We_n; |
input [0 : 0] Dqm; |
|
reg [data_bits - 1 : 0] Bank0 [0 : mem_sizes]; |
reg [data_bits - 1 : 0] Bank1 [0 : mem_sizes]; |
reg [data_bits - 1 : 0] Bank2 [0 : mem_sizes]; |
reg [data_bits - 1 : 0] Bank3 [0 : mem_sizes]; |
|
reg [1 : 0] Bank_addr [0 : 3]; // Bank Address Pipeline |
reg [col_bits - 1 : 0] Col_addr [0 : 3]; // Column Address Pipeline |
reg [3 : 0] Command [0 : 3]; // Command Operation Pipeline |
reg [0 : 0] Dqm_reg0, Dqm_reg1; // DQM Operation Pipeline |
reg [addr_bits - 1 : 0] B0_row_addr, B1_row_addr, B2_row_addr, B3_row_addr; |
|
reg [addr_bits - 1 : 0] Mode_reg; |
reg [data_bits - 1 : 0] Dq_reg, Dq_dqm; |
reg [col_bits - 1 : 0] Col_temp, Burst_counter; |
|
reg Act_b0, Act_b1, Act_b2, Act_b3; // Bank Activate |
reg Pc_b0, Pc_b1, Pc_b2, Pc_b3; // Bank Precharge |
|
reg [1 : 0] Bank_precharge [0 : 3]; // Precharge Command |
reg A10_precharge [0 : 3]; // Addr[10] = 1 (All banks) |
reg Auto_precharge [0 : 3]; // RW AutoPrecharge (Bank) |
reg Read_precharge [0 : 3]; // R AutoPrecharge |
reg Write_precharge [0 : 3]; // W AutoPrecharge |
integer Count_precharge [0 : 3]; // RW AutoPrecharge (Counter) |
reg RW_interrupt_read [0 : 3]; // RW Interrupt Read with Auto Precharge |
reg RW_interrupt_write [0 : 3]; // RW Interrupt Write with Auto Precharge |
|
reg Data_in_enable; |
reg Data_out_enable; |
|
reg [1 : 0] Bank, Previous_bank; |
reg [addr_bits - 1 : 0] Row; |
reg [col_bits - 1 : 0] Col, Col_brst; |
|
// Internal system clock |
reg CkeZ, Sys_clk; |
|
// Commands Decode |
wire Active_enable = ~Cs_n & ~Ras_n & Cas_n & We_n; |
wire Aref_enable = ~Cs_n & ~Ras_n & ~Cas_n & We_n; |
wire Burst_term = ~Cs_n & Ras_n & Cas_n & ~We_n; |
wire Mode_reg_enable = ~Cs_n & ~Ras_n & ~Cas_n & ~We_n; |
wire Prech_enable = ~Cs_n & ~Ras_n & Cas_n & ~We_n; |
wire Read_enable = ~Cs_n & Ras_n & ~Cas_n & We_n; |
wire Write_enable = ~Cs_n & Ras_n & ~Cas_n & ~We_n; |
|
// Burst Length Decode |
wire Burst_length_1 = ~Mode_reg[2] & ~Mode_reg[1] & ~Mode_reg[0]; |
wire Burst_length_2 = ~Mode_reg[2] & ~Mode_reg[1] & Mode_reg[0]; |
wire Burst_length_4 = ~Mode_reg[2] & Mode_reg[1] & ~Mode_reg[0]; |
wire Burst_length_8 = ~Mode_reg[2] & Mode_reg[1] & Mode_reg[0]; |
|
// CAS Latency Decode |
wire Cas_latency_2 = ~Mode_reg[6] & Mode_reg[5] & ~Mode_reg[4]; |
wire Cas_latency_3 = ~Mode_reg[6] & Mode_reg[5] & Mode_reg[4]; |
|
`ifdef VERBOSE |
wire Debug = 1'b1; // Debug messages : 1 = On |
`else |
wire Debug = 1'b0; // Debug messages : 1 = On |
`endif |
// Write Burst Mode |
wire Write_burst_mode = Mode_reg[9]; |
|
wire Dq_chk = Sys_clk & Data_in_enable; // Check setup/hold time for DQ |
|
assign Dq = Dq_reg; // DQ buffer |
|
// Commands Operation |
`define ACT 0 |
`define NOP 1 |
`define READ 2 |
`define READ_A 3 |
`define SDRAM_WRITE 4 |
`define WRITE_A 5 |
`define SDRAM_PRECH 6 |
`define SDRAM_A_REF 7 |
`define SDRAM_BST 8 |
`define SDRAM_LMR 9 |
|
// Timing Parameters for -75 (PC133) and CAS Latency = 2 |
parameter tAC = 6.0; |
parameter tHZ = 7.0; |
parameter tOH = 2.7; |
parameter tMRD = 2.0; // 2 Clk Cycles |
parameter tRAS = 44.0; |
parameter tRC = 66.0; |
parameter tRCD = 20.0; |
parameter tRP = 20.0; |
parameter tRRD = 15.0; |
parameter tWRa = 7.5; // A2 Version - Auto precharge mode only (1 Clk + 7.5 ns) |
parameter tWRp = 15.0; // A2 Version - Precharge mode only (15 ns) |
|
// Timing Check variable |
integer MRD_chk; |
integer WR_counter [0 : 3]; |
time WR_chk [0 : 3]; |
time RC_chk, RRD_chk; |
time RAS_chk0, RAS_chk1, RAS_chk2, RAS_chk3; |
time RCD_chk0, RCD_chk1, RCD_chk2, RCD_chk3; |
time RP_chk0, RP_chk1, RP_chk2, RP_chk3; |
|
initial begin |
|
Dq_reg = {data_bits{1'bz}}; |
{Data_in_enable, Data_out_enable} = 0; |
{Act_b0, Act_b1, Act_b2, Act_b3} = 4'b0000; |
{Pc_b0, Pc_b1, Pc_b2, Pc_b3} = 4'b0000; |
{WR_chk[0], WR_chk[1], WR_chk[2], WR_chk[3]} = 0; |
{WR_counter[0], WR_counter[1], WR_counter[2], WR_counter[3]} = 0; |
{RW_interrupt_read[0], RW_interrupt_read[1], RW_interrupt_read[2], RW_interrupt_read[3]} = 0; |
{RW_interrupt_write[0], RW_interrupt_write[1], RW_interrupt_write[2], RW_interrupt_write[3]} = 0; |
{MRD_chk, RC_chk, RRD_chk} = 0; |
{RAS_chk0, RAS_chk1, RAS_chk2, RAS_chk3} = 0; |
{RCD_chk0, RCD_chk1, RCD_chk2, RCD_chk3} = 0; |
{RP_chk0, RP_chk1, RP_chk2, RP_chk3} = 0; |
$timeformat (-9, 0, " ns", 12); |
//$readmemh("bank0.txt", Bank0); |
//$readmemh("bank1.txt", Bank1); |
//$readmemh("bank2.txt", Bank2); |
//$readmemh("bank3.txt", Bank3); |
end |
|
// System clock generator |
always begin |
@ (posedge Clk) begin |
Sys_clk = CkeZ; |
CkeZ = Cke; |
end |
@ (negedge Clk) begin |
Sys_clk = 1'b0; |
end |
end |
|
always @ (posedge Sys_clk) begin |
// Internal Commamd Pipelined |
Command[0] = Command[1]; |
Command[1] = Command[2]; |
Command[2] = Command[3]; |
Command[3] = `NOP; |
|
Col_addr[0] = Col_addr[1]; |
Col_addr[1] = Col_addr[2]; |
Col_addr[2] = Col_addr[3]; |
Col_addr[3] = {col_bits{1'b0}}; |
|
Bank_addr[0] = Bank_addr[1]; |
Bank_addr[1] = Bank_addr[2]; |
Bank_addr[2] = Bank_addr[3]; |
Bank_addr[3] = 2'b0; |
|
Bank_precharge[0] = Bank_precharge[1]; |
Bank_precharge[1] = Bank_precharge[2]; |
Bank_precharge[2] = Bank_precharge[3]; |
Bank_precharge[3] = 2'b0; |
|
A10_precharge[0] = A10_precharge[1]; |
A10_precharge[1] = A10_precharge[2]; |
A10_precharge[2] = A10_precharge[3]; |
A10_precharge[3] = 1'b0; |
|
// Dqm pipeline for Read |
Dqm_reg0 = Dqm_reg1; |
Dqm_reg1 = Dqm; |
|
// Read or Write with Auto Precharge Counter |
if (Auto_precharge[0] == 1'b1) begin |
Count_precharge[0] = Count_precharge[0] + 1; |
end |
if (Auto_precharge[1] == 1'b1) begin |
Count_precharge[1] = Count_precharge[1] + 1; |
end |
if (Auto_precharge[2] == 1'b1) begin |
Count_precharge[2] = Count_precharge[2] + 1; |
end |
if (Auto_precharge[3] == 1'b1) begin |
Count_precharge[3] = Count_precharge[3] + 1; |
end |
|
// tMRD Counter |
MRD_chk = MRD_chk + 1; |
|
// tWR Counter for Write |
WR_counter[0] = WR_counter[0] + 1; |
WR_counter[1] = WR_counter[1] + 1; |
WR_counter[2] = WR_counter[2] + 1; |
WR_counter[3] = WR_counter[3] + 1; |
|
// Auto Refresh |
if (Aref_enable == 1'b1) begin |
if (Debug) $display ("at time %t AREF : Auto Refresh", $time); |
// Auto Refresh to Auto Refresh |
if ($time - RC_chk < tRC) begin |
//->tb.test_control.error_detected; |
$display ("at time %t ERROR: tRC violation during Auto Refresh", $time); |
end |
// Precharge to Auto Refresh |
if ($time - RP_chk0 < tRP || $time - RP_chk1 < tRP || $time - RP_chk2 < tRP || $time - RP_chk3 < tRP) begin |
//->tb.test_control.error_detected; |
$display ("at time %t ERROR: tRP violation during Auto Refresh", $time); |
end |
// Precharge to Refresh |
if (Pc_b0 == 1'b0 || Pc_b1 == 1'b0 || Pc_b2 == 1'b0 || Pc_b3 == 1'b0) begin |
//->tb.test_control.error_detected; |
$display ("at time %t ERROR: All banks must be Precharge before Auto Refresh", $time); |
end |
// Record Current tRC time |
RC_chk = $time; |
end |
|
// Load Mode Register |
if (Mode_reg_enable == 1'b1) begin |
// Decode CAS Latency, Burst Length, Burst Type, and Write Burst Mode |
if (Pc_b0 == 1'b1 && Pc_b1 == 1'b1 && Pc_b2 == 1'b1 && Pc_b3 == 1'b1) begin |
Mode_reg = Addr; |
if (Debug) begin |
$display ("at time %t LMR : Load Mode Register", $time); |
// CAS Latency |
if (Addr[6 : 4] == 3'b010) |
$display (" CAS Latency = 2"); |
else if (Addr[6 : 4] == 3'b011) |
$display (" CAS Latency = 3"); |
else |
$display (" CAS Latency = Reserved"); |
// Burst Length |
if (Addr[2 : 0] == 3'b000) |
$display (" Burst Length = 1"); |
else if (Addr[2 : 0] == 3'b001) |
$display (" Burst Length = 2"); |
else if (Addr[2 : 0] == 3'b010) |
$display (" Burst Length = 4"); |
else if (Addr[2 : 0] == 3'b011) |
$display (" Burst Length = 8"); |
else if (Addr[3 : 0] == 4'b0111) |
$display (" Burst Length = Full"); |
else |
$display (" Burst Length = Reserved"); |
// Burst Type |
if (Addr[3] == 1'b0) |
$display (" Burst Type = Sequential"); |
else if (Addr[3] == 1'b1) |
$display (" Burst Type = Interleaved"); |
else |
$display (" Burst Type = Reserved"); |
// Write Burst Mode |
if (Addr[9] == 1'b0) |
$display (" Write Burst Mode = Programmed Burst Length"); |
else if (Addr[9] == 1'b1) |
$display (" Write Burst Mode = Single Location Access"); |
else |
$display (" Write Burst Mode = Reserved"); |
end |
end else begin |
|
//->tb.test_control.error_detected; |
$display ("at time %t ERROR: all banks must be Precharge before Load Mode Register", $time); |
end |
// REF to LMR |
if ($time - RC_chk < tRC) begin |
|
//->tb.test_control.error_detected; |
$display ("at time %t ERROR: tRC violation during Load Mode Register", $time); |
end |
// LMR to LMR |
if (MRD_chk < tMRD) begin |
|
//->tb.test_control.error_detected; |
$display ("at time %t ERROR: tMRD violation during Load Mode Register", $time); |
end |
MRD_chk = 0; |
end |
|
// Active Block (Latch Bank Address and Row Address) |
if (Active_enable == 1'b1) begin |
if (Ba == 2'b00 && Pc_b0 == 1'b1) begin |
{Act_b0, Pc_b0} = 2'b10; |
B0_row_addr = Addr [addr_bits - 1 : 0]; |
RCD_chk0 = $time; |
RAS_chk0 = $time; |
if (Debug) $display ("at time %t ACT : Bank = 0 Row = %d", $time, Addr); |
// Precharge to Activate Bank 0 |
if ($time - RP_chk0 < tRP) begin |
|
//->tb.test_control.error_detected; |
$display ("at time %t ERROR: tRP violation during Activate bank 0", $time); |
end |
end else if (Ba == 2'b01 && Pc_b1 == 1'b1) begin |
{Act_b1, Pc_b1} = 2'b10; |
B1_row_addr = Addr [addr_bits - 1 : 0]; |
RCD_chk1 = $time; |
RAS_chk1 = $time; |
if (Debug) $display ("at time %t ACT : Bank = 1 Row = %d", $time, Addr); |
// Precharge to Activate Bank 1 |
if ($time - RP_chk1 < tRP) begin |
|
//->tb.test_control.error_detected; |
$display ("at time %t ERROR: tRP violation during Activate bank 1", $time); |
end |
end else if (Ba == 2'b10 && Pc_b2 == 1'b1) begin |
{Act_b2, Pc_b2} = 2'b10; |
B2_row_addr = Addr [addr_bits - 1 : 0]; |
RCD_chk2 = $time; |
RAS_chk2 = $time; |
if (Debug) $display ("at time %t ACT : Bank = 2 Row = %d", $time, Addr); |
// Precharge to Activate Bank 2 |
if ($time - RP_chk2 < tRP) begin |
|
//->tb.test_control.error_detected; |
$display ("at time %t ERROR: tRP violation during Activate bank 2", $time); |
end |
end else if (Ba == 2'b11 && Pc_b3 == 1'b1) begin |
{Act_b3, Pc_b3} = 2'b10; |
B3_row_addr = Addr [addr_bits - 1 : 0]; |
RCD_chk3 = $time; |
RAS_chk3 = $time; |
if (Debug) $display ("at time %t ACT : Bank = 3 Row = %d", $time, Addr); |
// Precharge to Activate Bank 3 |
if ($time - RP_chk3 < tRP) begin |
|
//->tb.test_control.error_detected; |
$display ("at time %t ERROR: tRP violation during Activate bank 3", $time); |
end |
end else if (Ba == 2'b00 && Pc_b0 == 1'b0) begin |
|
//->tb.test_control.error_detected; |
$display ("at time %t ERROR: Bank 0 is not Precharged.", $time); |
end else if (Ba == 2'b01 && Pc_b1 == 1'b0) begin |
|
//->tb.test_control.error_detected; |
$display ("at time %t ERROR: Bank 1 is not Precharged.", $time); |
end else if (Ba == 2'b10 && Pc_b2 == 1'b0) begin |
|
//->tb.test_control.error_detected; |
$display ("at time %t ERROR: Bank 2 is not Precharged.", $time); |
end else if (Ba == 2'b11 && Pc_b3 == 1'b0) begin |
|
//->tb.test_control.error_detected; |
$display ("at time %t ERROR: Bank 3 is not Precharged.", $time); |
end |
// Active Bank A to Active Bank B |
if ((Previous_bank != Ba) && ($time - RRD_chk < tRRD)) begin |
|
//->tb.test_control.error_detected; |
$display ("at time %t ERROR: tRRD violation during Activate bank = %d", $time, Ba); |
end |
// Load Mode Register to Active |
if (MRD_chk < tMRD ) begin |
|
//->tb.test_control.error_detected; |
$display ("at time %t ERROR: tMRD violation during Activate bank = %d", $time, Ba); |
end |
// Auto Refresh to Activate |
if ($time - RC_chk < tRC) begin |
|
//->tb.test_control.error_detected; |
$display ("at time %t ERROR: tRC violation during Activate bank = %d", $time, Ba); |
end |
// Record variables for checking violation |
RRD_chk = $time; |
Previous_bank = Ba; |
end |
|
// Precharge Block |
if (Prech_enable == 1'b1) begin |
if (Addr[10] == 1'b1) begin |
{Pc_b0, Pc_b1, Pc_b2, Pc_b3} = 4'b1111; |
{Act_b0, Act_b1, Act_b2, Act_b3} = 4'b0000; |
RP_chk0 = $time; |
RP_chk1 = $time; |
RP_chk2 = $time; |
RP_chk3 = $time; |
if (Debug) $display ("at time %t PRE : Bank = ALL",$time); |
// Activate to Precharge all banks |
if (($time - RAS_chk0 < tRAS) || ($time - RAS_chk1 < tRAS) || |
($time - RAS_chk2 < tRAS) || ($time - RAS_chk3 < tRAS)) begin |
|
//->tb.test_control.error_detected; |
$display ("at time %t ERROR: tRAS violation during Precharge all bank", $time); |
end |
// tWR violation check for write |
if (($time - WR_chk[0] < tWRp) || ($time - WR_chk[1] < tWRp) || |
($time - WR_chk[2] < tWRp) || ($time - WR_chk[3] < tWRp)) begin |
|
//->tb.test_control.error_detected; |
$display ("at time %t ERROR: tWR violation during Precharge all bank", $time); |
end |
end else if (Addr[10] == 1'b0) begin |
if (Ba == 2'b00) begin |
{Pc_b0, Act_b0} = 2'b10; |
RP_chk0 = $time; |
if (Debug) $display ("at time %t PRE : Bank = 0",$time); |
// Activate to Precharge Bank 0 |
if ($time - RAS_chk0 < tRAS) begin |
|
//->tb.test_control.error_detected; |
$display ("at time %t ERROR: tRAS violation during Precharge bank 0", $time); |
end |
end else if (Ba == 2'b01) begin |
{Pc_b1, Act_b1} = 2'b10; |
RP_chk1 = $time; |
if (Debug) $display ("at time %t PRE : Bank = 1",$time); |
// Activate to Precharge Bank 1 |
if ($time - RAS_chk1 < tRAS) begin |
|
//->tb.test_control.error_detected; |
$display ("at time %t ERROR: tRAS violation during Precharge bank 1", $time); |
end |
end else if (Ba == 2'b10) begin |
{Pc_b2, Act_b2} = 2'b10; |
RP_chk2 = $time; |
if (Debug) $display ("at time %t PRE : Bank = 2",$time); |
// Activate to Precharge Bank 2 |
if ($time - RAS_chk2 < tRAS) begin |
|
//->tb.test_control.error_detected; |
$display ("at time %t ERROR: tRAS violation during Precharge bank 2", $time); |
end |
end else if (Ba == 2'b11) begin |
{Pc_b3, Act_b3} = 2'b10; |
RP_chk3 = $time; |
if (Debug) $display ("at time %t PRE : Bank = 3",$time); |
// Activate to Precharge Bank 3 |
if ($time - RAS_chk3 < tRAS) begin |
|
//->tb.test_control.error_detected; |
$display ("at time %t ERROR: tRAS violation during Precharge bank 3", $time); |
end |
end |
// tWR violation check for write |
if ($time - WR_chk[Ba] < tWRp) begin |
|
//->tb.test_control.error_detected; |
$display ("at time %t ERROR: tWR violation during Precharge bank %d", $time, Ba); |
end |
end |
// Terminate a Write Immediately (if same bank or all banks) |
if (Data_in_enable == 1'b1 && (Bank == Ba || Addr[10] == 1'b1)) begin |
Data_in_enable = 1'b0; |
end |
// Precharge Command Pipeline for Read |
if (Cas_latency_3 == 1'b1) begin |
Command[2] = `SDRAM_PRECH; |
Bank_precharge[2] = Ba; |
A10_precharge[2] = Addr[10]; |
end else if (Cas_latency_2 == 1'b1) begin |
Command[1] = `SDRAM_PRECH; |
Bank_precharge[1] = Ba; |
A10_precharge[1] = Addr[10]; |
end |
end |
|
// Burst terminate |
if (Burst_term == 1'b1) begin |
// Terminate a Write Immediately |
if (Data_in_enable == 1'b1) begin |
Data_in_enable = 1'b0; |
end |
// Terminate a Read Depend on CAS Latency |
if (Cas_latency_3 == 1'b1) begin |
Command[2] = `SDRAM_BST; |
end else if (Cas_latency_2 == 1'b1) begin |
Command[1] = `SDRAM_BST; |
end |
if (Debug) $display ("at time %t BST : Burst Terminate",$time); |
end |
|
// Read, Write, Column Latch |
if (Read_enable == 1'b1 || Write_enable == 1'b1) begin |
// Check to see if bank is open (ACT) |
if ((Ba == 2'b00 && Pc_b0 == 1'b1) || (Ba == 2'b01 && Pc_b1 == 1'b1) || |
(Ba == 2'b10 && Pc_b2 == 1'b1) || (Ba == 2'b11 && Pc_b3 == 1'b1)) begin |
|
//->tb.test_control.error_detected; |
$display("at time %t ERROR: Cannot Read or Write - Bank %d is not Activated", $time, Ba); |
end |
// Activate to Read or Write |
if ((Ba == 2'b00) && ($time - RCD_chk0 < tRCD)) |
begin |
//->tb.test_control.error_detected; |
$display("at time %t ERROR: tRCD violation during Read or Write to Bank 0", $time); |
end |
|
if ((Ba == 2'b01) && ($time - RCD_chk1 < tRCD)) |
begin |
//->tb.test_control.error_detected; |
$display("at time %t ERROR: tRCD violation during Read or Write to Bank 1", $time); |
end |
if ((Ba == 2'b10) && ($time - RCD_chk2 < tRCD)) |
begin |
//->tb.test_control.error_detected; |
$display("at time %t ERROR: tRCD violation during Read or Write to Bank 2", $time); |
end |
if ((Ba == 2'b11) && ($time - RCD_chk3 < tRCD)) |
begin |
//->tb.test_control.error_detected; |
$display("at time %t ERROR: tRCD violation during Read or Write to Bank 3", $time); |
end |
// Read Command |
if (Read_enable == 1'b1) begin |
// CAS Latency pipeline |
if (Cas_latency_3 == 1'b1) begin |
if (Addr[10] == 1'b1) begin |
Command[2] = `READ_A; |
end else begin |
Command[2] = `READ; |
end |
Col_addr[2] = Addr; |
Bank_addr[2] = Ba; |
end else if (Cas_latency_2 == 1'b1) begin |
if (Addr[10] == 1'b1) begin |
Command[1] = `READ_A; |
end else begin |
Command[1] = `READ; |
end |
Col_addr[1] = Addr; |
Bank_addr[1] = Ba; |
end |
|
// Read interrupt Write (terminate Write immediately) |
if (Data_in_enable == 1'b1) begin |
Data_in_enable = 1'b0; |
end |
|
// Write Command |
end else if (Write_enable == 1'b1) begin |
if (Addr[10] == 1'b1) begin |
Command[0] = `WRITE_A; |
end else begin |
Command[0] = `SDRAM_WRITE; |
end |
Col_addr[0] = Addr; |
Bank_addr[0] = Ba; |
|
// Write interrupt Write (terminate Write immediately) |
if (Data_in_enable == 1'b1) begin |
Data_in_enable = 1'b0; |
end |
|
// Write interrupt Read (terminate Read immediately) |
if (Data_out_enable == 1'b1) begin |
Data_out_enable = 1'b0; |
end |
end |
|
// Interrupting a Write with Autoprecharge |
if (Auto_precharge[Bank] == 1'b1 && Write_precharge[Bank] == 1'b1) begin |
RW_interrupt_write[Bank] = 1'b1; |
if (Debug) $display ("at time %t NOTE : Read/Write Bank %d interrupt Write Bank %d with Autoprecharge", $time, Ba, Bank); |
end |
|
// Interrupting a Read with Autoprecharge |
if (Auto_precharge[Bank] == 1'b1 && Read_precharge[Bank] == 1'b1) begin |
RW_interrupt_read[Bank] = 1'b1; |
if (Debug) $display ("at time %t NOTE : Read/Write Bank %d interrupt Read Bank %d with Autoprecharge", $time, Ba, Bank); |
end |
|
// Read or Write with Auto Precharge |
if (Addr[10] == 1'b1) begin |
Auto_precharge[Ba] = 1'b1; |
Count_precharge[Ba] = 0; |
if (Read_enable == 1'b1) begin |
Read_precharge[Ba] = 1'b1; |
end else if (Write_enable == 1'b1) begin |
Write_precharge[Ba] = 1'b1; |
end |
end |
end |
|
// Read with Auto Precharge Calculation |
// The device start internal precharge: |
// 1. CAS Latency - 1 cycles before last burst |
// and 2. Meet minimum tRAS requirement |
// or 3. Interrupt by a Read or Write (with or without AutoPrecharge) |
if ((Auto_precharge[0] == 1'b1) && (Read_precharge[0] == 1'b1)) begin |
if ((($time - RAS_chk0 >= tRAS) && // Case 2 |
((Burst_length_1 == 1'b1 && Count_precharge[0] >= 1) || // Case 1 |
(Burst_length_2 == 1'b1 && Count_precharge[0] >= 2) || |
(Burst_length_4 == 1'b1 && Count_precharge[0] >= 4) || |
(Burst_length_8 == 1'b1 && Count_precharge[0] >= 8))) || |
(RW_interrupt_read[0] == 1'b1)) begin // Case 3 |
Pc_b0 = 1'b1; |
Act_b0 = 1'b0; |
RP_chk0 = $time; |
Auto_precharge[0] = 1'b0; |
Read_precharge[0] = 1'b0; |
RW_interrupt_read[0] = 1'b0; |
if (Debug) $display ("at time %t NOTE : Start Internal Auto Precharge for Bank 0", $time); |
end |
end |
if ((Auto_precharge[1] == 1'b1) && (Read_precharge[1] == 1'b1)) begin |
if ((($time - RAS_chk1 >= tRAS) && |
((Burst_length_1 == 1'b1 && Count_precharge[1] >= 1) || |
(Burst_length_2 == 1'b1 && Count_precharge[1] >= 2) || |
(Burst_length_4 == 1'b1 && Count_precharge[1] >= 4) || |
(Burst_length_8 == 1'b1 && Count_precharge[1] >= 8))) || |
(RW_interrupt_read[1] == 1'b1)) begin |
Pc_b1 = 1'b1; |
Act_b1 = 1'b0; |
RP_chk1 = $time; |
Auto_precharge[1] = 1'b0; |
Read_precharge[1] = 1'b0; |
RW_interrupt_read[1] = 1'b0; |
if (Debug) $display ("at time %t NOTE : Start Internal Auto Precharge for Bank 1", $time); |
end |
end |
if ((Auto_precharge[2] == 1'b1) && (Read_precharge[2] == 1'b1)) begin |
if ((($time - RAS_chk2 >= tRAS) && |
((Burst_length_1 == 1'b1 && Count_precharge[2] >= 1) || |
(Burst_length_2 == 1'b1 && Count_precharge[2] >= 2) || |
(Burst_length_4 == 1'b1 && Count_precharge[2] >= 4) || |
(Burst_length_8 == 1'b1 && Count_precharge[2] >= 8))) || |
(RW_interrupt_read[2] == 1'b1)) begin |
Pc_b2 = 1'b1; |
Act_b2 = 1'b0; |
RP_chk2 = $time; |
Auto_precharge[2] = 1'b0; |
Read_precharge[2] = 1'b0; |
RW_interrupt_read[2] = 1'b0; |
if (Debug) $display ("at time %t NOTE : Start Internal Auto Precharge for Bank 2", $time); |
end |
end |
if ((Auto_precharge[3] == 1'b1) && (Read_precharge[3] == 1'b1)) begin |
if ((($time - RAS_chk3 >= tRAS) && |
((Burst_length_1 == 1'b1 && Count_precharge[3] >= 1) || |
(Burst_length_2 == 1'b1 && Count_precharge[3] >= 2) || |
(Burst_length_4 == 1'b1 && Count_precharge[3] >= 4) || |
(Burst_length_8 == 1'b1 && Count_precharge[3] >= 8))) || |
(RW_interrupt_read[3] == 1'b1)) begin |
Pc_b3 = 1'b1; |
Act_b3 = 1'b0; |
RP_chk3 = $time; |
Auto_precharge[3] = 1'b0; |
Read_precharge[3] = 1'b0; |
RW_interrupt_read[3] = 1'b0; |
if (Debug) $display ("at time %t NOTE : Start Internal Auto Precharge for Bank 3", $time); |
end |
end |
|
// Internal Precharge or Bst |
if (Command[0] == `SDRAM_PRECH) begin // Precharge terminate a read with same bank or all banks |
if (Bank_precharge[0] == Bank || A10_precharge[0] == 1'b1) begin |
if (Data_out_enable == 1'b1) begin |
Data_out_enable = 1'b0; |
end |
end |
end else if (Command[0] == `SDRAM_BST) begin // BST terminate a read to current bank |
if (Data_out_enable == 1'b1) begin |
Data_out_enable = 1'b0; |
end |
end |
|
if (Data_out_enable == 1'b0) begin |
Dq_reg <= #tOH {data_bits{1'bz}}; |
end |
|
// Detect Read or Write command |
if (Command[0] == `READ || Command[0] == `READ_A) begin |
Bank = Bank_addr[0]; |
Col = Col_addr[0]; |
Col_brst = Col_addr[0]; |
if (Bank_addr[0] == 2'b00) begin |
Row = B0_row_addr; |
end else if (Bank_addr[0] == 2'b01) begin |
Row = B1_row_addr; |
end else if (Bank_addr[0] == 2'b10) begin |
Row = B2_row_addr; |
end else if (Bank_addr[0] == 2'b11) begin |
Row = B3_row_addr; |
end |
Burst_counter = 0; |
Data_in_enable = 1'b0; |
Data_out_enable = 1'b1; |
end else if (Command[0] == `SDRAM_WRITE || Command[0] == `WRITE_A) begin |
Bank = Bank_addr[0]; |
Col = Col_addr[0]; |
Col_brst = Col_addr[0]; |
if (Bank_addr[0] == 2'b00) begin |
Row = B0_row_addr; |
end else if (Bank_addr[0] == 2'b01) begin |
Row = B1_row_addr; |
end else if (Bank_addr[0] == 2'b10) begin |
Row = B2_row_addr; |
end else if (Bank_addr[0] == 2'b11) begin |
Row = B3_row_addr; |
end |
Burst_counter = 0; |
Data_in_enable = 1'b1; |
Data_out_enable = 1'b0; |
end |
|
// DQ buffer (Driver/Receiver) |
if (Data_in_enable == 1'b1) begin // Writing Data to Memory |
// Array buffer |
if (Bank == 2'b00) Dq_dqm [15 : 0] = Bank0 [{Row, Col}]; |
if (Bank == 2'b01) Dq_dqm [15 : 0] = Bank1 [{Row, Col}]; |
if (Bank == 2'b10) Dq_dqm [15 : 0] = Bank2 [{Row, Col}]; |
if (Bank == 2'b11) Dq_dqm [15 : 0] = Bank3 [{Row, Col}]; |
// Dqm operation |
if (Dqm[0] == 1'b0) Dq_dqm [ 7 : 0] = Dq [ 7 : 0]; |
// Write to memory |
if (Bank == 2'b00) Bank0 [{Row, Col}] = Dq_dqm [15 : 0]; |
if (Bank == 2'b01) Bank1 [{Row, Col}] = Dq_dqm [15 : 0]; |
if (Bank == 2'b10) Bank2 [{Row, Col}] = Dq_dqm [15 : 0]; |
if (Bank == 2'b11) Bank3 [{Row, Col}] = Dq_dqm [15 : 0]; |
// Output result |
if (Dqm == 1'b1) begin |
if (Debug) $display("at time %t WRITE: Bank = %d Row = %d, Col = %d, Data = Hi-Z due to DQM", $time, Bank, Row, Col); |
end else begin |
if (Debug) $display("at time %t WRITE: Bank = %d Row = %d, Col = %d, Data = %h, Dqm = %b", $time, Bank, Row, Col, Dq_dqm, Dqm); |
// Record tWR time and reset counter |
WR_chk [Bank] = $time; |
WR_counter [Bank] = 0; |
end |
// Advance burst counter subroutine |
#tHZ Burst; |
end else if (Data_out_enable == 1'b1) begin // Reading Data from Memory |
// Array buffer |
if (Bank == 2'b00) Dq_dqm [15 : 0] = Bank0 [{Row, Col}]; |
if (Bank == 2'b01) Dq_dqm [15 : 0] = Bank1 [{Row, Col}]; |
if (Bank == 2'b10) Dq_dqm [15 : 0] = Bank2 [{Row, Col}]; |
if (Bank == 2'b11) Dq_dqm [15 : 0] = Bank3 [{Row, Col}]; |
// Dqm operation |
if (Dqm_reg0[0] == 1'b1) Dq_dqm [ 7 : 0] = 8'bz; |
// Display result |
Dq_reg [15 : 0] = #tAC Dq_dqm [15 : 0]; |
if (Dqm_reg0 == 1'b1) begin |
if (Debug) $display("at time %t READ : Bank = %d Row = %d, Col = %d, Data = Hi-Z due to DQM", $time, Bank, Row, Col); |
end else begin |
if (Debug) $display("at time %t READ : Bank = %d Row = %d, Col = %d, Data = %h, Dqm = %b", $time, Bank, Row, Col, Dq_reg, Dqm_reg0); |
end |
// Advance burst counter subroutine |
Burst; |
end |
end |
|
// Write with Auto Precharge Calculation |
// The device start internal precharge: |
// 1. tWR Clock after last burst |
// and 2. Meet minimum tRAS requirement |
// or 3. Interrupt by a Read or Write (with or without AutoPrecharge) |
always @ (WR_counter[0]) begin |
if ((Auto_precharge[0] == 1'b1) && (Write_precharge[0] == 1'b1)) begin |
if ((($time - RAS_chk0 >= tRAS) && // Case 2 |
(((Burst_length_1 == 1'b1 || Write_burst_mode == 1'b1) && Count_precharge [0] >= 1) || // Case 1 |
(Burst_length_2 == 1'b1 && Count_precharge [0] >= 2) || |
(Burst_length_4 == 1'b1 && Count_precharge [0] >= 4) || |
(Burst_length_8 == 1'b1 && Count_precharge [0] >= 8))) || |
(RW_interrupt_write[0] == 1'b1 && WR_counter[0] >= 2)) begin // Case 3 (stop count when interrupt) |
Auto_precharge[0] = 1'b0; |
Write_precharge[0] = 1'b0; |
RW_interrupt_write[0] = 1'b0; |
#tWRa; // Wait for tWR |
Pc_b0 = 1'b1; |
Act_b0 = 1'b0; |
RP_chk0 = $time; |
if (Debug) $display ("at time %t NOTE : Start Internal Auto Precharge for Bank 0", $time); |
end |
end |
end |
always @ (WR_counter[1]) begin |
if ((Auto_precharge[1] == 1'b1) && (Write_precharge[1] == 1'b1)) begin |
if ((($time - RAS_chk1 >= tRAS) && |
(((Burst_length_1 == 1'b1 || Write_burst_mode == 1'b1) && Count_precharge [1] >= 1) || |
(Burst_length_2 == 1'b1 && Count_precharge [1] >= 2) || |
(Burst_length_4 == 1'b1 && Count_precharge [1] >= 4) || |
(Burst_length_8 == 1'b1 && Count_precharge [1] >= 8))) || |
(RW_interrupt_write[1] == 1'b1 && WR_counter[1] >= 2)) begin |
Auto_precharge[1] = 1'b0; |
Write_precharge[1] = 1'b0; |
RW_interrupt_write[1] = 1'b0; |
#tWRa; // Wait for tWR |
Pc_b1 = 1'b1; |
Act_b1 = 1'b0; |
RP_chk1 = $time; |
if (Debug) $display ("at time %t NOTE : Start Internal Auto Precharge for Bank 1", $time); |
end |
end |
end |
always @ (WR_counter[2]) begin |
if ((Auto_precharge[2] == 1'b1) && (Write_precharge[2] == 1'b1)) begin |
if ((($time - RAS_chk2 >= tRAS) && |
(((Burst_length_1 == 1'b1 || Write_burst_mode == 1'b1) && Count_precharge [2] >= 1) || |
(Burst_length_2 == 1'b1 && Count_precharge [2] >= 2) || |
(Burst_length_4 == 1'b1 && Count_precharge [2] >= 4) || |
(Burst_length_8 == 1'b1 && Count_precharge [2] >= 8))) || |
(RW_interrupt_write[2] == 1'b1 && WR_counter[2] >= 2)) begin |
Auto_precharge[2] = 1'b0; |
Write_precharge[2] = 1'b0; |
RW_interrupt_write[2] = 1'b0; |
#tWRa; // Wait for tWR |
Pc_b2 = 1'b1; |
Act_b2 = 1'b0; |
RP_chk2 = $time; |
if (Debug) $display ("at time %t NOTE : Start Internal Auto Precharge for Bank 2", $time); |
end |
end |
end |
always @ (WR_counter[3]) begin |
if ((Auto_precharge[3] == 1'b1) && (Write_precharge[3] == 1'b1)) begin |
if ((($time - RAS_chk3 >= tRAS) && |
(((Burst_length_1 == 1'b1 || Write_burst_mode == 1'b1) && Count_precharge [3] >= 1) || |
(Burst_length_2 == 1'b1 && Count_precharge [3] >= 2) || |
(Burst_length_4 == 1'b1 && Count_precharge [3] >= 4) || |
(Burst_length_8 == 1'b1 && Count_precharge [3] >= 8))) || |
(RW_interrupt_write[3] == 1'b1 && WR_counter[3] >= 2)) begin |
Auto_precharge[3] = 1'b0; |
Write_precharge[3] = 1'b0; |
RW_interrupt_write[3] = 1'b0; |
#tWRa; // Wait for tWR |
Pc_b3 = 1'b1; |
Act_b3 = 1'b0; |
RP_chk3 = $time; |
if (Debug) $display ("at time %t NOTE : Start Internal Auto Precharge for Bank 3", $time); |
end |
end |
end |
|
task Burst; |
begin |
// Advance Burst Counter |
Burst_counter = Burst_counter + 1; |
|
// Burst Type |
if (Mode_reg[3] == 1'b0) begin // Sequential Burst |
Col_temp = Col + 1; |
end else if (Mode_reg[3] == 1'b1) begin // Interleaved Burst |
Col_temp[2] = Burst_counter[2] ^ Col_brst[2]; |
Col_temp[1] = Burst_counter[1] ^ Col_brst[1]; |
Col_temp[0] = Burst_counter[0] ^ Col_brst[0]; |
end |
|
// Burst Length |
if (Burst_length_2) begin // Burst Length = 2 |
Col [0] = Col_temp [0]; |
end else if (Burst_length_4) begin // Burst Length = 4 |
Col [1 : 0] = Col_temp [1 : 0]; |
end else if (Burst_length_8) begin // Burst Length = 8 |
Col [2 : 0] = Col_temp [2 : 0]; |
end else begin // Burst Length = FULL |
Col = Col_temp; |
end |
|
// Burst Read Single Write |
if (Write_burst_mode == 1'b1) begin |
Data_in_enable = 1'b0; |
end |
|
// Data Counter |
if (Burst_length_1 == 1'b1) begin |
if (Burst_counter >= 1) begin |
Data_in_enable = 1'b0; |
Data_out_enable = 1'b0; |
end |
end else if (Burst_length_2 == 1'b1) begin |
if (Burst_counter >= 2) begin |
Data_in_enable = 1'b0; |
Data_out_enable = 1'b0; |
end |
end else if (Burst_length_4 == 1'b1) begin |
if (Burst_counter >= 4) begin |
Data_in_enable = 1'b0; |
Data_out_enable = 1'b0; |
end |
end else if (Burst_length_8 == 1'b1) begin |
if (Burst_counter >= 8) begin |
Data_in_enable = 1'b0; |
Data_out_enable = 1'b0; |
end |
end |
end |
endtask |
|
// Timing Parameters for -75 (PC133) and CAS Latency = 2 |
specify |
specparam |
tAH = 0.8, // Addr, Ba Hold Time |
tAS = 1.5, // Addr, Ba Setup Time |
tCH = 2.5, // Clock High-Level Width |
tCL = 2.5, // Clock Low-Level Width |
tCK = 10, // Clock Cycle Time |
tDH = 0.8, // Data-in Hold Time |
tDS = 1.5, // Data-in Setup Time |
tCKH = 0.8, // CKE Hold Time |
tCKS = 1.5, // CKE Setup Time |
tCMH = 0.8, // CS#, RAS#, CAS#, WE#, DQM# Hold Time |
tCMS = 1.5; // CS#, RAS#, CAS#, WE#, DQM# Setup Time |
$width (posedge Clk, tCH); |
$width (negedge Clk, tCL); |
$period (negedge Clk, tCK); |
$period (posedge Clk, tCK); |
$setuphold(posedge Clk, Cke, tCKS, tCKH); |
$setuphold(posedge Clk, Cs_n, tCMS, tCMH); |
$setuphold(posedge Clk, Cas_n, tCMS, tCMH); |
$setuphold(posedge Clk, Ras_n, tCMS, tCMH); |
$setuphold(posedge Clk, We_n, tCMS, tCMH); |
$setuphold(posedge Clk, Addr, tAS, tAH); |
$setuphold(posedge Clk, Ba, tAS, tAH); |
$setuphold(posedge Clk, Dqm, tCMS, tCMH); |
$setuphold(posedge Dq_chk, Dq, tDS, tDH); |
endspecify |
|
endmodule |
|
yifive/trunk/caravel_yifive/verilog/dv/model/mt48lc8m8a2.v
Property changes :
Added: svn:executable
## -0,0 +1 ##
+*
\ No newline at end of property
Index: yifive/trunk/caravel_yifive/verilog/dv/risc_boot/Makefile
===================================================================
--- yifive/trunk/caravel_yifive/verilog/dv/risc_boot/Makefile (nonexistent)
+++ yifive/trunk/caravel_yifive/verilog/dv/risc_boot/Makefile (revision 22)
@@ -0,0 +1,84 @@
+# SPDX-FileCopyrightText: 2020 Efabless Corporation
+#
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+#
+# SPDX-License-Identifier: Apache-2.0
+
+## Caravel Pointers
+CARAVEL_ROOT ?= ../../../caravel
+CARAVEL_PATH ?= $(CARAVEL_ROOT)
+CARAVEL_FIRMWARE_PATH = $(CARAVEL_PATH)/verilog/dv/caravel
+CARAVEL_VERILOG_PATH = $(CARAVEL_PATH)/verilog
+CARAVEL_RTL_PATH = $(CARAVEL_VERILOG_PATH)/rtl
+CARAVEL_BEHAVIOURAL_MODELS = $(CARAVEL_VERILOG_PATH)/dv/caravel
+
+## User Project Pointers
+UPRJ_VERILOG_PATH ?= ../../../verilog
+UPRJ_RTL_PATH = $(UPRJ_VERILOG_PATH)/rtl
+UPRJ_BEHAVIOURAL_MODELS = ../model
+UPRJ_INCLUDE_PATH1 = $(UPRJ_RTL_PATH)/syntacore/scr1/src/includes
+UPRJ_INCLUDE_PATH2 = $(UPRJ_RTL_PATH)/sdram_ctrl/src/defs
+UPRJ_INCLUDE_PATH2 = $(UPRJ_RTL_PATH)/sdram_ctrl/src/defs
+
+## RISCV GCC
+GCC_PATH?=/ef/apps/bin
+GCC_PREFIX?=riscv32-unknown-elf
+PDK_PATH?=/ef/tech/SW/sky130A
+
+## Simulation mode: RTL/GL
+SIM?=RTL
+
+.SUFFIXES:
+
+PATTERN = risc_boot
+
+all: ${PATTERN:=.vcd}
+
+hex: ${PATTERN:=.hex}
+
+vvp: ${PATTERN:=.vvp}
+
+%.vvp: %_tb.v %.hex
+ifeq ($(SIM),RTL)
+ iverilog -g2005-sv -DFUNCTIONAL -DSIM -I $(PDK_PATH) \
+ -I $(CARAVEL_BEHAVIOURAL_MODELS) -I $(CARAVEL_RTL_PATH) \
+ -I $(UPRJ_BEHAVIOURAL_MODELS) -I $(UPRJ_RTL_PATH) \
+ -I $(UPRJ_INCLUDE_PATH1) -I $(UPRJ_INCLUDE_PATH2) \
+ $< -o $@
+else
+ iverilog -DFUNCTIONAL -DSIM -DGL -I $(PDK_PATH) \
+ -I $(CARAVEL_BEHAVIOURAL_MODELS) -I $(CARAVEL_RTL_PATH) -I $(CARAVEL_VERILOG_PATH) \
+ -I $(UPRJ_BEHAVIOURAL_MODELS) -I$(UPRJ_RTL_PATH) -I $(UPRJ_VERILOG_PATH) \
+ $< -o $@
+endif
+
+%.vcd: %.vvp
+ vvp $<
+
+%.elf: %.c $(CARAVEL_FIRMWARE_PATH)/sections.lds $(CARAVEL_FIRMWARE_PATH)/start.s
+ ${GCC_PATH}/${GCC_PREFIX}-gcc -I $(CARAVEL_PATH) -march=rv32imc -mabi=ilp32 -Wl,-Bstatic,-T,$(CARAVEL_FIRMWARE_PATH)/sections.lds,--strip-debug -ffreestanding -nostdlib -o $@ $(CARAVEL_FIRMWARE_PATH)/start.s $<
+
+%.hex: %.elf
+ ${GCC_PATH}/${GCC_PREFIX}-objcopy -O verilog $< $@
+ # to fix flash base address
+ sed -i 's/@10000000/@00000000/g' $@
+
+%.bin: %.elf
+ ${GCC_PATH}/${GCC_PREFIX}-objcopy -O binary $< /dev/stdout | tail -c +1048577 > $@
+
+# ---- Clean ----
+
+clean:
+ rm -f *.elf *.hex *.bin *.vvp *.vcd *.log
+
+.PHONY: clean hex all
Index: yifive/trunk/caravel_yifive/verilog/dv/risc_boot/risc_boot.c
===================================================================
--- yifive/trunk/caravel_yifive/verilog/dv/risc_boot/risc_boot.c (nonexistent)
+++ yifive/trunk/caravel_yifive/verilog/dv/risc_boot/risc_boot.c (revision 22)
@@ -0,0 +1,213 @@
+/*
+ * SPDX-FileCopyrightText: 2020 Efabless Corporation
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * SPDX-License-Identifier: Apache-2.0
+ */
+
+// This include is relative to $CARAVEL_PATH (see Makefile)
+#include "verilog/dv/caravel/defs.h"
+#include "verilog/dv/caravel/stub.c"
+
+// User Project Slaves (0x3000_0000)
+#define reg_mprj_slave (*(volatile uint32_t*)0x30000000)
+
+#define reg_mprj_globl_reg0 (*(volatile uint32_t*)0x30000000)
+#define reg_mprj_globl_reg1 (*(volatile uint32_t*)0x30000004)
+#define reg_mprj_globl_reg2 (*(volatile uint32_t*)0x30000008)
+#define reg_mprj_globl_reg3 (*(volatile uint32_t*)0x3000000C)
+#define reg_mprj_globl_reg4 (*(volatile uint32_t*)0x30000010)
+#define reg_mprj_globl_reg5 (*(volatile uint32_t*)0x30000014)
+#define reg_mprj_globl_reg6 (*(volatile uint32_t*)0x30000018)
+#define reg_mprj_globl_reg7 (*(volatile uint32_t*)0x3000001C)
+#define reg_mprj_globl_reg8 (*(volatile uint32_t*)0x30000020)
+#define reg_mprj_globl_reg9 (*(volatile uint32_t*)0x30000024)
+#define reg_mprj_globl_reg10 (*(volatile uint32_t*)0x30000028)
+#define reg_mprj_globl_reg11 (*(volatile uint32_t*)0x3000002C)
+#define reg_mprj_globl_reg12 (*(volatile uint32_t*)0x30000030)
+#define reg_mprj_globl_reg13 (*(volatile uint32_t*)0x30000034)
+#define reg_mprj_globl_reg14 (*(volatile uint32_t*)0x30000038)
+#define reg_mprj_globl_reg15 (*(volatile uint32_t*)0x3000003C)
+
+
+#define GPIO_MODE_USER_STD_BIDIRECTIONAL_PULLUP 0x1C00
+
+#define SC_SIM_OUTPORT (0xf0000000)
+
+/*
+ RiscV Hello World test.
+ - Wake up the Risc V
+ - Boot from SPI Flash
+ - Riscv Write Hello World to SDRAM,
+ - External Wishbone read back validation the data
+*/
+int i = 0;
+int clk = 0;
+
+void main()
+{
+
+ int bFail = 0;
+ /*
+ IO Control Registers
+ | DM | VTRIP | SLOW | AN_POL | AN_SEL | AN_EN | MOD_SEL | INP_DIS | HOLDH | OEB_N | MGMT_EN |
+ | 3-bits | 1-bit | 1-bit | 1-bit | 1-bit | 1-bit | 1-bit | 1-bit | 1-bit | 1-bit | 1-bit |
+ Output: 0000_0110_0000_1110 (0x1808) = GPIO_MODE_USER_STD_OUTPUT
+ | DM | VTRIP | SLOW | AN_POL | AN_SEL | AN_EN | MOD_SEL | INP_DIS | HOLDH | OEB_N | MGMT_EN |
+ | 110 | 0 | 0 | 0 | 0 | 0 | 0 | 1 | 0 | 0 | 0 |
+
+
+ Input: 0000_0001_0000_1111 (0x0402) = GPIO_MODE_USER_STD_INPUT_NOPULL
+ | DM | VTRIP | SLOW | AN_POL | AN_SEL | AN_EN | MOD_SEL | INP_DIS | HOLDH | OEB_N | MGMT_EN |
+ | 001 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 1 | 0 |
+
+ Input: 0000_0001_0000_1111 (0x1800) = GPIO_MODE_USER_STD_BIDIRECTIONAL
+ | DM | VTRIP | SLOW | AN_POL | AN_SEL | AN_EN | MOD_SEL | INP_DIS | HOLDH | OEB_N | MGMT_EN |
+ | 110 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 |
+ */
+
+ /* Set up the housekeeping SPI to be connected internally so */
+ /* that external pin changes don't affect it. */
+
+ reg_spimaster_config = 0xa002; // Enable, prescaler = 2,
+ // connect to housekeeping SPI
+
+ // Connect the housekeeping SPI to the SPI master
+ // so that the CSB line is not left floating. This allows
+ // all of the GPIO pins to be used for user functions.
+ reg_mprj_io_31 = GPIO_MODE_MGMT_STD_OUTPUT;
+ reg_mprj_io_30 = GPIO_MODE_MGMT_STD_OUTPUT;
+ reg_mprj_io_29 = GPIO_MODE_MGMT_STD_OUTPUT;
+ reg_mprj_io_28 = GPIO_MODE_MGMT_STD_OUTPUT;
+ reg_mprj_io_27 = GPIO_MODE_MGMT_STD_OUTPUT;
+ reg_mprj_io_26 = GPIO_MODE_MGMT_STD_OUTPUT;
+ reg_mprj_io_25 = GPIO_MODE_MGMT_STD_OUTPUT;
+ reg_mprj_io_24 = GPIO_MODE_MGMT_STD_OUTPUT;
+ reg_mprj_io_23 = GPIO_MODE_MGMT_STD_OUTPUT;
+ reg_mprj_io_22 = GPIO_MODE_MGMT_STD_OUTPUT;
+ reg_mprj_io_21 = GPIO_MODE_MGMT_STD_OUTPUT;
+ reg_mprj_io_20 = GPIO_MODE_MGMT_STD_OUTPUT;
+ reg_mprj_io_19 = GPIO_MODE_MGMT_STD_OUTPUT;
+ reg_mprj_io_18 = GPIO_MODE_MGMT_STD_OUTPUT;
+ reg_mprj_io_17 = GPIO_MODE_MGMT_STD_OUTPUT;
+ reg_mprj_io_16 = GPIO_MODE_MGMT_STD_OUTPUT;
+
+
+ /* Apply configuration */
+ reg_mprj_xfer = 1;
+ while (reg_mprj_xfer == 1);
+
+ reg_la2_oenb = reg_la2_iena = 0xFFFFFFFF; // [95:64]
+
+ // Flag start of the test
+ reg_mprj_datal = 0xAB600000;
+
+ //-----------------------------------------------------
+ // Start of User Functionality and take over the GPIO Pins
+ // ------------------------------------------------------
+ // User block decide on the GPIO function
+ reg_mprj_io_37 = GPIO_MODE_USER_STD_BIDIRECTIONAL_PULLUP;
+ reg_mprj_io_36 = GPIO_MODE_USER_STD_BIDIRECTIONAL_PULLUP;
+ reg_mprj_io_35 = GPIO_MODE_USER_STD_BIDIRECTIONAL_PULLUP;
+ reg_mprj_io_34 = GPIO_MODE_USER_STD_BIDIRECTIONAL_PULLUP;
+ reg_mprj_io_33 = GPIO_MODE_USER_STD_BIDIRECTIONAL_PULLUP;
+ reg_mprj_io_32 = GPIO_MODE_USER_STD_BIDIRECTIONAL_PULLUP;
+ reg_mprj_io_31 = GPIO_MODE_USER_STD_BIDIRECTIONAL_PULLUP;
+ reg_mprj_io_30 = GPIO_MODE_USER_STD_BIDIRECTIONAL_PULLUP;
+ reg_mprj_io_29 = GPIO_MODE_USER_STD_BIDIRECTIONAL_PULLUP;
+ reg_mprj_io_28 = GPIO_MODE_USER_STD_BIDIRECTIONAL_PULLUP;
+ reg_mprj_io_27 = GPIO_MODE_USER_STD_BIDIRECTIONAL_PULLUP;
+ reg_mprj_io_26 = GPIO_MODE_USER_STD_BIDIRECTIONAL_PULLUP;
+ reg_mprj_io_25 = GPIO_MODE_USER_STD_BIDIRECTIONAL_PULLUP;
+ reg_mprj_io_24 = GPIO_MODE_USER_STD_BIDIRECTIONAL_PULLUP;
+ reg_mprj_io_23 = GPIO_MODE_USER_STD_BIDIRECTIONAL_PULLUP;
+ reg_mprj_io_22 = GPIO_MODE_USER_STD_BIDIRECTIONAL_PULLUP;
+ reg_mprj_io_21 = GPIO_MODE_USER_STD_BIDIRECTIONAL_PULLUP;
+ reg_mprj_io_20 = GPIO_MODE_USER_STD_BIDIRECTIONAL_PULLUP;
+ reg_mprj_io_19 = GPIO_MODE_USER_STD_BIDIRECTIONAL_PULLUP;
+ reg_mprj_io_18 = GPIO_MODE_USER_STD_BIDIRECTIONAL_PULLUP;
+ reg_mprj_io_17 = GPIO_MODE_USER_STD_BIDIRECTIONAL_PULLUP;
+ reg_mprj_io_16 = GPIO_MODE_USER_STD_BIDIRECTIONAL_PULLUP;
+ reg_mprj_io_15 = GPIO_MODE_USER_STD_BIDIRECTIONAL_PULLUP;
+ reg_mprj_io_14 = GPIO_MODE_USER_STD_BIDIRECTIONAL_PULLUP;
+ reg_mprj_io_13 = GPIO_MODE_USER_STD_BIDIRECTIONAL_PULLUP;
+ reg_mprj_io_12 = GPIO_MODE_USER_STD_BIDIRECTIONAL_PULLUP;
+ reg_mprj_io_11 = GPIO_MODE_USER_STD_BIDIRECTIONAL_PULLUP;
+ reg_mprj_io_10 = GPIO_MODE_USER_STD_BIDIRECTIONAL_PULLUP;
+ reg_mprj_io_9 = GPIO_MODE_USER_STD_BIDIRECTIONAL_PULLUP;
+ reg_mprj_io_8 = GPIO_MODE_USER_STD_BIDIRECTIONAL_PULLUP;
+ reg_mprj_io_7 = GPIO_MODE_USER_STD_BIDIRECTIONAL_PULLUP;
+ reg_mprj_io_6 = GPIO_MODE_USER_STD_BIDIRECTIONAL_PULLUP;
+ reg_mprj_io_5 = GPIO_MODE_USER_STD_BIDIRECTIONAL_PULLUP;
+ reg_mprj_io_4 = GPIO_MODE_USER_STD_BIDIRECTIONAL_PULLUP;
+ reg_mprj_io_3 = GPIO_MODE_USER_STD_BIDIRECTIONAL_PULLUP;
+ reg_mprj_io_2 = GPIO_MODE_USER_STD_BIDIRECTIONAL_PULLUP;
+ reg_mprj_io_1 = GPIO_MODE_USER_STD_BIDIRECTIONAL_PULLUP;
+ reg_mprj_io_0 = GPIO_MODE_USER_STD_BIDIRECTIONAL_PULLUP;
+
+ /* Apply configuration */
+ reg_mprj_xfer = 1;
+ while (reg_mprj_xfer == 1);
+ // SDRAM Config-2
+ reg_mprj_globl_reg5 = 0x100019E;
+
+
+ // SDRAM Config-1
+ reg_mprj_globl_reg4 = 0x2F172242;
+
+ // Wake Up CPU Core
+ reg_mprj_globl_reg0 = 0x07;
+
+ // Add some delay for user core to boot
+ for(i = 0; i < 40; i ++);
+ for(i = 0; i < 40; i ++);
+
+ if(reg_mprj_globl_reg6 != 0x11223344) bFail = 1;
+ if(reg_mprj_globl_reg7 != 0x22334455) bFail = 1;
+ if(reg_mprj_globl_reg8 != 0x33445566) bFail = 1;
+ if(reg_mprj_globl_reg9 != 0x44556677) bFail = 1;
+ if(reg_mprj_globl_reg10 != 0x55667788) bFail = 1;
+ if(reg_mprj_globl_reg11 != 0x66778899) bFail = 1;
+
+
+ if(bFail == 0) {
+ reg_mprj_datal = 0xAB610000;
+ } else {
+ reg_mprj_datal = 0xAB600000;
+ }
+
+ // Connect the housekeeping SPI to the SPI master
+ // so that the CSB line is not left floating. This allows
+ // all of the GPIO pins to be used for user functions.
+ reg_mprj_io_31 = GPIO_MODE_MGMT_STD_OUTPUT;
+ reg_mprj_io_30 = GPIO_MODE_MGMT_STD_OUTPUT;
+ reg_mprj_io_29 = GPIO_MODE_MGMT_STD_OUTPUT;
+ reg_mprj_io_28 = GPIO_MODE_MGMT_STD_OUTPUT;
+ reg_mprj_io_27 = GPIO_MODE_MGMT_STD_OUTPUT;
+ reg_mprj_io_26 = GPIO_MODE_MGMT_STD_OUTPUT;
+ reg_mprj_io_25 = GPIO_MODE_MGMT_STD_OUTPUT;
+ reg_mprj_io_24 = GPIO_MODE_MGMT_STD_OUTPUT;
+ reg_mprj_io_23 = GPIO_MODE_MGMT_STD_OUTPUT;
+ reg_mprj_io_22 = GPIO_MODE_MGMT_STD_OUTPUT;
+ reg_mprj_io_21 = GPIO_MODE_MGMT_STD_OUTPUT;
+ reg_mprj_io_20 = GPIO_MODE_MGMT_STD_OUTPUT;
+ reg_mprj_io_19 = GPIO_MODE_MGMT_STD_OUTPUT;
+ reg_mprj_io_18 = GPIO_MODE_MGMT_STD_OUTPUT;
+ reg_mprj_io_17 = GPIO_MODE_MGMT_STD_OUTPUT;
+ reg_mprj_io_16 = GPIO_MODE_MGMT_STD_OUTPUT;
+
+
+ /* Apply configuration */
+ reg_mprj_xfer = 1;
+ while (reg_mprj_xfer == 1);
+}
Index: yifive/trunk/caravel_yifive/verilog/dv/risc_boot/risc_boot_tb.v
===================================================================
--- yifive/trunk/caravel_yifive/verilog/dv/risc_boot/risc_boot_tb.v (nonexistent)
+++ yifive/trunk/caravel_yifive/verilog/dv/risc_boot/risc_boot_tb.v (revision 22)
@@ -0,0 +1,303 @@
+//////////////////////////////////////////////////////////////////////
+//// ////
+//// User Risc Core Boot Validation ////
+//// ////
+//// This file is part of the YIFive cores project ////
+//// http://www.opencores.org/cores/yifive/ ////
+//// ////
+//// Description ////
+//// 1. User Risc core is booted using compiled code of ////
+//// user_risc_boot.hex ////
+//// 2. User Risc core uses Serial Flash and SDRAM to boot ////
+//// 3. After successful boot, Risc core will write signature////
+//// in to user register from 0x3000_0018 to 0x3000_002C ////
+//// 4. Through the External Wishbone Interface we read back ////
+//// and validate the user register to declared pass fail ////
+//// ////
+//// To Do: ////
+//// nothing ////
+//// ////
+//// Author(s): ////
+//// - Dinesh Annayya, dinesha@opencores.org ////
+//// ////
+//// Revision : ////
+//// 0.1 - 12th June 2021, Dinesh A ////
+//// ////
+//////////////////////////////////////////////////////////////////////
+//// ////
+//// Copyright (C) 2000 Authors and OPENCORES.ORG ////
+//// ////
+//// 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 ////
+//// ////
+//////////////////////////////////////////////////////////////////////
+
+`default_nettype none
+
+`timescale 1 ns / 1 ps
+
+`include "uprj_netlists.v"
+`include "caravel_netlists.v"
+`include "spiflash.v"
+`include "mt48lc8m8a2.v"
+
+module risc_boot_tb;
+ reg clock;
+ reg RSTB;
+ reg CSB;
+ reg power1, power2;
+ reg power3, power4;
+
+ wire gpio;
+ wire [37:0] mprj_io;
+ wire [7:0] mprj_io_0;
+ wire [15:0] checkbits;
+
+ assign checkbits = mprj_io[31:16];
+
+ assign mprj_io[3] = (CSB == 1'b1) ? 1'b1 : 1'bz;
+
+ // External clock is used by default. Make this artificially fast for the
+ // simulation. Normally this would be a slow clock and the digital PLL
+ // would be the fast clock.
+
+ always #12.5 clock <= (clock === 1'b0);
+
+ initial begin
+ clock = 0;
+ end
+
+ `ifdef WFDUMP
+ initial
+ begin
+ $dumpfile("simx.vcd");
+ $dumpvars(1,risc_boot_tb);
+ //$dumpvars(2,risc_boot_tb.uut);
+ $dumpvars(1,risc_boot_tb.uut.mprj.u_core);
+ //$dumpvars(0,risc_boot_tb.u_user_spiflash);
+ $display("Waveform Dump started");
+ end
+ `endif
+
+ initial begin
+
+ // Repeat cycles of 1000 clock edges as needed to complete testbench
+ repeat (600) begin
+ repeat (1000) @(posedge clock);
+ // $display("+1000 cycles");
+ end
+ $display("%c[1;31m",27);
+ `ifdef GL
+ $display ("Monitor: Timeout, Test user Risc Boot (GL) Failed");
+ `else
+ $display ("Monitor: Timeout, Test user Risc Boot (RTL) Failed");
+ `endif
+ $display("%c[0m",27);
+ $finish;
+ end
+
+ initial begin
+ wait(checkbits == 16'h AB60);
+ $display("Monitor: Test User Risc Boot Started");
+ wait(checkbits == 16'h AB61);
+ $display("#############################################");
+ `ifdef GL
+ $display("Monitor: Test User Risc Boot (GL) Passed");
+ `else
+ $display("Monitor: Test User Risc Boot (RTL) Passed");
+ `endif
+ $display("#############################################");
+ $finish;
+ end
+
+ initial begin
+ RSTB <= 1'b0;
+ CSB <= 1'b1; // Force CSB high
+ #2000;
+ RSTB <= 1'b1; // Release reset
+ #170000;
+ CSB = 1'b0; // CSB can be released
+ end
+
+ initial begin // Power-up sequence
+ power1 <= 1'b0;
+ power2 <= 1'b0;
+ power3 <= 1'b0;
+ power4 <= 1'b0;
+ #100;
+ power1 <= 1'b1;
+ #100;
+ power2 <= 1'b1;
+ #100;
+ power3 <= 1'b1;
+ #100;
+ power4 <= 1'b1;
+ end
+
+ //always @(mprj_io) begin
+ // #1 $display("MPRJ-IO state = %b ", mprj_io[7:0]);
+ //end
+
+ wire flash_csb;
+ wire flash_clk;
+ wire flash_io0;
+ wire flash_io1;
+
+ wire VDD3V3 = power1;
+ wire VDD1V8 = power2;
+ wire USER_VDD3V3 = power3;
+ wire USER_VDD1V8 = power4;
+ wire VSS = 1'b0;
+
+ caravel uut (
+ .vddio (VDD3V3),
+ .vssio (VSS),
+ .vdda (VDD3V3),
+ .vssa (VSS),
+ .vccd (VDD1V8),
+ .vssd (VSS),
+ .vdda1 (USER_VDD3V3),
+ .vdda2 (USER_VDD3V3),
+ .vssa1 (VSS),
+ .vssa2 (VSS),
+ .vccd1 (USER_VDD1V8),
+ .vccd2 (USER_VDD1V8),
+ .vssd1 (VSS),
+ .vssd2 (VSS),
+ .clock (clock),
+ .gpio (gpio),
+ .mprj_io (mprj_io),
+ .flash_csb(flash_csb),
+ .flash_clk(flash_clk),
+ .flash_io0(flash_io0),
+ .flash_io1(flash_io1),
+ .resetb (RSTB)
+ );
+
+ spiflash #(
+ .FILENAME("risc_boot.hex")
+ ) spiflash (
+ .csb(flash_csb),
+ .clk(flash_clk),
+ .io0(flash_io0),
+ .io1(flash_io1),
+ .io2(), // not used
+ .io3() // not used
+ );
+
+//-----------------------------------------
+// Connect Quad Flash to for usr Risc Core
+//-----------------------------------------
+
+ wire user_flash_clk = mprj_io[30];
+ wire user_flash_csb = mprj_io[31];
+ //tri user_flash_io0 = mprj_io[33];
+ //tri user_flash_io1 = mprj_io[34];
+ //tri user_flash_io2 = mprj_io[35];
+ //tri user_flash_io3 = mprj_io[36];
+
+ // Quard flash
+ spiflash #(
+ .FILENAME("user_risc_boot.hex")
+ ) u_user_spiflash (
+ .csb(user_flash_csb),
+ .clk(user_flash_clk),
+ .io0(mprj_io[32]),
+ .io1(mprj_io[33]),
+ .io2(mprj_io[34]),
+ .io3(mprj_io[35])
+ );
+
+
+//------------------------------------------------
+// Integrate the SDRAM 8 BIT Memory
+// -----------------------------------------------
+
+tri [7:0] Dq ; // SDRAM Read/Write Data Bus
+wire [0:0] sdr_dqm ; // SDRAM DATA Mask
+wire [1:0] sdr_ba ; // SDRAM Bank Select
+wire [12:0] sdr_addr ; // SDRAM ADRESS
+wire sdr_cs_n ; // chip select
+wire sdr_cke ; // clock gate
+wire sdr_ras_n ; // ras
+wire sdr_cas_n ; // cas
+wire sdr_we_n ; // write enable
+wire sdram_clk ;
+
+//assign Dq[7:0] = mprj_io [7:0];
+assign sdr_addr[12:0] = mprj_io [20:8] ;
+assign sdr_ba[1:0] = mprj_io [22:21] ;
+assign sdr_dqm[0] = mprj_io [23] ;
+assign sdr_we_n = mprj_io [24] ;
+assign sdr_cas_n = mprj_io [25] ;
+assign sdr_ras_n = mprj_io [26] ;
+assign sdr_cs_n = mprj_io [27] ;
+assign sdr_cke = mprj_io [28] ;
+assign sdram_clk = mprj_io [29] ;
+
+// to fix the sdram interface timing issue
+wire #(2.0) sdram_clk_d = sdram_clk;
+
+ // SDRAM 8bit
+mt48lc8m8a2 #(.data_bits(8)) u_sdram8 (
+ .Dq (mprj_io [7:0] ) ,
+ .Addr (sdr_addr[11:0] ),
+ .Ba (sdr_ba ),
+ .Clk (sdram_clk_d ),
+ .Cke (sdr_cke ),
+ .Cs_n (sdr_cs_n ),
+ .Ras_n (sdr_ras_n ),
+ .Cas_n (sdr_cas_n ),
+ .We_n (sdr_we_n ),
+ .Dqm (sdr_dqm )
+ );
+
+
+
+/**
+//-----------------------------------------------------------------------------
+// RISC IMEM amd DMEM Monitoring TASK
+//-----------------------------------------------------------------------------
+logic [`SCR1_DMEM_AWIDTH-1:0] core2imem_addr_o_r; // DMEM address
+logic [`SCR1_DMEM_AWIDTH-1:0] core2dmem_addr_o_r; // DMEM address
+logic core2dmem_cmd_o_r;
+
+`define RISC_CORE test_tb.uut.mprj.u_core.u_riscv_top.i_core_top
+
+always@(posedge `RISC_CORE.clk) begin
+ if(`RISC_CORE.imem2core_req_ack_i && `RISC_CORE.core2imem_req_o)
+ core2imem_addr_o_r <= `RISC_CORE.core2imem_addr_o;
+
+ if(`RISC_CORE.dmem2core_req_ack_i && `RISC_CORE.core2dmem_req_o) begin
+ core2dmem_addr_o_r <= `RISC_CORE.core2dmem_addr_o;
+ core2dmem_cmd_o_r <= `RISC_CORE.core2dmem_cmd_o;
+ end
+
+ if(`RISC_CORE.imem2core_resp_i !=0)
+ $display("RISCV-DEBUG => IMEM ADDRESS: %x Read Data : %x Resonse: %x", core2imem_addr_o_r,`RISC_CORE.imem2core_rdata_i,`RISC_CORE.imem2core_resp_i);
+ if((`RISC_CORE.dmem2core_resp_i !=0) && core2dmem_cmd_o_r)
+ $display("RISCV-DEBUG => DMEM ADDRESS: %x Write Data: %x Resonse: %x", core2dmem_addr_o_r,`RISC_CORE.core2dmem_wdata_o,`RISC_CORE.dmem2core_resp_i);
+ if((`RISC_CORE.dmem2core_resp_i !=0) && !core2dmem_cmd_o_r)
+ $display("RISCV-DEBUG => DMEM ADDRESS: %x READ Data : %x Resonse: %x", core2dmem_addr_o_r,`RISC_CORE.dmem2core_rdata_i,`RISC_CORE.dmem2core_resp_i);
+end
+*/
+endmodule
+`default_nettype wire
Index: yifive/trunk/caravel_yifive/verilog/dv/risc_boot/run_iverilog
===================================================================
--- yifive/trunk/caravel_yifive/verilog/dv/risc_boot/run_iverilog (nonexistent)
+++ yifive/trunk/caravel_yifive/verilog/dv/risc_boot/run_iverilog (revision 22)
@@ -0,0 +1,10 @@
+
+#add -DWFDUMP to enable waveform dump
+iverilog -g2005-sv -DFUNCTIONAL -DSIM -I $PDK_PATH \
+-I $CARAVEL_ROOT/verilog/dv/caravel -I $CARAVEL_ROOT/verilog/rtl \
+-I ../model -I ../../../verilog/rtl \
+-I ../../../verilog/rtl/syntacore/scr1/src/includes -I ../../../verilog/rtl/sdram_ctrl/src/defs \
+risc_boot_tb.v -o risc_boot.vvp
+
+vvp risc_boot.vvp
+rm risc_boot.vvp
yifive/trunk/caravel_yifive/verilog/dv/risc_boot/run_iverilog
Property changes :
Added: svn:executable
## -0,0 +1 ##
+*
\ No newline at end of property
Index: yifive/trunk/caravel_yifive/verilog/dv/risc_boot/user_risc_boot.hex
===================================================================
--- yifive/trunk/caravel_yifive/verilog/dv/risc_boot/user_risc_boot.hex (nonexistent)
+++ yifive/trunk/caravel_yifive/verilog/dv/risc_boot/user_risc_boot.hex (revision 22)
@@ -0,0 +1,79 @@
+@00000000
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 13 00 00 00 6F 00 00 00 FF FF FF FF
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+6F 00 E0 18 13 00 00 00 13 00 00 00 13 00 00 00
+13 00 00 00 13 00 00 00 13 00 00 00 13 00 00 00
+13 00 00 00 13 00 00 00 13 00 00 00 13 00 00 00
+13 00 00 00 13 00 00 00 13 00 00 00 13 00 00 00
+93 00 00 00 13 01 00 00 93 01 00 00 13 02 00 00
+93 02 00 00 13 03 00 00 93 03 00 00 13 04 00 00
+93 04 00 00 13 05 00 00 93 05 00 00 13 06 00 00
+93 06 00 00 13 07 00 00 93 07 00 00 13 08 00 00
+93 08 00 00 13 09 00 00 93 09 00 00 13 0A 00 00
+93 0A 00 00 13 0B 00 00 93 0B 00 00 13 0C 00 00
+93 0C 00 00 13 0D 00 00 93 0D 00 00 13 0E 00 00
+93 0E 00 00 13 0F 00 00 93 0F 00 00 97 01 48 00
+93 81 41 62 13 05 00 40 97 05 48 00 93 85 85 D7
+17 06 48 00 13 06 06 E3 63 0D B5 00 29 A0 14 41
+94 C1 11 05 91 05 E3 9C C5 FE 17 06 48 00 13 06
+66 E1 97 05 48 00 93 85 E5 E0 21 A0 23 20 06 00
+11 06 E3 9D C5 FE 17 01 49 00 13 01 A1 D3 17 05
+48 00 13 05 25 DF 17 06 48 00 13 06 A6 DE B3 05
+A6 40 17 07 49 00 13 07 E7 91 33 02 B7 40 92 85
+17 06 48 00 13 06 06 DD 29 A0 14 41 94 C1 11 05
+91 05 E3 1C C5 FE 21 A0 23 A0 05 00 91 05 E3 9D
+E5 FE B7 02 49 00 05 43 23 A0 62 00 B7 02 49 00
+91 02 13 03 30 06 23 A0 62 00 B7 02 49 00 C1 02
+7D 53 23 A0 62 00 23 A2 62 00 01 45 81 45 97 02
+48 00 E7 80 22 CC 97 02 48 00 93 82 A2 D1 6D 71
+06 C2 0A C4 0E C6 12 C8 16 CA 1A CC 1E CE 22 D0
+26 D2 2A D4 2E D6 32 D8 36 DA 3A DC 3E DE C2 C0
+C6 C2 CA C4 CE C6 D2 C8 D6 CA DA CC DE CE E2 D0
+E6 D2 EA D4 EE D6 F2 D8 F6 DA FA DC FE DE 73 25
+20 34 F3 25 10 34 0A 86 EF 00 80 04 92 40 22 41
+B2 41 42 42 D2 42 62 43 F2 43 02 54 92 54 22 55
+B2 55 42 56 D2 56 62 57 F2 57 06 48 96 48 26 49
+B6 49 46 4A D6 4A 66 4B F6 4B 06 5C 96 5C 26 5D
+B6 5D 46 5E D6 5E 66 5F F6 5F 51 61 73 00 20 30
+6F F0 5F D1 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+@00000400
+37 37 22 11 B7 07 00 30 93 02 47 34 37 43 33 22
+23 AC 57 00 93 03 53 45 37 55 44 33 23 AE 77 00
+93 05 65 56 37 66 55 44 8C D3 93 06 76 67 37 78
+66 55 D4 D3 93 08 88 78 37 9E 77 66 23 A4 17 03
+93 0E 9E 89 23 A6 D7 03 01 A0 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+97 02 B8 FF 93 82 42 09 82 82 13 00 00 00 13 00
+00 00 13 00 00 00 13 00 00 00 13 00 00 00 01 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+@000004A0
+13 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
yifive/trunk/caravel_yifive/verilog/dv/risc_boot/user_risc_boot.hex
Property changes :
Added: svn:executable
## -0,0 +1 ##
+*
\ No newline at end of property
Index: yifive/trunk/caravel_yifive/verilog/dv/user_risc_boot/Makefile
===================================================================
--- yifive/trunk/caravel_yifive/verilog/dv/user_risc_boot/Makefile (nonexistent)
+++ yifive/trunk/caravel_yifive/verilog/dv/user_risc_boot/Makefile (revision 22)
@@ -0,0 +1,83 @@
+# SPDX-FileCopyrightText: 2020 Efabless Corporation
+#
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+#
+# SPDX-License-Identifier: Apache-2.0
+
+## Caravel Pointers
+CARAVEL_ROOT ?= ../../../caravel
+CARAVEL_PATH ?= $(CARAVEL_ROOT)
+CARAVEL_FIRMWARE_PATH = $(CARAVEL_PATH)/verilog/dv/caravel
+CARAVEL_VERILOG_PATH = $(CARAVEL_PATH)/verilog
+CARAVEL_RTL_PATH = $(CARAVEL_VERILOG_PATH)/rtl
+CARAVEL_BEHAVIOURAL_MODELS = $(CARAVEL_VERILOG_PATH)/dv/caravel
+
+## User Project Pointers
+UPRJ_VERILOG_PATH ?= ../../../verilog
+UPRJ_RTL_PATH = $(UPRJ_VERILOG_PATH)/rtl
+UPRJ_BEHAVIOURAL_MODELS = ../model
+UPRJ_INCLUDE_PATH1 = $(UPRJ_RTL_PATH)/syntacore/scr1/src/includes
+UPRJ_INCLUDE_PATH2 = $(UPRJ_RTL_PATH)/sdram_ctrl/src/defs
+
+## RISCV GCC
+GCC_PATH?=/ef/apps/bin
+GCC_PREFIX?=riscv64-unknown-elf
+PDK_PATH?=/ef/tech/SW/sky130A
+
+## Simulation mode: RTL/GL
+SIM?=RTL
+
+.SUFFIXES:
+
+PATTERN = user_risc_boot
+
+all: ${PATTERN:=.vcd}
+
+hex: ${PATTERN:=.hex}
+
+vvp: ${PATTERN:=.vvp}
+
+%.vvp: %_tb.v %.hex
+ifeq ($(SIM),RTL)
+ iverilog -g2005-sv -DFUNCTIONAL -DSIM -I $(PDK_PATH) \
+ -I $(CARAVEL_BEHAVIOURAL_MODELS) -I $(CARAVEL_RTL_PATH) \
+ -I $(UPRJ_BEHAVIOURAL_MODELS) -I $(UPRJ_RTL_PATH) \
+ -I $(UPRJ_INCLUDE_PATH1) -I $(UPRJ_INCLUDE_PATH2) \
+ $< -o $@
+else
+ iverilog -DFUNCTIONAL -DSIM -DGL -I $(PDK_PATH) \
+ -I $(CARAVEL_BEHAVIOURAL_MODELS) -I $(CARAVEL_RTL_PATH) -I $(CARAVEL_VERILOG_PATH) \
+ -I $(UPRJ_BEHAVIOURAL_MODELS) -I$(UPRJ_RTL_PATH) -I $(UPRJ_VERILOG_PATH) \
+ $< -o $@
+endif
+
+%.vcd: %.vvp
+ vvp $<
+
+%.elf: %.c $(CARAVEL_FIRMWARE_PATH)/sections.lds $(CARAVEL_FIRMWARE_PATH)/start.s
+ ${GCC_PREFIX}-gcc -I $(CARAVEL_PATH) -march=rv32imc -mabi=ilp32 -Wl,-Bstatic,-T,$(CARAVEL_FIRMWARE_PATH)/sections.lds,--strip-debug -ffreestanding -nostdlib -o $@ $(CARAVEL_FIRMWARE_PATH)/start.s $<
+
+%.hex: %.elf
+ ${GCC_PREFIX}-objcopy -O verilog $< $@
+ # to fix flash base address
+ sed -i 's/@10000000/@00000000/g' $@
+
+%.bin: %.elf
+ ${GCC_PREFIX}-objcopy -O binary $< /dev/stdout | tail -c +1048577 > $@
+
+# ---- Clean ----
+
+clean:
+ rm -f *.elf *.hex *.bin *.vvp *.vcd *.log
+
+.PHONY: clean hex all
Index: yifive/trunk/caravel_yifive/verilog/dv/user_risc_boot/run_iverilog
===================================================================
--- yifive/trunk/caravel_yifive/verilog/dv/user_risc_boot/run_iverilog (nonexistent)
+++ yifive/trunk/caravel_yifive/verilog/dv/user_risc_boot/run_iverilog (revision 22)
@@ -0,0 +1,20 @@
+riscv64-unknown-elf-gcc -O2 -funroll-loops -fpeel-loops -fgcse-sm -fgcse-las -D__RVC_EXT -static -std=gnu99 -fno-common -fno-builtin-printf -DTCM=1 -Wa,-march=rv32imc -march=rv32imc -mabi=ilp32 -DFLAGS_STR=\""-O2 -funroll-loops -fpeel-loops -fgcse-sm -fgcse-las "\" -c -I./ -I../../rtl/syntacore/scr1/sim/tests/common user_risc_boot.c -o user_risc_boot.o
+
+riscv64-unknown-elf-gcc -O2 -funroll-loops -fpeel-loops -fgcse-sm -fgcse-las -D__RVC_EXT -static -std=gnu99 -fno-common -fno-builtin-printf -DTCM=1 -Wa,-march=rv32imc -march=rv32imc -mabi=ilp32 -DFLAGS_STR=\""-O2 -funroll-loops -fpeel-loops -fgcse-sm -fgcse-las "\" -D__ASSEMBLY__=1 -c -I./ -I../../rtl/syntacore/scr1/sim/tests/common/ ../../rtl/syntacore/scr1/sim/tests/common/crt_tcm.S -o crt_tcm.o
+
+riscv64-unknown-elf-gcc -o user_risc_boot.elf -T ../../rtl/syntacore/scr1/sim/tests/common/link_tcm.ld user_risc_boot.o crt_tcm.o -nostartfiles -nostdlib -lc -lgcc -march=rv32imc -mabi=ilp32
+
+riscv64-unknown-elf-objcopy -O verilog user_risc_boot.elf user_risc_boot.hex
+
+riscv64-unknown-elf-objdump -D user_risc_boot.elf > user_risc_boot.dump
+
+rm crt_tcm.o user_risc_boot.o
+
+#iverilog with waveform dump
+#iverilog -g2005-sv -DWFDUMP -I $PDK_PATH -I ../ -I ../../../verilog/rtl -I ../../../verilog/rtl/syntacore/scr1/src/includes -I ../../../verilog/rtl/sdram_ctrl/src/defs -I $$CARAVEL_ROOT/verilog/dv/caravel -I ../model user_risc_boot_tb.v -o user_risc_boot_tb.vvp
+
+iverilog -g2005-sv -I $PDK_PATH -I ../ -I ../../../verilog/rtl -I ../../../verilog/rtl/syntacore/scr1/src/includes -I ../../../verilog/rtl/sdram_ctrl/src/defs -I $CARAVEL_ROOT/verilog/dv/caravel -I ../model user_risc_boot_tb.v -o user_risc_boot_tb.vvp
+
+vvp user_risc_boot_tb.vvp | tee test.log
+
+\rm -rf user_risc_boot_tb.vvp
yifive/trunk/caravel_yifive/verilog/dv/user_risc_boot/run_iverilog
Property changes :
Added: svn:executable
## -0,0 +1 ##
+*
\ No newline at end of property
Index: yifive/trunk/caravel_yifive/verilog/dv/user_risc_boot/uprj_netlists.v
===================================================================
--- yifive/trunk/caravel_yifive/verilog/dv/user_risc_boot/uprj_netlists.v (nonexistent)
+++ yifive/trunk/caravel_yifive/verilog/dv/user_risc_boot/uprj_netlists.v (revision 22)
@@ -0,0 +1,74 @@
+// SPDX-FileCopyrightText: 2020 Efabless Corporation
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+// SPDX-License-Identifier: Apache-2.0
+
+// Include caravel global defines for the number of the user project IO pads
+`define USE_POWER_PINS
+
+ `include "spi_master/src/spim_top.sv"
+ `include "spi_master/src/spim_regs.sv"
+ `include "spi_master/src/spim_clkgen.sv"
+ `include "spi_master/src/spim_ctrl.sv"
+ `include "spi_master/src/spim_rx.sv"
+ `include "spi_master/src/spim_tx.sv"
+
+ `include "sdram_ctrl/src/top/sdrc_top.v"
+ `include "sdram_ctrl/src/wb2sdrc/wb2sdrc.v"
+ `include "lib/async_fifo.sv"
+ `include "sdram_ctrl/src/core/sdrc_core.v"
+ `include "sdram_ctrl/src/core/sdrc_bank_ctl.v"
+ `include "sdram_ctrl/src/core/sdrc_bank_fsm.v"
+ `include "sdram_ctrl/src/core/sdrc_bs_convert.v"
+ `include "sdram_ctrl/src/core/sdrc_req_gen.v"
+ `include "sdram_ctrl/src/core/sdrc_xfr_ctl.v"
+
+ `include "lib/registers.v"
+ `include "lib/clk_ctl.v"
+ `include "digital_core/src/glbl_cfg.sv"
+ `include "digital_core/src/digital_core.sv"
+
+ `include "wb_interconnect/src/wb_arb.sv"
+ `include "wb_interconnect/src/wb_interconnect.sv"
+
+
+ `include "syntacore/scr1/src/core/pipeline/scr1_pipe_hdu.sv"
+ `include "syntacore/scr1/src/core/pipeline/scr1_pipe_tdu.sv"
+ `include "syntacore/scr1/src/core/pipeline/scr1_ipic.sv"
+ `include "syntacore/scr1/src/core/pipeline/scr1_pipe_csr.sv"
+ `include "syntacore/scr1/src/core/pipeline/scr1_pipe_exu.sv"
+ `include "syntacore/scr1/src/core/pipeline/scr1_pipe_ialu.sv"
+ `include "syntacore/scr1/src/core/pipeline/scr1_pipe_idu.sv"
+ `include "syntacore/scr1/src/core/pipeline/scr1_pipe_ifu.sv"
+ `include "syntacore/scr1/src/core/pipeline/scr1_pipe_lsu.sv"
+ `include "syntacore/scr1/src/core/pipeline/scr1_pipe_mprf.sv"
+ `include "syntacore/scr1/src/core/pipeline/scr1_pipe_top.sv"
+ `include "syntacore/scr1/src/core/primitives/scr1_reset_cells.sv"
+ `include "syntacore/scr1/src/core/primitives/scr1_cg.sv"
+ `include "syntacore/scr1/src/core/scr1_clk_ctrl.sv"
+ `include "syntacore/scr1/src/core/scr1_tapc_shift_reg.sv"
+ `include "syntacore/scr1/src/core/scr1_tapc.sv"
+ `include "syntacore/scr1/src/core/scr1_tapc_synchronizer.sv"
+ `include "syntacore/scr1/src/core/scr1_core_top.sv"
+ `include "syntacore/scr1/src/core/scr1_dm.sv"
+ `include "syntacore/scr1/src/core/scr1_dmi.sv"
+ `include "syntacore/scr1/src/core/scr1_scu.sv"
+
+ `include "syntacore/scr1/src/top/scr1_dmem_router.sv"
+ `include "syntacore/scr1/src/top/scr1_dp_memory.sv"
+ `include "syntacore/scr1/src/top/scr1_tcm.sv"
+ `include "syntacore/scr1/src/top/scr1_timer.sv"
+ `include "syntacore/scr1/src/top/scr1_dmem_wb.sv"
+ `include "syntacore/scr1/src/top/scr1_imem_wb.sv"
+ `include "syntacore/scr1/src/top/scr1_top_wb.sv"
+ `include "lib/sync_fifo.sv"
Index: yifive/trunk/caravel_yifive/verilog/dv/user_risc_boot/user_risc_boot.c
===================================================================
--- yifive/trunk/caravel_yifive/verilog/dv/user_risc_boot/user_risc_boot.c (nonexistent)
+++ yifive/trunk/caravel_yifive/verilog/dv/user_risc_boot/user_risc_boot.c (revision 22)
@@ -0,0 +1,45 @@
+
+#define SC_SIM_OUTPORT (0xf0000000)
+#define uint32_t long
+
+#define reg_mprj_globl_reg0 (*(volatile uint32_t*)0x30000000)
+#define reg_mprj_globl_reg1 (*(volatile uint32_t*)0x30000004)
+#define reg_mprj_globl_reg2 (*(volatile uint32_t*)0x30000008)
+#define reg_mprj_globl_reg3 (*(volatile uint32_t*)0x3000000C)
+#define reg_mprj_globl_reg4 (*(volatile uint32_t*)0x30000010)
+#define reg_mprj_globl_reg5 (*(volatile uint32_t*)0x30000014)
+#define reg_mprj_globl_reg6 (*(volatile uint32_t*)0x30000018)
+#define reg_mprj_globl_reg7 (*(volatile uint32_t*)0x3000001C)
+#define reg_mprj_globl_reg8 (*(volatile uint32_t*)0x30000020)
+#define reg_mprj_globl_reg9 (*(volatile uint32_t*)0x30000024)
+#define reg_mprj_globl_reg10 (*(volatile uint32_t*)0x30000028)
+#define reg_mprj_globl_reg11 (*(volatile uint32_t*)0x3000002C)
+#define reg_mprj_globl_reg12 (*(volatile uint32_t*)0x30000030)
+#define reg_mprj_globl_reg13 (*(volatile uint32_t*)0x30000034)
+#define reg_mprj_globl_reg14 (*(volatile uint32_t*)0x30000038)
+#define reg_mprj_globl_reg15 (*(volatile uint32_t*)0x3000003C)
+
+int main()
+{
+
+ //volatile long *out_ptr = (volatile long*)SC_SIM_OUTPORT;
+ //*out_ptr = 0xAABBCCDD;
+ //*out_ptr = 0xBBCCDDEE;
+ //*out_ptr = 0xCCDDEEFF;
+ //*out_ptr = 0xDDEEFF00;
+
+ // Write software Write & Read Register
+ reg_mprj_globl_reg6 = 0x11223344;
+ reg_mprj_globl_reg7 = 0x22334455;
+ reg_mprj_globl_reg8 = 0x33445566;
+ reg_mprj_globl_reg9 = 0x44556677;
+ reg_mprj_globl_reg10 = 0x55667788;
+ reg_mprj_globl_reg11 = 0x66778899;
+ //reg_mprj_globl_reg12 = 0x778899AA;
+ //reg_mprj_globl_reg13 = 0x8899AABB;
+ //reg_mprj_globl_reg14 = 0x99AABBCC;
+ //reg_mprj_globl_reg15 = 0xAABBCCDD;
+
+ while(1) {}
+ return 0;
+}
Index: yifive/trunk/caravel_yifive/verilog/dv/user_risc_boot/user_risc_boot.hex
===================================================================
--- yifive/trunk/caravel_yifive/verilog/dv/user_risc_boot/user_risc_boot.hex (nonexistent)
+++ yifive/trunk/caravel_yifive/verilog/dv/user_risc_boot/user_risc_boot.hex (revision 22)
@@ -0,0 +1,79 @@
+@00000000
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 13 00 00 00 6F 00 00 00 FF FF FF FF
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+6F 00 E0 18 13 00 00 00 13 00 00 00 13 00 00 00
+13 00 00 00 13 00 00 00 13 00 00 00 13 00 00 00
+13 00 00 00 13 00 00 00 13 00 00 00 13 00 00 00
+13 00 00 00 13 00 00 00 13 00 00 00 13 00 00 00
+93 00 00 00 13 01 00 00 93 01 00 00 13 02 00 00
+93 02 00 00 13 03 00 00 93 03 00 00 13 04 00 00
+93 04 00 00 13 05 00 00 93 05 00 00 13 06 00 00
+93 06 00 00 13 07 00 00 93 07 00 00 13 08 00 00
+93 08 00 00 13 09 00 00 93 09 00 00 13 0A 00 00
+93 0A 00 00 13 0B 00 00 93 0B 00 00 13 0C 00 00
+93 0C 00 00 13 0D 00 00 93 0D 00 00 13 0E 00 00
+93 0E 00 00 13 0F 00 00 93 0F 00 00 97 01 48 00
+93 81 41 62 13 05 00 40 97 05 48 00 93 85 85 D7
+17 06 48 00 13 06 06 E3 63 0D B5 00 29 A0 14 41
+94 C1 11 05 91 05 E3 9C C5 FE 17 06 48 00 13 06
+66 E1 97 05 48 00 93 85 E5 E0 21 A0 23 20 06 00
+11 06 E3 9D C5 FE 17 01 49 00 13 01 A1 D3 17 05
+48 00 13 05 25 DF 17 06 48 00 13 06 A6 DE B3 05
+A6 40 17 07 49 00 13 07 E7 91 33 02 B7 40 92 85
+17 06 48 00 13 06 06 DD 29 A0 14 41 94 C1 11 05
+91 05 E3 1C C5 FE 21 A0 23 A0 05 00 91 05 E3 9D
+E5 FE B7 02 49 00 05 43 23 A0 62 00 B7 02 49 00
+91 02 13 03 30 06 23 A0 62 00 B7 02 49 00 C1 02
+7D 53 23 A0 62 00 23 A2 62 00 01 45 81 45 97 02
+48 00 E7 80 22 CC 97 02 48 00 93 82 A2 D1 6D 71
+06 C2 0A C4 0E C6 12 C8 16 CA 1A CC 1E CE 22 D0
+26 D2 2A D4 2E D6 32 D8 36 DA 3A DC 3E DE C2 C0
+C6 C2 CA C4 CE C6 D2 C8 D6 CA DA CC DE CE E2 D0
+E6 D2 EA D4 EE D6 F2 D8 F6 DA FA DC FE DE 73 25
+20 34 F3 25 10 34 0A 86 EF 00 80 04 92 40 22 41
+B2 41 42 42 D2 42 62 43 F2 43 02 54 92 54 22 55
+B2 55 42 56 D2 56 62 57 F2 57 06 48 96 48 26 49
+B6 49 46 4A D6 4A 66 4B F6 4B 06 5C 96 5C 26 5D
+B6 5D 46 5E D6 5E 66 5F F6 5F 51 61 73 00 20 30
+6F F0 5F D1 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+@00000400
+37 37 22 11 B7 07 00 30 93 02 47 34 37 43 33 22
+23 AC 57 00 93 03 53 45 37 55 44 33 23 AE 77 00
+93 05 65 56 37 66 55 44 8C D3 93 06 76 67 37 78
+66 55 D4 D3 93 08 88 78 37 9E 77 66 23 A4 17 03
+93 0E 9E 89 23 A6 D7 03 01 A0 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+97 02 B8 FF 93 82 42 09 82 82 13 00 00 00 13 00
+00 00 13 00 00 00 13 00 00 00 13 00 00 00 01 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+@000004A0
+13 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
yifive/trunk/caravel_yifive/verilog/dv/user_risc_boot/user_risc_boot.hex
Property changes :
Added: svn:executable
## -0,0 +1 ##
+*
\ No newline at end of property
Index: yifive/trunk/caravel_yifive/verilog/dv/user_risc_boot/user_risc_boot_tb.v
===================================================================
--- yifive/trunk/caravel_yifive/verilog/dv/user_risc_boot/user_risc_boot_tb.v (nonexistent)
+++ yifive/trunk/caravel_yifive/verilog/dv/user_risc_boot/user_risc_boot_tb.v (revision 22)
@@ -0,0 +1,397 @@
+//////////////////////////////////////////////////////////////////////
+//// ////
+//// Standalone User validation Test bench ////
+//// ////
+//// This file is part of the YIFive cores project ////
+//// http://www.opencores.org/cores/yifive/ ////
+//// ////
+//// Description ////
+// This is a standalone test bench to validate the ////
+// Digital core. ////
+// 1. User Risc core is booted using compiled code of ////
+// user_risc_boot.c ////
+// 2. User Risc core uses Serial Flash and SDRAM to boot ////
+// 3. After successful boot, Risc core will write signature ////
+// in to user register from 0x3000_0018 to 0x3000_002C ////
+// 4. Through the External Wishbone Interface we read back ////
+// and validate the user register to declared pass fail ////
+//// ////
+//// To Do: ////
+//// nothing ////
+//// ////
+//// Author(s): ////
+//// - Dinesh Annayya, dinesha@opencores.org ////
+//// ////
+//// Revision : ////
+//// 0.1 - 16th Feb 2021, Dinesh A ////
+//// ////
+//////////////////////////////////////////////////////////////////////
+//// ////
+//// Copyright (C) 2000 Authors and OPENCORES.ORG ////
+//// ////
+//// 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 ////
+//// ////
+//////////////////////////////////////////////////////////////////////
+
+`default_nettype none
+
+`timescale 1 ns / 1 ps
+
+`include "uprj_netlists.v"
+`include "spiflash.v"
+`include "mt48lc8m8a2.v"
+
+module user_risc_boot_tb;
+ reg clock;
+ reg RSTB;
+ reg power1, power2;
+ reg power3, power4;
+
+ reg wbd_ext_cyc_i; // strobe/request
+ reg wbd_ext_stb_i; // strobe/request
+ reg [31:0] wbd_ext_adr_i; // address
+ reg wbd_ext_we_i; // write
+ reg [31:0] wbd_ext_dat_i; // data output
+ reg [3:0] wbd_ext_sel_i; // byte enable
+
+ wire [31:0] wbd_ext_dat_o; // data input
+ wire wbd_ext_ack_o; // acknowlegement
+ wire wbd_ext_err_o; // error
+
+ // User I/O
+ wire [37:0] io_oeb;
+ wire [37:0] io_out;
+ wire [37:0] io_in;
+
+ wire gpio;
+ wire [37:0] mprj_io;
+ wire [7:0] mprj_io_0;
+ reg test_fail;
+ reg [31:0] read_data;
+
+
+
+ // External clock is used by default. Make this artificially fast for the
+ // simulation. Normally this would be a slow clock and the digital PLL
+ // would be the fast clock.
+
+ always #12.5 clock <= (clock === 1'b0);
+
+ initial begin
+ clock = 0;
+ wbd_ext_cyc_i ='h0; // strobe/request
+ wbd_ext_stb_i ='h0; // strobe/request
+ wbd_ext_adr_i ='h0; // address
+ wbd_ext_we_i ='h0; // write
+ wbd_ext_dat_i ='h0; // data output
+ wbd_ext_sel_i ='h0; // byte enable
+ end
+
+ `ifdef WFDUMP
+ initial begin
+ $dumpfile("risc_boot.vcd");
+ $dumpvars(0, user_risc_boot_tb);
+ end
+ `endif
+
+ initial begin
+
+ #200; // Wait for reset removal
+ repeat (10) @(posedge clock);
+ $display("Monitor: Standalone User Risc Boot Test Started");
+
+ #1;
+ //------------ SDRAM Config - 2
+ wb_user_core_write('h3000_0014,'h100_019E);
+
+ repeat (2) @(posedge clock);
+ #1;
+ //------------ SDRAM Config - 1
+ wb_user_core_write('h3000_0010,'h2F17_2242);
+
+ repeat (2) @(posedge clock);
+ #1;
+ // Remove all the reset
+ wb_user_core_write('h3000_0000,'h7);
+
+
+ // Repeat cycles of 1000 clock edges as needed to complete testbench
+ repeat (30) begin
+ repeat (1000) @(posedge clock);
+ // $display("+1000 cycles");
+ end
+
+
+ $display("Monitor: Reading Back the expected value");
+ // User RISC core expect to write these value in global
+ // register, read back and decide on pass fail
+ // 0x30000018 = 0x11223344;
+ // 0x3000001C = 0x22334455;
+ // 0x30000020 = 0x33445566;
+ // 0x30000024 = 0x44556677;
+ // 0x30000028 = 0x55667788;
+ // 0x3000002C = 0x66778899;
+
+ test_fail = 0;
+ wb_user_core_read(32'h30000018,read_data);
+ if(read_data != 32'h11223344) test_fail = 1;
+
+ wb_user_core_read(32'h3000001C,read_data);
+ if(read_data != 32'h22334455) test_fail = 1;
+
+ wb_user_core_read(32'h30000020,read_data);
+ if(read_data != 32'h33445566) test_fail = 1;
+
+ wb_user_core_read(32'h30000024,read_data);
+ if(read_data!= 32'h44556677) test_fail = 1;
+
+ wb_user_core_read(32'h30000028,read_data);
+ if(read_data!= 32'h55667788) test_fail = 1;
+
+ wb_user_core_read(32'h3000002C,read_data) ;
+ if(read_data != 32'h66778899) test_fail = 1;
+
+
+ $display("###################################################");
+ if(test_fail == 0) begin
+ `ifdef GL
+ $display("Monitor: Standalone User Risc Boot (GL) Passed");
+ `else
+ $display("Monitor: Standalone User Risc Boot (RTL) Passed");
+ `endif
+ end else begin
+ `ifdef GL
+ $display("Monitor: Standalone User Risc Boot (GL) Failed");
+ `else
+ $display("Monitor: Standalone User Risc Boot (RTL) Failed");
+ `endif
+ end
+ $display("###################################################");
+ $finish;
+ end
+
+ initial begin
+ RSTB <= 1'b0;
+ #100;
+ RSTB <= 1'b1; // Release reset
+ end
+
+
+ digital_core u_core(
+`ifdef USE_POWER_PINS
+ .vdda1(), // User area 1 3.3V supply
+ .vdda2(), // User area 2 3.3V supply
+ .vssa1(), // User area 1 analog ground
+ .vssa2(), // User area 2 analog ground
+ .vccd1(), // User area 1 1.8V supply
+ .vccd2(), // User area 2 1.8v supply
+ .vssd1(), // User area 1 digital ground
+ .vssd2(), // User area 2 digital ground
+`endif
+ .clk (clock), // System clock
+ .rtc_clk (1'b1), // Real-time clock
+ .rst_n (RSTB), // Regular Reset signal
+
+ .wbd_ext_cyc_i (wbd_ext_cyc_i), // strobe/request
+ .wbd_ext_stb_i (wbd_ext_stb_i), // strobe/request
+ .wbd_ext_adr_i (wbd_ext_adr_i), // address
+ .wbd_ext_we_i (wbd_ext_we_i), // write
+ .wbd_ext_dat_i (wbd_ext_dat_i), // data output
+ .wbd_ext_sel_i (wbd_ext_sel_i), // byte enable
+
+ .wbd_ext_dat_o (wbd_ext_dat_o), // data input
+ .wbd_ext_ack_o (wbd_ext_ack_o), // acknowlegement
+ .wbd_ext_err_o (wbd_ext_err_o), // error
+
+
+ // Logic Analyzer Signals
+ .la_data_in ('0) ,
+ .la_data_out (),
+ .la_oenb ('0),
+
+
+ // IOs
+ .io_in (io_in) ,
+ .io_out (io_out) ,
+ .io_oeb (io_oeb) ,
+
+ .irq ()
+
+);
+
+//------------------------------------------------------
+// Integrate the Serial flash with qurd support to
+// user core using the gpio pads
+// ----------------------------------------------------
+
+ wire flash_clk = io_out[30];
+ wire flash_csb = io_out[31];
+ tri flash_io0 = (io_oeb[32]== 1'b0) ? io_out[32] : 1'bz;
+ tri flash_io1 = (io_oeb[33]== 1'b0) ? io_out[33] : 1'bz;
+ tri flash_io2 = (io_oeb[34]== 1'b0) ? io_out[34] : 1'bz;
+ tri flash_io3 = (io_oeb[35]== 1'b0) ? io_out[35] : 1'bz;
+
+ assign io_in[32] = flash_io0;
+ assign io_in[33] = flash_io1;
+ assign io_in[34] = flash_io2;
+ assign io_in[35] = flash_io3;
+
+
+ // Quard flash
+ spiflash #(
+ .FILENAME("user_risc_boot.hex")
+ ) u_user_spiflash (
+ .csb(flash_csb),
+ .clk(flash_clk),
+ .io0(flash_io0),
+ .io1(flash_io1),
+ .io2(flash_io2),
+ .io3(flash_io3)
+ );
+
+
+//------------------------------------------------
+// Integrate the SDRAM 8 BIT Memory
+// -----------------------------------------------
+
+wire [7:0] Dq ; // SDRAM Read/Write Data Bus
+wire [0:0] sdr_dqm ; // SDRAM DATA Mask
+wire [1:0] sdr_ba ; // SDRAM Bank Select
+wire [12:0] sdr_addr ; // SDRAM ADRESS
+wire sdr_cs_n ; // chip select
+wire sdr_cke ; // clock gate
+wire sdr_ras_n ; // ras
+wire sdr_cas_n ; // cas
+wire sdr_we_n ; // write enable
+wire sdram_clk ;
+
+assign Dq[7:0] = (io_oeb[7:0] == 8'h0) ? io_out [7:0] : 8'hZZ;
+assign sdr_addr[12:0] = io_out [20:8] ;
+assign sdr_ba[1:0] = io_out [22:21] ;
+assign sdr_dqm[0] = io_out [23] ;
+assign sdr_we_n = io_out [24] ;
+assign sdr_cas_n = io_out [25] ;
+assign sdr_ras_n = io_out [26] ;
+assign sdr_cs_n = io_out [27] ;
+assign sdr_cke = io_out [28] ;
+assign sdram_clk = io_out [29] ;
+assign io_in[29] = sdram_clk;
+assign #(1) io_in[7:0] = Dq;
+
+// to fix the sdram interface timing issue
+wire #(1) sdram_clk_d = sdram_clk;
+
+ // SDRAM 8bit
+mt48lc8m8a2 #(.data_bits(8)) u_sdram8 (
+ .Dq (Dq ) ,
+ .Addr (sdr_addr[11:0] ),
+ .Ba (sdr_ba ),
+ .Clk (sdram_clk_d ),
+ .Cke (sdr_cke ),
+ .Cs_n (sdr_cs_n ),
+ .Ras_n (sdr_ras_n ),
+ .Cas_n (sdr_cas_n ),
+ .We_n (sdr_we_n ),
+ .Dqm (sdr_dqm )
+ );
+
+
+task wb_user_core_write;
+input [31:0] address;
+input [31:0] data;
+begin
+ repeat (1) @(posedge clock);
+ wbd_ext_adr_i =address; // address
+ wbd_ext_we_i ='h1; // write
+ wbd_ext_dat_i =data; // data output
+ wbd_ext_sel_i ='hF; // byte enable
+ wbd_ext_cyc_i ='h1; // strobe/request
+ wbd_ext_stb_i ='h1; // strobe/request
+ wait(wbd_ext_ack_o == 1);
+ repeat (1) @(posedge clock);
+ wbd_ext_cyc_i ='h0; // strobe/request
+ wbd_ext_stb_i ='h0; // strobe/request
+ wbd_ext_adr_i ='h0; // address
+ wbd_ext_we_i ='h0; // write
+ wbd_ext_dat_i ='h0; // data output
+ wbd_ext_sel_i ='h0; // byte enable
+ $display("DEBUG WB USER ACCESS WRITE Address : %x, Data : %x",address,data);
+ repeat (2) @(posedge clock);
+end
+endtask
+
+task wb_user_core_read;
+input [31:0] address;
+output [31:0] data;
+reg [31:0] data;
+begin
+ repeat (1) @(posedge clock);
+ wbd_ext_adr_i =address; // address
+ wbd_ext_we_i ='h0; // write
+ wbd_ext_dat_i ='0; // data output
+ wbd_ext_sel_i ='hF; // byte enable
+ wbd_ext_cyc_i ='h1; // strobe/request
+ wbd_ext_stb_i ='h1; // strobe/request
+ wait(wbd_ext_ack_o == 1);
+ data = wbd_ext_dat_o;
+ repeat (1) @(posedge clock);
+ wbd_ext_cyc_i ='h0; // strobe/request
+ wbd_ext_stb_i ='h0; // strobe/request
+ wbd_ext_adr_i ='h0; // address
+ wbd_ext_we_i ='h0; // write
+ wbd_ext_dat_i ='h0; // data output
+ wbd_ext_sel_i ='h0; // byte enable
+ $display("DEBUG WB USER ACCESS READ Address : %x, Data : %x",address,data);
+ repeat (2) @(posedge clock);
+end
+endtask
+
+
+
+
+////-----------------------------------------------------------------------------
+//// RISC IMEM amd DMEM Monitoring TASK
+////-----------------------------------------------------------------------------
+//logic [`SCR1_DMEM_AWIDTH-1:0] core2imem_addr_o_r; // DMEM address
+//logic [`SCR1_DMEM_AWIDTH-1:0] core2dmem_addr_o_r; // DMEM address
+//logic core2dmem_cmd_o_r;
+//
+//`define RISC_CORE user_risc_boot_tb.u_core.u_riscv_top.i_core_top
+//
+//always@(posedge `RISC_CORE.clk) begin
+// if(`RISC_CORE.imem2core_req_ack_i && `RISC_CORE.core2imem_req_o)
+// core2imem_addr_o_r <= `RISC_CORE.core2imem_addr_o;
+//
+// if(`RISC_CORE.dmem2core_req_ack_i && `RISC_CORE.core2dmem_req_o) begin
+// core2dmem_addr_o_r <= `RISC_CORE.core2dmem_addr_o;
+// core2dmem_cmd_o_r <= `RISC_CORE.core2dmem_cmd_o;
+// end
+//
+// if(`RISC_CORE.imem2core_resp_i !=0)
+// $display("RISCV-DEBUG => IMEM ADDRESS: %x Read Data : %x Resonse: %x", core2imem_addr_o_r,`RISC_CORE.imem2core_rdata_i,`RISC_CORE.imem2core_resp_i);
+// if((`RISC_CORE.dmem2core_resp_i !=0) && core2dmem_cmd_o_r)
+// $display("RISCV-DEBUG => DMEM ADDRESS: %x Write Data: %x Resonse: %x", core2dmem_addr_o_r,`RISC_CORE.core2dmem_wdata_o,`RISC_CORE.dmem2core_resp_i);
+// if((`RISC_CORE.dmem2core_resp_i !=0) && !core2dmem_cmd_o_r)
+// $display("RISCV-DEBUG => DMEM ADDRESS: %x READ Data : %x Resonse: %x", core2dmem_addr_o_r,`RISC_CORE.dmem2core_rdata_i,`RISC_CORE.dmem2core_resp_i);
+//end
+endmodule
+`default_nettype wire
Index: yifive/trunk/caravel_yifive/verilog/dv/wb_port/Makefile
===================================================================
--- yifive/trunk/caravel_yifive/verilog/dv/wb_port/Makefile (revision 21)
+++ yifive/trunk/caravel_yifive/verilog/dv/wb_port/Makefile (revision 22)
@@ -26,6 +26,8 @@
UPRJ_VERILOG_PATH ?= ../../../verilog
UPRJ_RTL_PATH = $(UPRJ_VERILOG_PATH)/rtl
UPRJ_BEHAVIOURAL_MODELS = ../
+UPRJ_INCLUDE_PATH1 = $(UPRJ_RTL_PATH)/syntacore/scr1/src/includes
+UPRJ_INCLUDE_PATH2 = $(UPRJ_RTL_PATH)/sdram_ctrl/src/defs
## RISCV GCC
GCC_PATH?=/ef/apps/bin
@@ -43,11 +45,14 @@
hex: ${PATTERN:=.hex}
+vvp: ${PATTERN:=.vvp}
+
%.vvp: %_tb.v %.hex
ifeq ($(SIM),RTL)
- iverilog -DFUNCTIONAL -DSIM -I $(PDK_PATH) \
+ iverilog -g2005-sv -DFUNCTIONAL -DSIM -I $(PDK_PATH) \
-I $(CARAVEL_BEHAVIOURAL_MODELS) -I $(CARAVEL_RTL_PATH) \
-I $(UPRJ_BEHAVIOURAL_MODELS) -I $(UPRJ_RTL_PATH) \
+ -I $(UPRJ_INCLUDE_PATH1) -I $(UPRJ_INCLUDE_PATH2) \
$< -o $@
else
iverilog -DFUNCTIONAL -DSIM -DGL -I $(PDK_PATH) \
/yifive/trunk/caravel_yifive/verilog/dv/wb_port/wb_port.c
19,6 → 19,27
#include "verilog/dv/caravel/defs.h" |
#include "verilog/dv/caravel/stub.c" |
|
// User Project Slaves (0x3000_0000) |
#define reg_mprj_slave (*(volatile uint32_t*)0x30000000) |
|
#define reg_mprj_globl_reg0 (*(volatile uint32_t*)0x30000000) |
#define reg_mprj_globl_reg1 (*(volatile uint32_t*)0x30000004) |
#define reg_mprj_globl_reg2 (*(volatile uint32_t*)0x30000008) |
#define reg_mprj_globl_reg3 (*(volatile uint32_t*)0x3000000C) |
#define reg_mprj_globl_reg4 (*(volatile uint32_t*)0x30000010) |
#define reg_mprj_globl_reg5 (*(volatile uint32_t*)0x30000014) |
#define reg_mprj_globl_reg6 (*(volatile uint32_t*)0x30000018) |
#define reg_mprj_globl_reg7 (*(volatile uint32_t*)0x3000001C) |
#define reg_mprj_globl_reg8 (*(volatile uint32_t*)0x30000020) |
#define reg_mprj_globl_reg9 (*(volatile uint32_t*)0x30000024) |
#define reg_mprj_globl_reg10 (*(volatile uint32_t*)0x30000028) |
#define reg_mprj_globl_reg11 (*(volatile uint32_t*)0x3000002C) |
#define reg_mprj_globl_reg12 (*(volatile uint32_t*)0x30000030) |
#define reg_mprj_globl_reg13 (*(volatile uint32_t*)0x30000034) |
#define reg_mprj_globl_reg14 (*(volatile uint32_t*)0x30000038) |
#define reg_mprj_globl_reg15 (*(volatile uint32_t*)0x3000003C) |
|
|
/* |
Wishbone Test: |
- Configures MPRJ lower 8-IO pins as outputs |
30,6 → 51,7
void main() |
{ |
|
int bFail = 0; |
/* |
IO Control Registers |
| DM | VTRIP | SLOW | AN_POL | AN_SEL | AN_EN | MOD_SEL | INP_DIS | HOLDH | OEB_N | MGMT_EN | |
80,8 → 102,34
// Flag start of the test |
reg_mprj_datal = 0xAB600000; |
|
reg_mprj_slave = 0x00002710; |
if (reg_mprj_slave == 0x2752) { |
if (reg_mprj_globl_reg1 != 0xA55AA55A) bFail = 1; |
if (reg_mprj_globl_reg2 != 0xAABBCCDD) bFail = 1; |
|
// Write software Write & Read Register |
reg_mprj_globl_reg6 = 0x11223344; |
reg_mprj_globl_reg7 = 0x22334455; |
reg_mprj_globl_reg8 = 0x33445566; |
reg_mprj_globl_reg9 = 0x44556677; |
reg_mprj_globl_reg10 = 0x55667788; |
reg_mprj_globl_reg11 = 0x66778899; |
reg_mprj_globl_reg12 = 0x778899AA; |
reg_mprj_globl_reg13 = 0x8899AABB; |
reg_mprj_globl_reg14 = 0x99AABBCC; |
reg_mprj_globl_reg15 = 0xAABBCCDD; |
|
|
if (reg_mprj_globl_reg6 != 0x11223344) bFail = 1; |
if (reg_mprj_globl_reg7 != 0x22334455) bFail = 1; |
if (reg_mprj_globl_reg8 != 0x33445566) bFail = 1; |
if (reg_mprj_globl_reg9 != 0x44556677) bFail = 1; |
if (reg_mprj_globl_reg10 != 0x55667788) bFail = 1; |
if (reg_mprj_globl_reg11 != 0x66778899) bFail = 1; |
if (reg_mprj_globl_reg12 != 0x778899AA) bFail = 1; |
if (reg_mprj_globl_reg13 != 0x8899AABB) bFail = 1; |
if (reg_mprj_globl_reg14 != 0x99AABBCC) bFail = 1; |
if (reg_mprj_globl_reg15 != 0xAABBCCDD) bFail = 1; |
|
if(bFail == 0) { |
reg_mprj_datal = 0xAB610000; |
} else { |
reg_mprj_datal = 0xAB600000; |
/yifive/trunk/caravel_yifive/verilog/dv/wb_port/wb_port_tb.v
47,10 → 47,15
clock = 0; |
end |
|
`ifdef WFDUMP |
initial begin |
$dumpfile("wb_port.vcd"); |
$dumpvars(0, wb_port_tb); |
$dumpvars(0, wb_port_tb.uut.mprj); |
end |
`endif |
|
initial begin |
|
// Repeat cycles of 1000 clock edges as needed to complete testbench |
repeat (30) begin |
repeat (1000) @(posedge clock); |
57,11 → 62,13
// $display("+1000 cycles"); |
end |
$display("%c[1;31m",27); |
$display ("##########################################################"); |
`ifdef GL |
$display ("Monitor: Timeout, Test Mega-Project WB Port (GL) Failed"); |
`else |
$display ("Monitor: Timeout, Test Mega-Project WB Port (RTL) Failed"); |
`endif |
$display ("##########################################################"); |
$display("%c[0m",27); |
$finish; |
end |
70,11 → 77,13
wait(checkbits == 16'h AB60); |
$display("Monitor: MPRJ-Logic WB Started"); |
wait(checkbits == 16'h AB61); |
$display ("##########################################################"); |
`ifdef GL |
$display("Monitor: Mega-Project WB (GL) Passed"); |
`else |
$display("Monitor: Mega-Project WB (RTL) Passed"); |
`endif |
$display ("##########################################################"); |
$finish; |
end |
|
102,9 → 111,9
power4 <= 1'b1; |
end |
|
always @(mprj_io) begin |
#1 $display("MPRJ-IO state = %b ", mprj_io[7:0]); |
end |
//always @(mprj_io) begin |
// #1 $display("MPRJ-IO state = %b ", mprj_io[7:0]); |
//end |
|
wire flash_csb; |
wire flash_clk; |
154,4 → 163,4
); |
|
endmodule |
`default_nettype wire |
`default_nettype wire |
/yifive/trunk/caravel_yifive/verilog/dv/Makefile
19,7 → 19,7
.SUFFIXES: |
.SILENT: clean all |
|
PATTERNS = io_ports la_test1 la_test2 wb_port mprj_stimulus |
PATTERNS = io_ports la_test1 la_test2 wb_port mprj_stimulus risc_boot user_risc_boot |
|
all: ${PATTERNS} |
for i in ${PATTERNS}; do \ |
/yifive/trunk/caravel_yifive/verilog/rtl/digital_core/src/glbl_cfg.sv
0,0 → 1,1056
////////////////////////////////////////////////////////////////////// |
//// //// |
//// Global confg register //// |
//// //// |
//// This file is part of the YIFive cores project //// |
//// http://www.opencores.org/cores/yifive/ //// |
//// //// |
//// Description //// |
//// This block generate all the global config and status //// |
//// //// |
//// To Do: //// |
//// nothing //// |
//// //// |
//// Author(s): //// |
//// - Dinesh Annayya, dinesha@opencores.org //// |
//// //// |
//// Revision : //// |
//// 0.1 - 08 June 2021 Dinesh A //// |
//// Initial version //// |
//// //// |
////////////////////////////////////////////////////////////////////// |
//// //// |
//// Copyright (C) 2000 Authors and OPENCORES.ORG //// |
//// //// |
//// 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 glbl_cfg ( |
|
input logic mclk, |
input logic reset_n, |
output logic [31:0] device_idcode, |
|
// Reg Bus Interface Signal |
input logic reg_cs, |
input logic reg_wr, |
input logic [3:0] reg_addr, |
input logic [31:0] reg_wdata, |
input logic [3:0] reg_be, |
|
// Outputs |
output logic [31:0] reg_rdata, |
output logic reg_ack, |
|
// SDRAM Clock |
|
output logic sdram_clk, |
|
// reset |
output logic cpu_rst_n, |
output logic spi_rst_n, |
output logic sdram_rst_n, |
|
// Risc configuration |
output logic [31:0] fuse_mhartid, |
output logic [15:0] irq_lines, |
output logic soft_irq, |
|
// SDRAM Config |
input logic sdr_init_done , // Indicate SDRAM Initialisation Done |
output logic [1:0] cfg_sdr_width , // 2'b00 - 32 Bit SDR, 2'b01 - 16 Bit SDR, 2'b1x - 8 Bit |
output logic [1:0] cfg_colbits , // 2'b00 - 8 Bit column address, |
output logic [3:0] cfg_sdr_tras_d , // Active to precharge delay |
output logic [3:0] cfg_sdr_trp_d , // Precharge to active delay |
output logic [3:0] cfg_sdr_trcd_d , // Active to R/W delay |
output logic cfg_sdr_en , // Enable SDRAM controller |
output logic [1:0] cfg_req_depth , // Maximum Request accepted by SDRAM controller |
output logic [12:0] cfg_sdr_mode_reg , |
output logic [2:0] cfg_sdr_cas , // SDRAM CAS Latency |
output logic [3:0] cfg_sdr_trcar_d , // Auto-refresh period |
output logic [3:0] cfg_sdr_twr_d , // Write recovery delay |
output logic [11:0] cfg_sdr_rfsh , |
output logic [2:0] cfg_sdr_rfmax |
|
|
); |
|
|
|
//----------------------------------------------------------------------- |
// Internal Wire Declarations |
//----------------------------------------------------------------------- |
|
logic sw_rd_en; |
logic sw_wr_en; |
logic [3:0] sw_addr ; // addressing 16 registers |
logic [3:0] wr_be ; |
logic [31:0] sw_reg_wdata; |
|
logic reg_cs_l ; |
logic reg_cs_2l ; |
logic cfg_sdram_clk_div; |
|
|
logic [31:0] reg_0; // Software_Reg_0 |
logic [31:0] reg_1; // Software-Reg_1 |
logic [31:0] reg_2; // Software-Reg_2 |
logic [31:0] reg_3; // Software-Reg_3 |
logic [31:0] reg_4; // Software-Reg_4 |
logic [31:0] reg_5; // Software-Reg_5 |
logic [31:0] reg_6; // Software-Reg_6 |
logic [31:0] reg_7; // Software-Reg_7 |
logic [31:0] reg_8; // Software-Reg_8 |
logic [31:0] reg_9; // Software-Reg_9 |
logic [31:0] reg_10; // Software-Reg_10 |
logic [31:0] reg_11; // Software-Reg_11 |
logic [31:0] reg_12; // Software-Reg_12 |
logic [31:0] reg_13; // Software-Reg_13 |
logic [31:0] reg_14; // Software-Reg_14 |
logic [31:0] reg_15; // Software-Reg_15 |
logic [31:0] reg_out; |
|
//----------------------------------------------------------------------- |
// Main code starts here |
//----------------------------------------------------------------------- |
|
//----------------------------------------------------------------------- |
// To avoid interface timing, all the content are registered |
//----------------------------------------------------------------------- |
always @ (posedge mclk or negedge reset_n) |
begin |
if (reset_n == 1'b0) |
begin |
sw_addr <= '0; |
sw_rd_en <= '0; |
sw_wr_en <= '0; |
sw_reg_wdata <= '0; |
wr_be <= '0; |
reg_cs_l <= '0; |
reg_cs_2l <= '0; |
end else begin |
sw_addr <= reg_addr [3:0]; |
sw_rd_en <= reg_cs & !reg_wr; |
sw_wr_en <= reg_cs & reg_wr; |
sw_reg_wdata <= reg_wdata; |
wr_be <= reg_be; |
reg_cs_l <= reg_cs; |
reg_cs_2l <= reg_cs_l; |
end |
end |
|
|
//----------------------------------------------------------------------- |
// Read path mux |
//----------------------------------------------------------------------- |
|
always @ (posedge mclk or negedge reset_n) |
begin : preg_out_Seq |
if (reset_n == 1'b0) begin |
reg_rdata [31:0] <= 32'h0000_0000; |
reg_ack <= 1'b0; |
end else if (sw_rd_en && !reg_ack && !reg_cs_2l) begin |
reg_rdata [31:0] <= reg_out [31:0]; |
reg_ack <= 1'b1; |
end else if (sw_wr_en && !reg_ack && !reg_cs_2l) begin |
reg_ack <= 1'b1; |
end else begin |
reg_ack <= 1'b0; |
end |
end |
|
|
//----------------------------------------------------------------------- |
// register read enable and write enable decoding logic |
//----------------------------------------------------------------------- |
wire sw_wr_en_0 = sw_wr_en & (sw_addr == 4'h0); |
wire sw_rd_en_0 = sw_rd_en & (sw_addr == 4'h0); |
wire sw_wr_en_1 = sw_wr_en & (sw_addr == 4'h1); |
wire sw_rd_en_1 = sw_rd_en & (sw_addr == 4'h1); |
wire sw_wr_en_2 = sw_wr_en & (sw_addr == 4'h2); |
wire sw_rd_en_2 = sw_rd_en & (sw_addr == 4'h2); |
wire sw_wr_en_3 = sw_wr_en & (sw_addr == 4'h3); |
wire sw_rd_en_3 = sw_rd_en & (sw_addr == 4'h3); |
wire sw_wr_en_4 = sw_wr_en & (sw_addr == 4'h4); |
wire sw_rd_en_4 = sw_rd_en & (sw_addr == 4'h4); |
wire sw_wr_en_5 = sw_wr_en & (sw_addr == 4'h5); |
wire sw_rd_en_5 = sw_rd_en & (sw_addr == 4'h5); |
wire sw_wr_en_6 = sw_wr_en & (sw_addr == 4'h6); |
wire sw_rd_en_6 = sw_rd_en & (sw_addr == 4'h6); |
wire sw_wr_en_7 = sw_wr_en & (sw_addr == 4'h7); |
wire sw_rd_en_7 = sw_rd_en & (sw_addr == 4'h7); |
wire sw_wr_en_8 = sw_wr_en & (sw_addr == 4'h8); |
wire sw_rd_en_8 = sw_rd_en & (sw_addr == 4'h8); |
wire sw_wr_en_9 = sw_wr_en & (sw_addr == 4'h9); |
wire sw_rd_en_9 = sw_rd_en & (sw_addr == 4'h9); |
wire sw_wr_en_10 = sw_wr_en & (sw_addr == 4'hA); |
wire sw_rd_en_10 = sw_rd_en & (sw_addr == 4'hA); |
wire sw_wr_en_11 = sw_wr_en & (sw_addr == 4'hB); |
wire sw_rd_en_11 = sw_rd_en & (sw_addr == 4'hB); |
wire sw_wr_en_12 = sw_wr_en & (sw_addr == 4'hC); |
wire sw_rd_en_12 = sw_rd_en & (sw_addr == 4'hC); |
wire sw_wr_en_13 = sw_wr_en & (sw_addr == 4'hD); |
wire sw_rd_en_13 = sw_rd_en & (sw_addr == 4'hD); |
wire sw_wr_en_14 = sw_wr_en & (sw_addr == 4'hE); |
wire sw_rd_en_14 = sw_rd_en & (sw_addr == 4'hE); |
wire sw_wr_en_15 = sw_wr_en & (sw_addr == 4'hF); |
wire sw_rd_en_15 = sw_rd_en & (sw_addr == 4'hF); |
|
|
always @( *) |
begin : preg_sel_Com |
|
reg_out [31:0] = 32'd0; |
|
case (sw_addr [3:0]) |
4'b0000 : reg_out [31:0] = reg_0 [31:0]; |
4'b0001 : reg_out [31:0] = reg_1 [31:0]; |
4'b0010 : reg_out [31:0] = reg_2 [31:0]; |
4'b0011 : reg_out [31:0] = reg_3 [31:0]; |
4'b0100 : reg_out [31:0] = reg_4 [31:0]; |
4'b0101 : reg_out [31:0] = reg_5 [31:0]; |
4'b0110 : reg_out [31:0] = reg_6 [31:0]; |
4'b0111 : reg_out [31:0] = reg_7 [31:0]; |
4'b1000 : reg_out [31:0] = reg_8 [31:0]; |
4'b1001 : reg_out [31:0] = reg_9 [31:0]; |
4'b1010 : reg_out [31:0] = reg_10 [31:0]; |
4'b1011 : reg_out [31:0] = reg_11 [31:0]; |
4'b1100 : reg_out [31:0] = reg_12 [31:0]; |
4'b1101 : reg_out [31:0] = reg_13 [31:0]; |
4'b1110 : reg_out [31:0] = reg_14 [31:0]; |
4'b1111 : reg_out [31:0] = reg_15 [31:0]; |
endcase |
end |
|
|
|
//----------------------------------------------------------------------- |
// Individual register assignments |
//----------------------------------------------------------------------- |
//----------------------------------------------------------------------- |
// reg-0 |
// ----------------------------------------------------------------- |
|
assign cpu_rst_n = reg_0[0]; |
assign spi_rst_n = reg_0[1]; |
assign sdram_rst_n = reg_0[2]; |
assign cfg_sdram_clk_div = reg_0[3]; |
|
|
|
generic_register #(8,0 ) u_reg0_be0 ( |
.we ({8{sw_wr_en_0 & |
wr_be[0] }} ), |
.data_in (sw_reg_wdata[7:0] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_0[7:0] ) |
); |
|
generic_register #(8,0 ) u_reg0_be1 ( |
.we ({8{sw_wr_en_0 & |
wr_be[1] }} ), |
.data_in (sw_reg_wdata[15:8] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_0[15:8] ) |
); |
generic_register #(8,0 ) u_reg0_be2 ( |
.we ({8{sw_wr_en_0 & |
wr_be[2] }} ), |
.data_in (sw_reg_wdata[23:16] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_0[23:16] ) |
); |
|
generic_register #(8,0 ) u_reg0_be3 ( |
.we ({8{sw_wr_en_0 & |
wr_be[3] }} ), |
.data_in (sw_reg_wdata[31:24] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_0[31:24] ) |
); |
|
|
|
//----------------------------------------------------------------------- |
// reg-1, reset value = 32'hA55A_A55A |
// ----------------------------------------------------------------- |
assign device_idcode = reg_1[31:0]; |
|
generic_register #(.WD(8),.RESET_DEFAULT(8'h5A)) u_reg1_be0 ( |
.we ({8{sw_wr_en_1 & |
wr_be[0] }} ), |
.data_in (sw_reg_wdata[7:0] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_1[7:0] ) |
); |
|
generic_register #(.WD(8),.RESET_DEFAULT(8'hA5) ) u_reg1_be1 ( |
.we ({8{sw_wr_en_1 & |
wr_be[1] }} ), |
.data_in (sw_reg_wdata[15:8] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_1[15:8] ) |
); |
generic_register #(.WD(8),.RESET_DEFAULT(8'h5A) ) u_reg1_be2 ( |
.we ({8{sw_wr_en_1 & |
wr_be[2] }} ), |
.data_in (sw_reg_wdata[23:16] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_1[23:16] ) |
); |
|
generic_register #(.WD(8),.RESET_DEFAULT(8'hA5) ) u_reg1_be3 ( |
.we ({8{sw_wr_en_1 & |
wr_be[3] }} ), |
.data_in (sw_reg_wdata[31:24] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_1[31:24] ) |
); |
|
//----------------------------------------------------------------------- |
// reg-2, reset value = 32'hAABBCCDD |
//----------------------------------------------------------------- |
assign fuse_mhartid = reg_1[31:0]; |
|
generic_register #(.WD(8),.RESET_DEFAULT(8'hDD) ) u_reg2_be0 ( |
.we ({8{sw_wr_en_2 & |
wr_be[0] }} ), |
.data_in (sw_reg_wdata[7:0] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_2[7:0] ) |
); |
|
generic_register #(.WD(8),.RESET_DEFAULT(8'hCC) ) u_reg2_be1 ( |
.we ({8{sw_wr_en_2 & |
wr_be[1] }} ), |
.data_in (sw_reg_wdata[15:8] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_2[15:8] ) |
); |
generic_register #(.WD(8),.RESET_DEFAULT(8'hBB) ) u_reg2_be2 ( |
.we ({8{sw_wr_en_2 & |
wr_be[2] }} ), |
.data_in (sw_reg_wdata[23:16] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_2[23:16] ) |
); |
|
generic_register #(.WD(8),.RESET_DEFAULT(8'hAA) ) u_reg2_be3 ( |
.we ({8{sw_wr_en_2 & |
wr_be[3] }} ), |
.data_in (sw_reg_wdata[31:24] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_2[31:24] ) |
); |
|
//----------------------------------------------------------------------- |
// reg-3 |
//----------------------------------------------------------------- |
assign irq_lines = reg_3[15:0]; |
assign soft_irq = reg_3[16]; |
|
generic_register #(8,0 ) u_reg3_be0 ( |
.we ({8{sw_wr_en_3 & |
wr_be[0] }} ), |
.data_in (sw_reg_wdata[7:0] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_3[7:0] ) |
); |
|
generic_register #(8,0 ) u_reg3_be1 ( |
.we ({8{sw_wr_en_3 & |
wr_be[1] }} ), |
.data_in (sw_reg_wdata[15:8] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_3[15:8] ) |
); |
generic_register #(1,0 ) u_reg3_be2 ( |
.we ({1{sw_wr_en_3 & |
wr_be[2] }} ), |
.data_in (sw_reg_wdata[16] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_3[16] ) |
); |
|
assign reg_3[31:17] = '0; |
|
|
//----------------------------------------------------------------------- |
// reg-4 |
// recommended Default value: |
// 1'b1,3'h3,2'h3,4'h1,4'h7',4'h2,4'h2,4'h4,2'b00,2'b10 = 32'h2F17_2242 |
//----------------------------------------------------------------- |
assign cfg_sdr_width = reg_4[1:0] ; // 2'b10 // 2'b00 - 32 Bit SDR, 2'b01 - 16 Bit SDR, 2'b1x - 8 Bit |
assign cfg_colbits = reg_4[3:2] ; // 2'b00 // 8 Bit column address, |
assign cfg_sdr_tras_d = reg_4[7:4] ; // 4'h4 // Active to precharge delay |
assign cfg_sdr_trp_d = reg_4[11:8]; // 4'h2 // Precharge to active delay |
assign cfg_sdr_trcd_d = reg_4[15:12]; // 4'h2 // Active to R/W delay |
assign cfg_sdr_trcar_d = reg_4[19:16]; // 4'h7 // Auto-refresh period |
assign cfg_sdr_twr_d = reg_4[23:20]; // 4'h1 // Write recovery delay |
assign cfg_req_depth = reg_4[25:24]; // 2'h3 // Maximum Request accepted by SDRAM controller |
assign cfg_sdr_cas = reg_4[28:26]; // 3'h3 // SDRAM CAS Latency |
assign cfg_sdr_en = reg_4[29] ; // 1'b1 // Enable SDRAM controller |
assign reg_4[30] = sdr_init_done ; // Indicate SDRAM Initialisation Done |
assign reg_4[31] = 1'b0; |
|
|
generic_register #(8,0 ) u_reg4_be0 ( |
.we ({8{sw_wr_en_4 & |
wr_be[0] }} ), |
.data_in (sw_reg_wdata[7:0] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_4[7:0] ) |
); |
|
generic_register #(8,0 ) u_reg4_be1 ( |
.we ({8{sw_wr_en_4 & |
wr_be[1] }} ), |
.data_in (sw_reg_wdata[15:8] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_4[15:8] ) |
); |
generic_register #(8,0 ) u_reg4_be2 ( |
.we ({8{sw_wr_en_4 & |
wr_be[2] }} ), |
.data_in (sw_reg_wdata[23:16] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_4[23:16] ) |
); |
|
generic_register #(6,0 ) u_reg4_be3 ( |
.we ({6{sw_wr_en_4 & |
wr_be[3] }} ), |
.data_in (sw_reg_wdata[29:24] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_4[29:24] ) |
); |
//----------------------------------------------------------------------- |
// reg-5, recomended default value {12'h100,13'h33,3'h6} = 32'h100_019E |
//----------------------------------------------------------------- |
assign cfg_sdr_rfmax = reg_5[2:0] ; // 3'h6 |
assign cfg_sdr_mode_reg = reg_5[15:3] ; // 13'h033 |
assign cfg_sdr_rfsh = reg_5[27:16]; // 12'h100 |
|
generic_register #(8,0 ) u_reg5_be0 ( |
.we ({8{sw_wr_en_5 & |
wr_be[0] }} ), |
.data_in (sw_reg_wdata[7:0] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_5[7:0] ) |
); |
|
generic_register #(8,0 ) u_reg5_be1 ( |
.we ({8{sw_wr_en_5 & |
wr_be[1] }} ), |
.data_in (sw_reg_wdata[15:8] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_5[15:8] ) |
); |
generic_register #(8,0 ) u_reg5_be2 ( |
.we ({8{sw_wr_en_5 & |
wr_be[2] }} ), |
.data_in (sw_reg_wdata[23:16] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_5[23:16] ) |
); |
|
generic_register #(8,0 ) u_reg5_be3 ( |
.we ({8{sw_wr_en_5 & |
wr_be[3] }} ), |
.data_in (sw_reg_wdata[31:24] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_5[31:24] ) |
); |
|
|
//----------------------------------------------------------------- |
// reg- 6 |
//----------------------------------------------------------------- |
|
generic_register #(8,0 ) u_reg6_be0 ( |
.we ({8{sw_wr_en_6 & |
wr_be[0] }} ), |
.data_in (sw_reg_wdata[7:0] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_6[7:0] ) |
); |
|
generic_register #(8,0 ) u_reg6_be1 ( |
.we ({8{sw_wr_en_6 & |
wr_be[1] }} ), |
.data_in (sw_reg_wdata[15:8] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_6[15:8] ) |
); |
generic_register #(8,0 ) u_reg6_be2 ( |
.we ({8{sw_wr_en_6 & |
wr_be[2] }} ), |
.data_in (sw_reg_wdata[23:16] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_6[23:16] ) |
); |
|
generic_register #(8,0 ) u_reg6_be3 ( |
.we ({8{sw_wr_en_6 & |
wr_be[3] }} ), |
.data_in (sw_reg_wdata[31:24] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_6[31:24] ) |
); |
|
|
//----------------------------------------------------------------- |
// reg- 7 |
//----------------------------------------------------------------- |
|
generic_register #(8,0 ) u_reg7_be0 ( |
.we ({8{sw_wr_en_7 & |
wr_be[0] }} ), |
.data_in (sw_reg_wdata[7:0] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_7[7:0] ) |
); |
|
generic_register #(8,0 ) u_reg7_be1 ( |
.we ({8{sw_wr_en_7 & |
wr_be[1] }} ), |
.data_in (sw_reg_wdata[15:8] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_7[15:8] ) |
); |
generic_register #(8,0 ) u_reg7_be2 ( |
.we ({8{sw_wr_en_7 & |
wr_be[2] }} ), |
.data_in (sw_reg_wdata[23:16] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_7[23:16] ) |
); |
|
generic_register #(8,0 ) u_reg7_be3 ( |
.we ({8{sw_wr_en_7 & |
wr_be[3] }} ), |
.data_in (sw_reg_wdata[31:24] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_7[31:24] ) |
); |
|
|
//----------------------------------------------------------------- |
// reg- 8 |
//----------------------------------------------------------------- |
|
generic_register #(8,0 ) u_reg8_be0 ( |
.we ({8{sw_wr_en_8 & |
wr_be[0] }} ), |
.data_in (sw_reg_wdata[7:0] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_8[7:0] ) |
); |
|
generic_register #(8,0 ) u_reg8_be1 ( |
.we ({8{sw_wr_en_8 & |
wr_be[1] }} ), |
.data_in (sw_reg_wdata[15:8] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_8[15:8] ) |
); |
generic_register #(8,0 ) u_reg8_be2 ( |
.we ({8{sw_wr_en_8 & |
wr_be[2] }} ), |
.data_in (sw_reg_wdata[23:16] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_8[23:16] ) |
); |
|
generic_register #(8,0 ) u_reg8_be3 ( |
.we ({8{sw_wr_en_8 & |
wr_be[3] }} ), |
.data_in (sw_reg_wdata[31:24] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_8[31:24] ) |
); |
|
|
//----------------------------------------------------------------- |
// reg- 9 |
//----------------------------------------------------------------- |
|
generic_register #(8,0 ) u_reg9_be0 ( |
.we ({8{sw_wr_en_9 & |
wr_be[0] }} ), |
.data_in (sw_reg_wdata[7:0] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_9[7:0] ) |
); |
|
generic_register #(8,0 ) u_reg9_be1 ( |
.we ({8{sw_wr_en_9 & |
wr_be[1] }} ), |
.data_in (sw_reg_wdata[15:8] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_9[15:8] ) |
); |
generic_register #(8,0 ) u_reg9_be2 ( |
.we ({8{sw_wr_en_9 & |
wr_be[2] }} ), |
.data_in (sw_reg_wdata[23:16] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_9[23:16] ) |
); |
|
generic_register #(8,0 ) u_reg9_be3 ( |
.we ({8{sw_wr_en_9 & |
wr_be[3] }} ), |
.data_in (sw_reg_wdata[31:24] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_9[31:24] ) |
); |
|
|
//----------------------------------------------------------------- |
// reg- 10 |
//----------------------------------------------------------------- |
|
generic_register #(8,0 ) u_reg10_be0 ( |
.we ({8{sw_wr_en_10 & |
wr_be[0] }} ), |
.data_in (sw_reg_wdata[7:0] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_10[7:0] ) |
); |
|
generic_register #(8,0 ) u_reg10_be1 ( |
.we ({8{sw_wr_en_10 & |
wr_be[1] }} ), |
.data_in (sw_reg_wdata[15:8] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_10[15:8] ) |
); |
generic_register #(8,0 ) u_reg10_be2 ( |
.we ({8{sw_wr_en_10 & |
wr_be[2] }} ), |
.data_in (sw_reg_wdata[23:16] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_10[23:16] ) |
); |
|
generic_register #(8,0 ) u_reg10_be3 ( |
.we ({8{sw_wr_en_10 & |
wr_be[3] }} ), |
.data_in (sw_reg_wdata[31:24] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_10[31:24] ) |
); |
|
|
//----------------------------------------------------------------- |
// reg- 11 |
//----------------------------------------------------------------- |
|
generic_register #(8,0 ) u_reg11_be0 ( |
.we ({8{sw_wr_en_11 & |
wr_be[0] }} ), |
.data_in (sw_reg_wdata[7:0] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_11[7:0] ) |
); |
|
generic_register #(8,0 ) u_reg11_be1 ( |
.we ({8{sw_wr_en_11 & |
wr_be[1] }} ), |
.data_in (sw_reg_wdata[15:8] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_11[15:8] ) |
); |
generic_register #(8,0 ) u_reg11_be2 ( |
.we ({8{sw_wr_en_11 & |
wr_be[2] }} ), |
.data_in (sw_reg_wdata[23:16] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_11[23:16] ) |
); |
|
generic_register #(8,0 ) u_reg11_be3 ( |
.we ({8{sw_wr_en_11 & |
wr_be[3] }} ), |
.data_in (sw_reg_wdata[31:24] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_11[31:24] ) |
); |
|
|
//----------------------------------------------------------------- |
// reg- 12 |
//----------------------------------------------------------------- |
|
generic_register #(8,0 ) u_reg12_be0 ( |
.we ({8{sw_wr_en_12 & |
wr_be[0] }} ), |
.data_in (sw_reg_wdata[7:0] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_12[7:0] ) |
); |
|
generic_register #(8,0 ) u_reg12_be1 ( |
.we ({8{sw_wr_en_12 & |
wr_be[1] }} ), |
.data_in (sw_reg_wdata[15:8] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_12[15:8] ) |
); |
generic_register #(8,0 ) u_reg12_be2 ( |
.we ({8{sw_wr_en_12 & |
wr_be[2] }} ), |
.data_in (sw_reg_wdata[23:16] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_12[23:16] ) |
); |
|
generic_register #(8,0 ) u_reg12_be3 ( |
.we ({8{sw_wr_en_12 & |
wr_be[3] }} ), |
.data_in (sw_reg_wdata[31:24] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_12[31:24] ) |
); |
|
|
//----------------------------------------------------------------- |
// reg- 13 |
//----------------------------------------------------------------- |
|
generic_register #(8,0 ) u_reg13_be0 ( |
.we ({8{sw_wr_en_13 & |
wr_be[0] }} ), |
.data_in (sw_reg_wdata[7:0] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_13[7:0] ) |
); |
|
generic_register #(8,0 ) u_reg13_be1 ( |
.we ({8{sw_wr_en_13 & |
wr_be[1] }} ), |
.data_in (sw_reg_wdata[15:8] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_13[15:8] ) |
); |
generic_register #(8,0 ) u_reg13_be2 ( |
.we ({8{sw_wr_en_13 & |
wr_be[2] }} ), |
.data_in (sw_reg_wdata[23:16] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_13[23:16] ) |
); |
|
generic_register #(8,0 ) u_reg13_be3 ( |
.we ({8{sw_wr_en_13 & |
wr_be[3] }} ), |
.data_in (sw_reg_wdata[31:24] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_13[31:24] ) |
); |
|
|
//----------------------------------------------------------------- |
// reg- 14 |
//----------------------------------------------------------------- |
|
generic_register #(8,0 ) u_reg14_be0 ( |
.we ({8{sw_wr_en_14 & |
wr_be[0] }} ), |
.data_in (sw_reg_wdata[7:0] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_14[7:0] ) |
); |
|
generic_register #(8,0 ) u_reg14_be1 ( |
.we ({8{sw_wr_en_14 & |
wr_be[1] }} ), |
.data_in (sw_reg_wdata[15:8] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_14[15:8] ) |
); |
generic_register #(8,0 ) u_reg14_be2 ( |
.we ({8{sw_wr_en_14 & |
wr_be[2] }} ), |
.data_in (sw_reg_wdata[23:16] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_14[23:16] ) |
); |
|
generic_register #(8,0 ) u_reg14_be3 ( |
.we ({8{sw_wr_en_14 & |
wr_be[3] }} ), |
.data_in (sw_reg_wdata[31:24] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_14[31:24] ) |
); |
|
|
//----------------------------------------------------------------- |
// reg- 15 |
//----------------------------------------------------------------- |
|
generic_register #(8,0 ) u_reg15_be0 ( |
.we ({8{sw_wr_en_15 & |
wr_be[0] }} ), |
.data_in (sw_reg_wdata[7:0] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_15[7:0] ) |
); |
|
generic_register #(8,0 ) u_reg15_be1 ( |
.we ({8{sw_wr_en_15 & |
wr_be[1] }} ), |
.data_in (sw_reg_wdata[15:8] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_15[15:8] ) |
); |
generic_register #(8,0 ) u_reg15_be2 ( |
.we ({8{sw_wr_en_15 & |
wr_be[2] }} ), |
.data_in (sw_reg_wdata[23:16] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_15[23:16] ) |
); |
|
generic_register #(8,0 ) u_reg15_be3 ( |
.we ({8{sw_wr_en_15 & |
wr_be[3] }} ), |
.data_in (sw_reg_wdata[31:24] ), |
.reset_n (reset_n ), |
.clk (mclk ), |
|
//List of Outs |
.data_out (reg_15[31:24] ) |
); |
|
|
|
|
//---------------------------------- |
// Generate SDRAM Div-2 Clock |
//---------------------------------- |
wire sdram_clk_div2; |
|
assign sdram_clk = (cfg_sdram_clk_div) ? sdram_clk_div2 : mclk; |
|
|
clk_ctl #(1) u_sdramclk ( |
// Outputs |
.clk_o (sdram_clk_div2), |
// Inputs |
.mclk (mclk), |
.reset_n (reset_n), |
.clk_div_ratio (2'b00) |
); |
|
|
|
endmodule |
/yifive/trunk/caravel_yifive/verilog/rtl/lib/clk_ctl.v
0,0 → 1,126
////////////////////////////////////////////////////////////////////// |
//// //// |
//// Tubo 8051 cores common library Module //// |
//// //// |
//// This file is part of the Turbo 8051 cores project //// |
//// http://www.opencores.org/cores/turbo8051/ //// |
//// //// |
//// Description //// |
//// Turbo 8051 definitions. //// |
//// //// |
//// To Do: //// |
//// nothing //// |
//// //// |
//// Author(s): //// |
//// - Dinesh Annayya, dinesha@opencores.org //// |
//// //// |
//// Revision : Mar 2, 2011 //// |
//// //// |
////////////////////////////////////////////////////////////////////// |
//// //// |
//// Copyright (C) 2000 Authors and OPENCORES.ORG //// |
//// //// |
//// 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: clk_ctl |
// |
// Description: Generic clock control logic , clk-out = mclk/(2+clk_div_ratio) |
// |
// |
// ################################################################# |
|
|
module clk_ctl ( |
// Outputs |
clk_o, |
// Inputs |
mclk, |
reset_n, |
clk_div_ratio |
); |
|
//--------------------------------- |
// CLOCK Default Divider value. |
// This value will be change from outside |
//--------------------------------- |
parameter WD = 'h1; |
|
//--------------------------------------------- |
// All the input to this block are declared here |
// -------------------------------------------- |
input mclk ;// |
input reset_n ;// primary reset signal |
input [WD:0] clk_div_ratio ;// primary clock divide ratio |
// output clock = selected clock / (div_ratio+1) |
|
//--------------------------------------------- |
// All the output to this block are declared here |
// -------------------------------------------- |
output clk_o ; // clock out |
|
|
|
//------------------------------------ |
// Clock Divide func is done here |
//------------------------------------ |
reg [WD-1:0] high_count ; // high level counter |
reg [WD-1:0] low_count ; // low level counter |
reg mclk_div ; // divided clock |
|
|
assign clk_o = mclk_div; |
|
always @ (posedge mclk or negedge reset_n) |
begin // { |
if(reset_n == 1'b0) |
begin |
high_count <= 'h0; |
low_count <= 'h0; |
mclk_div <= 'b0; |
end |
else |
begin |
if(high_count != 0) |
begin // { |
high_count <= high_count - 1; |
mclk_div <= 1'b1; |
end // } |
else if(low_count != 0) |
begin // { |
low_count <= low_count - 1; |
mclk_div <= 1'b0; |
end // } |
else |
begin // { |
high_count <= clk_div_ratio[WD:1] + clk_div_ratio[0]; |
low_count <= clk_div_ratio[WD:1] + 1; |
mclk_div <= ~mclk_div; |
end // } |
end // } |
end // } |
|
|
endmodule |
|
/yifive/trunk/caravel_yifive/verilog/rtl/lib/registers.v
0,0 → 1,277
////////////////////////////////////////////////////////////////////// |
//// //// |
//// Tubo 8051 cores common library Module //// |
//// //// |
//// This file is part of the Turbo 8051 cores project //// |
//// http://www.opencores.org/cores/turbo8051/ //// |
//// //// |
//// Description //// |
//// Turbo 8051 definitions. //// |
//// //// |
//// To Do: //// |
//// nothing //// |
//// //// |
//// Author(s): //// |
//// - Dinesh Annayya, dinesha@opencores.org //// |
//// //// |
//// Revision : Mar 2, 2011 //// |
//// //// |
////////////////////////////////////////////////////////////////////// |
//// //// |
//// Copyright (C) 2000 Authors and OPENCORES.ORG //// |
//// //// |
//// 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: bit register |
|
** description: infers a register, make it modular |
***********************************************************************/ |
module bit_register ( |
//inputs |
we, |
clk, |
reset_n, |
data_in, |
|
//outputs |
data_out |
); |
|
//--------------------------------- |
// Reset Default value |
//--------------------------------- |
parameter RESET_DEFAULT = 1'h0; |
|
input we; |
input clk; |
input reset_n; |
input data_in; |
output data_out; |
|
reg data_out; |
|
//infer the register |
always @(posedge clk or negedge reset_n) |
begin |
if (!reset_n) |
data_out <= RESET_DEFAULT; |
else if (we) |
data_out <= data_in; |
end // always @ (posedge clk or negedge reset_n) |
endmodule // register |
|
|
/********************************************************************* |
** module: req register. |
|
** description: This register is set by cpu writting 1 and reset by |
harward req = 1 |
|
Note: When there is a clash between cpu and hardware, cpu is given higher |
priority |
|
***********************************************************************/ |
module req_register ( |
//inputs |
clk, |
reset_n, |
cpu_we, |
cpu_req, |
hware_ack, |
|
//outputs |
data_out |
); |
|
//--------------------------------- |
// Reset Default value |
//--------------------------------- |
parameter RESET_DEFAULT = 1'h0; |
|
input clk ; |
input reset_n ; |
input cpu_we ; // cpu write enable |
input cpu_req ; // CPU Request |
input hware_ack; // Hardware Ack |
output data_out ; |
|
reg data_out; |
|
//infer the register |
always @(posedge clk or negedge reset_n) |
begin |
if (!reset_n) |
data_out <= RESET_DEFAULT; |
else if (cpu_we & cpu_req) // Set on CPU Request |
data_out <= 1'b1; |
else if (hware_ack) // Reset the flag on Hardware ack |
data_out <= 1'b0; |
end // always @ (posedge clk or negedge reset_n) |
endmodule // register |
|
|
/********************************************************************* |
** module: req register. |
|
** description: This register is cleared by cpu writting 1 and set by |
harward req = 1 |
|
Note: When there is a clash between cpu and hardware, |
hardware is given higher priority |
|
***********************************************************************/ |
module stat_register ( |
//inputs |
clk, |
reset_n, |
cpu_we, |
cpu_ack, |
hware_req, |
|
//outputs |
data_out |
); |
|
//--------------------------------- |
// Reset Default value |
//--------------------------------- |
parameter RESET_DEFAULT = 1'h0; |
|
input clk ; |
input reset_n ; |
input cpu_we ; // cpu write enable |
input cpu_ack ; // CPU Ack |
input hware_req; // Hardware Req |
output data_out ; |
|
reg data_out; |
|
//infer the register |
always @(posedge clk or negedge reset_n) |
begin |
if (!reset_n) |
data_out <= RESET_DEFAULT; |
else if (hware_req) // Set the flag on Hardware Req |
data_out <= 1'b1; |
else if (cpu_we & cpu_ack) // Clear on CPU Ack |
data_out <= 1'b0; |
end // always @ (posedge clk or negedge reset_n) |
endmodule // register |
|
|
|
|
|
/********************************************************************* |
** copyright message here. |
|
** module: generic register |
|
***********************************************************************/ |
module generic_register ( |
//List of Inputs |
we, |
data_in, |
reset_n, |
clk, |
|
//List of Outs |
data_out |
); |
|
parameter WD = 1; |
parameter RESET_DEFAULT = 0; |
input [WD-1:0] we; |
input [WD-1:0] data_in; |
input reset_n; |
input clk; |
output [WD-1:0] data_out; |
|
|
generate |
genvar i; |
for (i = 0; i < WD; i = i + 1) begin : gen_bit_reg |
bit_register #(RESET_DEFAULT[i]) u_bit_reg ( |
.we (we[i]), |
.clk (clk), |
.reset_n (reset_n), |
.data_in (data_in[i]), |
.data_out (data_out[i]) |
); |
end |
endgenerate |
|
|
endmodule |
|
|
/********************************************************************* |
** copyright message here. |
|
** module: generic register |
|
***********************************************************************/ |
module generic_intr_stat_reg ( |
//inputs |
clk, |
reset_n, |
reg_we, |
reg_din, |
hware_req, |
|
//outputs |
data_out |
); |
|
parameter WD = 1; |
parameter RESET_DEFAULT = 0; |
input [WD-1:0] reg_we; |
input [WD-1:0] reg_din; |
input [WD-1:0] hware_req; |
input reset_n; |
input clk; |
output [WD-1:0] data_out; |
|
|
generate |
genvar i; |
for (i = 0; i < WD; i = i + 1) begin : gen_bit_reg |
stat_register #(RESET_DEFAULT[i]) u_bit_reg ( |
//inputs |
. clk (clk ), |
. reset_n (reset_n ), |
. cpu_we (reg_we[i] ), |
. cpu_ack (reg_din[i] ), |
. hware_req (hware_req[i] ), |
|
//outputs |
. data_out (data_out[i] ) |
); |
|
end |
endgenerate |
|
|
endmodule |
yifive/trunk/caravel_yifive/verilog/rtl/lib/registers.v
Property changes :
Added: svn:executable
## -0,0 +1 ##
+*
\ No newline at end of property
Index: yifive/trunk/caravel_yifive/verilog/rtl/syntacore/scr1/sim/tests/common/LICENSE
===================================================================
--- yifive/trunk/caravel_yifive/verilog/rtl/syntacore/scr1/sim/tests/common/LICENSE (nonexistent)
+++ yifive/trunk/caravel_yifive/verilog/rtl/syntacore/scr1/sim/tests/common/LICENSE (revision 22)
@@ -0,0 +1,24 @@
+Copyright (c) 2012-2015, The Regents of the University of California (Regents).
+All Rights Reserved.
+
+Redistribution and use in source and binary forms, with or without
+modification, are permitted provided that the following conditions are met:
+1. Redistributions of source code must retain the above copyright
+ notice, this list of conditions and the following disclaimer.
+2. Redistributions in binary form must reproduce the above copyright
+ notice, this list of conditions and the following disclaimer in the
+ documentation and/or other materials provided with the distribution.
+3. Neither the name of the Regents nor the
+ names of its contributors may be used to endorse or promote products
+ derived from this software without specific prior written permission.
+
+IN NO EVENT SHALL REGENTS BE LIABLE TO ANY PARTY FOR DIRECT, INDIRECT,
+SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES, INCLUDING LOST PROFITS, ARISING
+OUT OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF REGENTS HAS
+BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+
+REGENTS SPECIFICALLY DISCLAIMS ANY WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
+THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+PURPOSE. THE SOFTWARE AND ACCOMPANYING DOCUMENTATION, IF ANY, PROVIDED
+HEREUNDER IS PROVIDED "AS IS". REGENTS HAS NO OBLIGATION TO PROVIDE
+MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.
Index: yifive/trunk/caravel_yifive/verilog/rtl/syntacore/scr1/sim/tests/common/common.mk
===================================================================
--- yifive/trunk/caravel_yifive/verilog/rtl/syntacore/scr1/sim/tests/common/common.mk (nonexistent)
+++ yifive/trunk/caravel_yifive/verilog/rtl/syntacore/scr1/sim/tests/common/common.mk (revision 22)
@@ -0,0 +1,44 @@
+ADD_ASM_MACRO ?= -D__ASSEMBLY__=1
+
+FLAGS = -O2 -funroll-loops -fpeel-loops -fgcse-sm -fgcse-las $(ADD_FLAGS)
+FLAGS_STR = "$(FLAGS)"
+
+CFLAGS_COMMON = -static -std=gnu99 -fno-common -fno-builtin-printf -DTCM=$(TCM)
+CFLAGS_ARCH = -Wa,-march=rv32$(ARCH) -march=rv32$(ARCH) -mabi=$(ABI)
+
+CFLAGS := $(FLAGS) $(EXT_CFLAGS) \
+$(CFLAGS_COMMON) \
+$(CFLAGS_ARCH) \
+-DFLAGS_STR=\"$(FLAGS_STR)\" \
+$(ADD_CFLAGS)
+
+LDFLAGS ?= -nostartfiles -nostdlib -lc -lgcc -march=rv32$(ARCH) -mabi=$(ABI)
+
+ifeq (,$(findstring 0,$(TCM)))
+ld_script ?= $(inc_dir)/link_tcm.ld
+asm_src ?= crt_tcm.S
+else
+ld_script ?= $(inc_dir)/link.ld
+asm_src ?= crt.S
+endif
+
+VPATH += $(src_dir) $(inc_dir) $(ADD_VPATH)
+incs += -I$(src_dir) -I$(inc_dir) $(ADD_incs)
+
+c_objs := $(addprefix $(bld_dir)/,$(patsubst %.c, %.o, $(c_src)))
+asm_objs := $(addprefix $(bld_dir)/,$(patsubst %.S, %.o, $(asm_src)))
+
+$(bld_dir)/%.o: %.S
+ $(RISCV_GCC) $(CFLAGS) $(ADD_ASM_MACRO) -c $(incs) $< -o $@
+
+$(bld_dir)/%.o: %.c
+ $(RISCV_GCC) $(CFLAGS) -c $(incs) $< -o $@
+
+$(bld_dir)/%.elf: $(ld_script) $(c_objs) $(asm_objs)
+ $(RISCV_GCC) -o $@ -T $^ $(LDFLAGS)
+
+$(bld_dir)/%.hex: $(bld_dir)/%.elf
+ $(RISCV_OBJCOPY) $^ $@
+
+$(bld_dir)/%.dump: $(bld_dir)/%.elf
+ $(RISCV_OBJDUMP) $^ > $@
\ No newline at end of file
Index: yifive/trunk/caravel_yifive/verilog/rtl/syntacore/scr1/sim/tests/common/crt.S
===================================================================
--- yifive/trunk/caravel_yifive/verilog/rtl/syntacore/scr1/sim/tests/common/crt.S (nonexistent)
+++ yifive/trunk/caravel_yifive/verilog/rtl/syntacore/scr1/sim/tests/common/crt.S (revision 22)
@@ -0,0 +1,146 @@
+/// Copyright by Syntacore LLC © 2016, 2017. See LICENSE for details
+/// @file
+///
+
+#include "riscv_csr_encoding.h"
+#include "sc_test.h"
+
+# define LREG lw
+# define SREG sw
+# define REGBYTES 4
+
+ .globl _start
+ .globl main
+ .globl trap_entry
+ .globl handle_trap
+ .globl sc_exit
+ .weak trap_entry, handle_trap
+
+ .text
+ .org (64*3)
+ .balign 64
+machine_trap_entry:
+ j trap_entry
+
+ .balign 64
+
+_start:
+#ifndef __RVE_EXT
+ zero_int_regs 1, 31
+#else
+ zero_int_regs 1, 15
+#endif
+ # Global pointer init
+ .option push
+ .option norelax
+ la gp, __global_pointer$
+ .option pop
+ # clear bss
+ la a1, __BSS_START__
+ la a2, __BSS_END__
+ j 4f
+3: sw zero, 0(a1)
+ add a1, a1, 4
+4: bne a1, a2, 3b
+ la sp, __C_STACK_TOP__
+
+ // Timer init
+ li t0, mtime_ctrl
+ li t1, (1 << SCR1_MTIME_CTRL_EN) // enable, use internal clock
+ sw t1, (t0)
+ li t0, mtime_div
+ li t1, (100-1) // divide by 100
+ sw t1, (t0)
+ li t0, mtimecmp
+ li t1, -1
+ sw t1, (t0) // max value for mtimecmp
+ sw t1, 4(t0)
+
+ li a0, 0
+ li a1, 0
+ jal main
+ j sc_exit
+
+trap_entry:
+ addi sp, sp, -272
+
+ SREG x1, 1*REGBYTES(sp)
+ SREG x2, 2*REGBYTES(sp)
+ SREG x3, 3*REGBYTES(sp)
+ SREG x4, 4*REGBYTES(sp)
+ SREG x5, 5*REGBYTES(sp)
+ SREG x6, 6*REGBYTES(sp)
+ SREG x7, 7*REGBYTES(sp)
+ SREG x8, 8*REGBYTES(sp)
+ SREG x9, 9*REGBYTES(sp)
+ SREG x10, 10*REGBYTES(sp)
+ SREG x11, 11*REGBYTES(sp)
+ SREG x12, 12*REGBYTES(sp)
+ SREG x13, 13*REGBYTES(sp)
+ SREG x14, 14*REGBYTES(sp)
+ SREG x15, 15*REGBYTES(sp)
+#ifndef __RVE_EXT
+ SREG x16, 16*REGBYTES(sp)
+ SREG x17, 17*REGBYTES(sp)
+ SREG x18, 18*REGBYTES(sp)
+ SREG x19, 19*REGBYTES(sp)
+ SREG x20, 20*REGBYTES(sp)
+ SREG x21, 21*REGBYTES(sp)
+ SREG x22, 22*REGBYTES(sp)
+ SREG x23, 23*REGBYTES(sp)
+ SREG x24, 24*REGBYTES(sp)
+ SREG x25, 25*REGBYTES(sp)
+ SREG x26, 26*REGBYTES(sp)
+ SREG x27, 27*REGBYTES(sp)
+ SREG x28, 28*REGBYTES(sp)
+ SREG x29, 29*REGBYTES(sp)
+ SREG x30, 30*REGBYTES(sp)
+ SREG x31, 31*REGBYTES(sp)
+#endif // __RVE_EXT
+
+ csrr a0, mcause
+ csrr a1, mepc
+ mv a2, sp
+ jal handle_trap
+
+ LREG x1, 1*REGBYTES(sp)
+ LREG x2, 2*REGBYTES(sp)
+ LREG x3, 3*REGBYTES(sp)
+ LREG x4, 4*REGBYTES(sp)
+ LREG x5, 5*REGBYTES(sp)
+ LREG x6, 6*REGBYTES(sp)
+ LREG x7, 7*REGBYTES(sp)
+ LREG x8, 8*REGBYTES(sp)
+ LREG x9, 9*REGBYTES(sp)
+ LREG x10, 10*REGBYTES(sp)
+ LREG x11, 11*REGBYTES(sp)
+ LREG x12, 12*REGBYTES(sp)
+ LREG x13, 13*REGBYTES(sp)
+ LREG x14, 14*REGBYTES(sp)
+ LREG x15, 15*REGBYTES(sp)
+#ifndef __RVE_EXT
+ LREG x16, 16*REGBYTES(sp)
+ LREG x17, 17*REGBYTES(sp)
+ LREG x18, 18*REGBYTES(sp)
+ LREG x19, 19*REGBYTES(sp)
+ LREG x20, 20*REGBYTES(sp)
+ LREG x21, 21*REGBYTES(sp)
+ LREG x22, 22*REGBYTES(sp)
+ LREG x23, 23*REGBYTES(sp)
+ LREG x24, 24*REGBYTES(sp)
+ LREG x25, 25*REGBYTES(sp)
+ LREG x26, 26*REGBYTES(sp)
+ LREG x27, 27*REGBYTES(sp)
+ LREG x28, 28*REGBYTES(sp)
+ LREG x29, 29*REGBYTES(sp)
+ LREG x30, 30*REGBYTES(sp)
+ LREG x31, 31*REGBYTES(sp)
+#endif // __RVE_EXT
+
+ addi sp, sp, 272
+ mret
+
+handle_trap:
+ j SIM_EXIT
+
+// end of crt.S
\ No newline at end of file
Index: yifive/trunk/caravel_yifive/verilog/rtl/syntacore/scr1/sim/tests/common/crt_tcm.S
===================================================================
--- yifive/trunk/caravel_yifive/verilog/rtl/syntacore/scr1/sim/tests/common/crt_tcm.S (nonexistent)
+++ yifive/trunk/caravel_yifive/verilog/rtl/syntacore/scr1/sim/tests/common/crt_tcm.S (revision 22)
@@ -0,0 +1,157 @@
+/// Copyright by Syntacore LLC © 2016, 2017. See LICENSE for details
+/// @file
+///
+
+#include "riscv_csr_encoding.h"
+#include "reloc.h"
+#include "sc_test.h"
+
+# define LREG lw
+# define SREG sw
+# define REGBYTES 4
+
+ .globl _start
+ .globl main
+ .globl trap_entry
+ .globl handle_trap
+ .globl sc_exit
+ .weak trap_entry, handle_trap
+
+ .section .text.init
+ .org (64*3)
+ .align 6;
+machine_trap_entry:
+ j trap_entry
+
+ .align 6
+_start:
+#ifndef __RVE_EXT
+ zero_int_regs 1, 31
+#else
+ zero_int_regs 1, 15
+#endif
+ # Global pointer init
+ .option push
+ .option norelax
+ la gp, __global_pointer$
+ .option pop
+
+ RELOC_PROC;
+
+ // init tdata
+ mv a1, tp
+ la a2, _tdata_end
+ j 6f
+5: lw a3, 0(a0)
+ sw a3, 0(a1)
+ add a0, a0, 4
+ add a1, a1, 4
+6: bne a0, a2, 5b
+ // clear tbss
+ j 8f
+7: sw zero, 0(a1)
+ add a1, a1, 4
+8: bne a1, a4, 7b
+
+ // Timer init
+ li t0, mtime_ctrl
+ li t1, (1 << SCR1_MTIME_CTRL_EN) // enable, use internal clock
+ sw t1, (t0)
+ li t0, mtime_div
+ li t1, (100-1) // divide by 100
+ sw t1, (t0)
+ li t0, mtimecmp
+ li t1, -1
+ sw t1, (t0) // max value for mtimecmp
+ sw t1, 4(t0)
+
+ li a0, 0
+ li a1, 0
+9: auipc t0, %pcrel_hi(main)
+ jalr t0, %pcrel_lo(9b)
+ la t0, sc_exit
+ //j sc_exit
+
+trap_entry:
+ addi sp, sp, -272
+
+ SREG x1, 1*REGBYTES(sp)
+ SREG x2, 2*REGBYTES(sp)
+ SREG x3, 3*REGBYTES(sp)
+ SREG x4, 4*REGBYTES(sp)
+ SREG x5, 5*REGBYTES(sp)
+ SREG x6, 6*REGBYTES(sp)
+ SREG x7, 7*REGBYTES(sp)
+ SREG x8, 8*REGBYTES(sp)
+ SREG x9, 9*REGBYTES(sp)
+ SREG x10, 10*REGBYTES(sp)
+ SREG x11, 11*REGBYTES(sp)
+ SREG x12, 12*REGBYTES(sp)
+ SREG x13, 13*REGBYTES(sp)
+ SREG x14, 14*REGBYTES(sp)
+ SREG x15, 15*REGBYTES(sp)
+#ifndef __RVE_EXT
+ SREG x16, 16*REGBYTES(sp)
+ SREG x17, 17*REGBYTES(sp)
+ SREG x18, 18*REGBYTES(sp)
+ SREG x19, 19*REGBYTES(sp)
+ SREG x20, 20*REGBYTES(sp)
+ SREG x21, 21*REGBYTES(sp)
+ SREG x22, 22*REGBYTES(sp)
+ SREG x23, 23*REGBYTES(sp)
+ SREG x24, 24*REGBYTES(sp)
+ SREG x25, 25*REGBYTES(sp)
+ SREG x26, 26*REGBYTES(sp)
+ SREG x27, 27*REGBYTES(sp)
+ SREG x28, 28*REGBYTES(sp)
+ SREG x29, 29*REGBYTES(sp)
+ SREG x30, 30*REGBYTES(sp)
+ SREG x31, 31*REGBYTES(sp)
+#endif // __RVE_EXT
+
+ csrr a0, mcause
+ csrr a1, mepc
+ mv a2, sp
+ jal handle_trap
+
+ LREG x1, 1*REGBYTES(sp)
+ LREG x2, 2*REGBYTES(sp)
+ LREG x3, 3*REGBYTES(sp)
+ LREG x4, 4*REGBYTES(sp)
+ LREG x5, 5*REGBYTES(sp)
+ LREG x6, 6*REGBYTES(sp)
+ LREG x7, 7*REGBYTES(sp)
+ LREG x8, 8*REGBYTES(sp)
+ LREG x9, 9*REGBYTES(sp)
+ LREG x10, 10*REGBYTES(sp)
+ LREG x11, 11*REGBYTES(sp)
+ LREG x12, 12*REGBYTES(sp)
+ LREG x13, 13*REGBYTES(sp)
+ LREG x14, 14*REGBYTES(sp)
+ LREG x15, 15*REGBYTES(sp)
+#ifndef __RVE_EXT
+ LREG x16, 16*REGBYTES(sp)
+ LREG x17, 17*REGBYTES(sp)
+ LREG x18, 18*REGBYTES(sp)
+ LREG x19, 19*REGBYTES(sp)
+ LREG x20, 20*REGBYTES(sp)
+ LREG x21, 21*REGBYTES(sp)
+ LREG x22, 22*REGBYTES(sp)
+ LREG x23, 23*REGBYTES(sp)
+ LREG x24, 24*REGBYTES(sp)
+ LREG x25, 25*REGBYTES(sp)
+ LREG x26, 26*REGBYTES(sp)
+ LREG x27, 27*REGBYTES(sp)
+ LREG x28, 28*REGBYTES(sp)
+ LREG x29, 29*REGBYTES(sp)
+ LREG x30, 30*REGBYTES(sp)
+ LREG x31, 31*REGBYTES(sp)
+#endif // __RVE_EXT
+
+ addi sp, sp, 272
+ mret
+
+handle_trap:
+ j SIM_EXIT
+
+// end of crt.S
\ No newline at end of file
Index: yifive/trunk/caravel_yifive/verilog/rtl/syntacore/scr1/sim/tests/common/csr.h
===================================================================
--- yifive/trunk/caravel_yifive/verilog/rtl/syntacore/scr1/sim/tests/common/csr.h (nonexistent)
+++ yifive/trunk/caravel_yifive/verilog/rtl/syntacore/scr1/sim/tests/common/csr.h (revision 22)
@@ -0,0 +1,113 @@
+/// Copyright by Syntacore LLC © 2016, 2017. See LICENSE for details
+/// @file
+/// Architecture specific CSR's defs and inlines
+
+#ifndef SCR_CSR_H
+#define SCR_CSR_H
+
+#include
+#include
+
+#define __xstringify(s) __stringify(s)
+#define __stringify(s) #s
+
+#ifdef read_csr
+#undef read_csr
+#endif
+
+#ifdef write_csr
+#undef write_csr
+#endif
+
+#ifdef swap_csr
+#undef swap_csr
+#endif
+
+#ifdef set_csr
+#undef set_csr
+#endif
+
+#ifdef clear_csr
+#undef clear_csr
+#endif
+
+#ifdef rdtime
+#undef rdtime
+#endif
+
+#ifdef rdcycle
+#undef rdcycle
+#endif
+
+#ifdef rdinstret
+#undef rdinstret
+#endif
+
+#define read_csr(reg) \
+ ({ \
+ unsigned long __tmp; \
+ asm volatile ("csrr %0, " __xstringify(reg) : "=r"(__tmp)); \
+ __tmp; \
+ })
+
+#define write_csr(reg, val) \
+ do { \
+ if (__builtin_constant_p(val) && (val) == 0) \
+ asm volatile ("csrw " __xstringify(reg) ", zero" ::); \
+ else if (__builtin_constant_p(val) && (unsigned long)(val) < 32) \
+ asm volatile ("csrw " __xstringify(reg) ", %0" :: "i"(val)); \
+ else \
+ asm volatile ("csrw " __xstringify(reg) ", %0" :: "r"(val)); \
+ } while (0)
+
+#define swap_csr(reg, val) \
+ ({ \
+ unsigned long __tmp; \
+ if (__builtin_constant_p(val) && (val) == 0) \
+ asm volatile ("csrrw %0, " __xstringify(reg) ", zero" : "=r"(__tmp) :); \
+ else if (__builtin_constant_p(val) && (unsigned long)(val) < 32) \
+ asm volatile ("csrrw %0, " __xstringify(reg) ", %1" : "=r"(__tmp) : "i"(val)); \
+ else \
+ asm volatile ("csrrw %0, " __xstringify(reg) ", %1" : "=r"(__tmp) : "r"(val)); \
+ __tmp; \
+ })
+
+#define set_csr(reg, bit) \
+ ({ \
+ unsigned long __tmp; \
+ if (__builtin_constant_p(bit) && (bit) < 32) \
+ asm volatile ("csrrs %0, " __xstringify(reg) ", %1" : "=r"(__tmp) : "i"(bit)); \
+ else \
+ asm volatile ("csrrs %0, " __xstringify(reg) ", %1" : "=r"(__tmp) : "r"(bit)); \
+ __tmp; \
+ })
+
+#define clear_csr(reg, bit) \
+ ({ \
+ unsigned long __tmp; \
+ if (__builtin_constant_p(bit) && (bit) < 32) \
+ asm volatile ("csrrc %0, " __xstringify(reg) ", %1" : "=r"(__tmp) : "i"(bit)); \
+ else \
+ asm volatile ("csrrc %0, " __xstringify(reg) ", %1" : "=r"(__tmp) : "r"(bit)); \
+ __tmp; \
+ })
+
+#define rdtime() read_csr(time)
+#define rdcycle() read_csr(cycle)
+#define rdinstret() read_csr(instret)
+
+static inline unsigned long __attribute__((const)) cpuid()
+{
+ unsigned long res;
+ asm ("csrr %0, mcpuid" : "=r"(res));
+ return res;
+}
+
+static inline unsigned long __attribute__((const)) impid()
+{
+ unsigned long res;
+ asm ("csrr %0, mimpid" : "=r"(res));
+ return res;
+}
+
+#endif // SCR_CSR_H
Index: yifive/trunk/caravel_yifive/verilog/rtl/syntacore/scr1/sim/tests/common/link.ld
===================================================================
--- yifive/trunk/caravel_yifive/verilog/rtl/syntacore/scr1/sim/tests/common/link.ld (nonexistent)
+++ yifive/trunk/caravel_yifive/verilog/rtl/syntacore/scr1/sim/tests/common/link.ld (revision 22)
@@ -0,0 +1,99 @@
+/*
+* Copyright by Syntacore LLC © 2016, 2017. See LICENSE for details
+* @file
+* @brief bare metal tests' linker script
+*/
+
+OUTPUT_ARCH( "riscv" )
+ENTRY(_start)
+
+MEMORY {
+ RAM (rwx) : ORIGIN = 0x0, LENGTH = 64K
+}
+
+STACK_SIZE = 1024;
+
+CL_SIZE = 32;
+
+SECTIONS {
+
+ /* code segment */
+ .text.init 0 : {
+ FILL(0);
+ . = 0x100 - 12;
+ SIM_EXIT = .;
+ LONG(0x13);
+ SIM_STOP = .;
+ LONG(0x6F);
+ LONG(-1);
+ . = 0x100;
+ PROVIDE(__TEXT_START__ = .);
+ *(.text.init)
+ } >RAM
+
+ .text : {
+ *crt.o(.text .text.*)
+ *(.text .text.*)
+ *(sc_test_section)
+ . = ALIGN(CL_SIZE);
+ PROVIDE(__TEXT_END__ = .);
+ } >RAM
+
+ /* data segment */
+ .data : {
+ *(.data .data.*)
+ . = ALIGN(CL_SIZE);
+ } >RAM
+
+ .sdata : {
+ __global_pointer$ = . + 0x800;
+ *(.srodata.cst16) *(.srodata.cst8) *(.srodata.cst4) *(.srodata.cst2) *(.srodata*)
+ *(.sdata .sdata.* .gnu.linkonce.s.*)
+ . = ALIGN(CL_SIZE);
+ } >RAM
+
+ /* thread-local data segment */
+ .tdata : {
+ PROVIDE(_tls_data = .);
+ PROVIDE(_tdata_begin = .);
+ *(.tdata .tdata.*)
+ PROVIDE(_tdata_end = .);
+ . = ALIGN(CL_SIZE);
+ } >RAM
+
+ .tbss : {
+ PROVIDE(__BSS_START__ = .);
+ *(.tbss .tbss.*)
+ . = ALIGN(CL_SIZE);
+ PROVIDE(_tbss_end = .);
+ } >RAM
+
+ /* bss segment */
+ .sbss : {
+ *(.sbss .sbss.* .gnu.linkonce.sb.*)
+ *(.scommon)
+ } >RAM
+
+ .bss : {
+ *(.bss .bss.*)
+ . = ALIGN(CL_SIZE);
+ PROVIDE(__BSS_END__ = .);
+ } >RAM
+
+ _end = .;
+ PROVIDE(__end = .);
+
+ /* End of uninitalized data segement */
+
+ .stack ORIGIN(RAM) + LENGTH(RAM) - STACK_SIZE : {
+ FILL(0);
+ PROVIDE(__STACK_START__ = .);
+ . += STACK_SIZE;
+ PROVIDE(__C_STACK_TOP__ = .);
+ PROVIDE(__STACK_END__ = .);
+ } >RAM
+
+ /DISCARD/ : {
+ *(.eh_frame .eh_frame.*)
+ }
+}
Index: yifive/trunk/caravel_yifive/verilog/rtl/syntacore/scr1/sim/tests/common/link_tcm.ld
===================================================================
--- yifive/trunk/caravel_yifive/verilog/rtl/syntacore/scr1/sim/tests/common/link_tcm.ld (nonexistent)
+++ yifive/trunk/caravel_yifive/verilog/rtl/syntacore/scr1/sim/tests/common/link_tcm.ld (revision 22)
@@ -0,0 +1,114 @@
+/*
+* Copyright by Syntacore LLC © 2016, 2017. See LICENSE for details
+* @file
+* @brief bare metal tests' linker script
+*/
+
+OUTPUT_ARCH( "riscv" )
+ENTRY(_start)
+
+MEMORY {
+ RAM (rwx) : ORIGIN = 0x0, LENGTH = 64K
+ TCM (rwx) : ORIGIN = 0x00480000, LENGTH = 64K
+}
+
+STACK_SIZE = 1024;
+
+CL_SIZE = 32;
+
+SECTIONS {
+
+ /* code segment */
+ .text.init ORIGIN(RAM) : {
+ FILL(0);
+ . = 0x100 - 12;
+ SIM_EXIT = .;
+ LONG(0x13);
+ SIM_STOP = .;
+ LONG(0x6F);
+ LONG(-1);
+ . = 0x100;
+ *crt_tcm.o(.text .text.*)
+ *(.text.init)
+ . = ALIGN(CL_SIZE);
+ } >RAM
+
+ __reloc_start = .;
+
+ .text : {
+ PROVIDE(__TEXT_START__ = .);
+ *(.text .text.*)
+ *(sc_test_section)
+ . = ALIGN(CL_SIZE);
+ PROVIDE(__TEXT_END__ = .);
+ } >TCM AT>RAM
+
+ .rodata ALIGN(CL_SIZE) : {
+ __global_pointer$ = . + 0x800;
+ *(.rodata) *(.rodata.*) *(.gnu.linkonce.r.*)
+ . = ALIGN(CL_SIZE);
+ LONG(0x13);
+ . = ALIGN(CL_SIZE);
+ } >TCM AT>RAM
+
+
+ /* data segment */
+ .data ALIGN(CL_SIZE) : {
+ PROVIDE(__DATA_START__ = .);
+ *(.data .data.*)
+ . = ALIGN(CL_SIZE);
+ } >TCM AT>RAM
+
+
+ .sdata ALIGN(CL_SIZE) : {
+ *(.sdata .sdata.* .gnu.linkonce.s.*)
+ . = ALIGN(CL_SIZE);
+ PROVIDE(__DATA_END__ = .);
+ } >TCM AT>RAM
+
+ /* thread-local data segment */
+ .tdata ALIGN(CL_SIZE) : {
+ PROVIDE(_tls_data = .);
+ PROVIDE(_tdata_begin = .);
+ *(.tdata .tdata.*)
+ PROVIDE(_tdata_end = .);
+ . = ALIGN(CL_SIZE);
+ } >TCM AT>RAM
+
+ .tbss ALIGN(CL_SIZE) : {
+ PROVIDE(_tbss_begin = .);
+ *(.tbss .tbss.*)
+ . = ALIGN(CL_SIZE);
+ PROVIDE(_tbss_end = .);
+ } >TCM AT>RAM
+
+ /* bss segment */
+ .sbss ALIGN(CL_SIZE) : {
+ PROVIDE(__BSS_START__ = .);
+ *(.sbss .sbss.* .gnu.linkonce.sb.*)
+ *(.scommon)
+ . = ALIGN(CL_SIZE);
+ } >TCM AT>RAM
+
+ .bss ALIGN(CL_SIZE) : {
+ *(.dynbss) *(.bss .bss.* .gnu.linkonce.b.*) *(COMMON)
+ . = ALIGN(CL_SIZE);
+ PROVIDE(__BSS_END__ = .);
+ } >TCM AT>RAM
+
+ _end = .;
+ PROVIDE(__end = .);
+
+ /* End of uninitalized data segement */
+
+ .stack ORIGIN(TCM) + LENGTH(TCM) - STACK_SIZE : {
+ PROVIDE(__STACK_START__ = .);
+ . += STACK_SIZE;
+ PROVIDE(__C_STACK_TOP__ = .);
+ PROVIDE(__STACK_END__ = .);
+ } >TCM
+
+ /DISCARD/ : {
+ *(.eh_frame .eh_frame.*)
+ }
+}
Index: yifive/trunk/caravel_yifive/verilog/rtl/syntacore/scr1/sim/tests/common/reloc.h
===================================================================
--- yifive/trunk/caravel_yifive/verilog/rtl/syntacore/scr1/sim/tests/common/reloc.h (nonexistent)
+++ yifive/trunk/caravel_yifive/verilog/rtl/syntacore/scr1/sim/tests/common/reloc.h (revision 22)
@@ -0,0 +1,37 @@
+#ifndef RELOC_H
+#define RELOC_H
+
+#if (TCM == 1)
+#define RELOC_PROC \
+ la a0, __reloc_start; \
+ la a1, __TEXT_START__; \
+ la a2, __DATA_END__; \
+ beq a0, a1, 21f; \
+ j 2f; \
+1: lw a3, 0(a0); \
+ sw a3, 0(a1); \
+ add a0, a0, 4; \
+ add a1, a1, 4; \
+2: bne a1, a2, 1b; \
+ /* clear bss */ \
+ la a2, __BSS_START__; \
+21: la a1, __BSS_END__; \
+ j 4f; \
+3: sw zero, 0(a2); \
+ add a2, a2, 4; \
+4: bne a1, a2, 3b; \
+ /* init stack */ \
+ la sp, __C_STACK_TOP__; \
+ /* init hart0 TLS */ \
+ la a0, _tdata_begin; \
+ la a2, _tbss_end; \
+ sub a1, a2, a0; \
+ la a4, __STACK_START__; \
+ sub tp, a4, a1;
+#else // #if TCM
+
+#define RELOC_PROC
+
+#endif // #else #if TCM
+
+#endif //
\ No newline at end of file
Index: yifive/trunk/caravel_yifive/verilog/rtl/syntacore/scr1/sim/tests/common/riscv_csr_encoding.h
===================================================================
--- yifive/trunk/caravel_yifive/verilog/rtl/syntacore/scr1/sim/tests/common/riscv_csr_encoding.h (nonexistent)
+++ yifive/trunk/caravel_yifive/verilog/rtl/syntacore/scr1/sim/tests/common/riscv_csr_encoding.h (revision 22)
@@ -0,0 +1,1473 @@
+// See LICENSE for license details.
+
+#ifndef RISCV_CSR_ENCODING_H
+#define RISCV_CSR_ENCODING_H
+
+#define MSTATUS_UIE 0x00000001
+#define MSTATUS_SIE 0x00000002
+#define MSTATUS_HIE 0x00000004
+#define MSTATUS_MIE 0x00000008
+#define MSTATUS_UPIE 0x00000010
+#define MSTATUS_SPIE 0x00000020
+#define MSTATUS_HPIE 0x00000040
+#define MSTATUS_MPIE 0x00000080
+#define MSTATUS_SPP 0x00000100
+#define MSTATUS_HPP 0x00000600
+#define MSTATUS_MPP 0x00001800
+#define MSTATUS_FS 0x00006000
+#define MSTATUS_XS 0x00018000
+#define MSTATUS_MPRV 0x00020000
+#define MSTATUS_SUM 0x00040000
+#define MSTATUS_MXR 0x00080000
+#define MSTATUS_TVM 0x00100000
+#define MSTATUS_TW 0x00200000
+#define MSTATUS_TSR 0x00400000
+#define MSTATUS32_SD 0x80000000
+#define MSTATUS_UXL 0x0000000300000000
+#define MSTATUS_SXL 0x0000000C00000000
+#define MSTATUS64_SD 0x8000000000000000
+
+#define SSTATUS_UIE 0x00000001
+#define SSTATUS_SIE 0x00000002
+#define SSTATUS_UPIE 0x00000010
+#define SSTATUS_SPIE 0x00000020
+#define SSTATUS_SPP 0x00000100
+#define SSTATUS_FS 0x00006000
+#define SSTATUS_XS 0x00018000
+#define SSTATUS_SUM 0x00040000
+#define SSTATUS_MXR 0x00080000
+#define SSTATUS32_SD 0x80000000
+#define SSTATUS_UXL 0x0000000300000000
+#define SSTATUS64_SD 0x8000000000000000
+
+#define DCSR_XDEBUGVER (3U<<30)
+#define DCSR_NDRESET (1<<29)
+#define DCSR_FULLRESET (1<<28)
+#define DCSR_EBREAKM (1<<15)
+#define DCSR_EBREAKH (1<<14)
+#define DCSR_EBREAKS (1<<13)
+#define DCSR_EBREAKU (1<<12)
+#define DCSR_STOPCYCLE (1<<10)
+#define DCSR_STOPTIME (1<<9)
+#define DCSR_CAUSE (7<<6)
+#define DCSR_DEBUGINT (1<<5)
+#define DCSR_HALT (1<<3)
+#define DCSR_STEP (1<<2)
+#define DCSR_PRV (3<<0)
+
+#define DCSR_CAUSE_NONE 0
+#define DCSR_CAUSE_SWBP 1
+#define DCSR_CAUSE_HWBP 2
+#define DCSR_CAUSE_DEBUGINT 3
+#define DCSR_CAUSE_STEP 4
+#define DCSR_CAUSE_HALT 5
+
+#define MCONTROL_TYPE(xlen) (0xfULL<<((xlen)-4))
+#define MCONTROL_DMODE(xlen) (1ULL<<((xlen)-5))
+#define MCONTROL_MASKMAX(xlen) (0x3fULL<<((xlen)-11))
+
+#define MCONTROL_SELECT (1<<19)
+#define MCONTROL_TIMING (1<<18)
+#define MCONTROL_ACTION (0x3f<<12)
+#define MCONTROL_CHAIN (1<<11)
+#define MCONTROL_MATCH (0xf<<7)
+#define MCONTROL_M (1<<6)
+#define MCONTROL_H (1<<5)
+#define MCONTROL_S (1<<4)
+#define MCONTROL_U (1<<3)
+#define MCONTROL_EXECUTE (1<<2)
+#define MCONTROL_STORE (1<<1)
+#define MCONTROL_LOAD (1<<0)
+
+#define MCONTROL_TYPE_NONE 0
+#define MCONTROL_TYPE_MATCH 2
+
+#define MCONTROL_ACTION_DEBUG_EXCEPTION 0
+#define MCONTROL_ACTION_DEBUG_MODE 1
+#define MCONTROL_ACTION_TRACE_START 2
+#define MCONTROL_ACTION_TRACE_STOP 3
+#define MCONTROL_ACTION_TRACE_EMIT 4
+
+#define MCONTROL_MATCH_EQUAL 0
+#define MCONTROL_MATCH_NAPOT 1
+#define MCONTROL_MATCH_GE 2
+#define MCONTROL_MATCH_LT 3
+#define MCONTROL_MATCH_MASK_LOW 4
+#define MCONTROL_MATCH_MASK_HIGH 5
+
+#define MIP_SSIP (1 << IRQ_S_SOFT)
+#define MIP_HSIP (1 << IRQ_H_SOFT)
+#define MIP_MSIP (1 << IRQ_M_SOFT)
+#define MIP_STIP (1 << IRQ_S_TIMER)
+#define MIP_HTIP (1 << IRQ_H_TIMER)
+#define MIP_MTIP (1 << IRQ_M_TIMER)
+#define MIP_SEIP (1 << IRQ_S_EXT)
+#define MIP_HEIP (1 << IRQ_H_EXT)
+#define MIP_MEIP (1 << IRQ_M_EXT)
+
+#define SIP_SSIP MIP_SSIP
+#define SIP_STIP MIP_STIP
+
+#define PRV_U 0
+#define PRV_S 1
+#define PRV_H 2
+#define PRV_M 3
+
+#define SPTBR32_MODE 0x80000000
+#define SPTBR32_ASID 0x7FC00000
+#define SPTBR32_PPN 0x003FFFFF
+#define SPTBR64_MODE 0xF000000000000000
+#define SPTBR64_ASID 0x0FFFF00000000000
+#define SPTBR64_PPN 0x00000FFFFFFFFFFF
+
+#define SPTBR_MODE_OFF 0
+#define SPTBR_MODE_SV32 1
+#define SPTBR_MODE_SV39 8
+#define SPTBR_MODE_SV48 9
+#define SPTBR_MODE_SV57 10
+#define SPTBR_MODE_SV64 11
+
+#define PMP_R 0x01
+#define PMP_W 0x02
+#define PMP_X 0x04
+#define PMP_A 0x18
+#define PMP_L 0x80
+#define PMP_SHIFT 2
+
+#define PMP_TOR 0x08
+#define PMP_NA4 0x10
+#define PMP_NAPOT 0x18
+
+#define IRQ_S_SOFT 1
+#define IRQ_H_SOFT 2
+#define IRQ_M_SOFT 3
+#define IRQ_S_TIMER 5
+#define IRQ_H_TIMER 6
+#define IRQ_M_TIMER 7
+#define IRQ_S_EXT 9
+#define IRQ_H_EXT 10
+#define IRQ_M_EXT 11
+#define IRQ_COP 12
+#define IRQ_HOST 13
+
+#define DEFAULT_RSTVEC 0x00001000
+#define CLINT_BASE 0x02000000
+#define CLINT_SIZE 0x000c0000
+#define EXT_IO_BASE 0x40000000
+#define DRAM_BASE 0x80000000
+
+// page table entry (PTE) fields
+#define PTE_V 0x001 // Valid
+#define PTE_R 0x002 // Read
+#define PTE_W 0x004 // Write
+#define PTE_X 0x008 // Execute
+#define PTE_U 0x010 // User
+#define PTE_G 0x020 // Global
+#define PTE_A 0x040 // Accessed
+#define PTE_D 0x080 // Dirty
+#define PTE_SOFT 0x300 // Reserved for Software
+
+#define PTE_PPN_SHIFT 10
+
+#define PTE_TABLE(PTE) (((PTE) & (PTE_V | PTE_R | PTE_W | PTE_X)) == PTE_V)
+
+#ifdef __riscv
+
+#if __riscv_xlen == 64
+# define MSTATUS_SD MSTATUS64_SD
+# define SSTATUS_SD SSTATUS64_SD
+# define RISCV_PGLEVEL_BITS 9
+# define SPTBR_MODE SPTBR64_MODE
+#else
+# define MSTATUS_SD MSTATUS32_SD
+# define SSTATUS_SD SSTATUS32_SD
+# define RISCV_PGLEVEL_BITS 10
+# define SPTBR_MODE SPTBR32_MODE
+#endif
+#define RISCV_PGSHIFT 12
+#define RISCV_PGSIZE (1 << RISCV_PGSHIFT)
+
+#ifndef __ASSEMBLER__
+
+#ifdef __GNUC__
+
+#define read_csr(reg) ({ unsigned long __tmp; \
+ asm volatile ("csrr %0, " #reg : "=r"(__tmp)); \
+ __tmp; })
+
+#define write_csr(reg, val) ({ \
+ asm volatile ("csrw " #reg ", %0" :: "rK"(val)); })
+
+#define swap_csr(reg, val) ({ unsigned long __tmp; \
+ asm volatile ("csrrw %0, " #reg ", %1" : "=r"(__tmp) : "rK"(val)); \
+ __tmp; })
+
+#define set_csr(reg, bit) ({ unsigned long __tmp; \
+ asm volatile ("csrrs %0, " #reg ", %1" : "=r"(__tmp) : "rK"(bit)); \
+ __tmp; })
+
+#define clear_csr(reg, bit) ({ unsigned long __tmp; \
+ asm volatile ("csrrc %0, " #reg ", %1" : "=r"(__tmp) : "rK"(bit)); \
+ __tmp; })
+
+#define rdtime() read_csr(time)
+#define rdcycle() read_csr(cycle)
+#define rdinstret() read_csr(instret)
+
+#endif
+
+#endif
+
+#endif
+
+#endif
+/* Automatically generated by parse-opcodes. */
+#ifndef RISCV_ENCODING_H
+#define RISCV_ENCODING_H
+#define MATCH_BEQ 0x63
+#define MASK_BEQ 0x707f
+#define MATCH_BNE 0x1063
+#define MASK_BNE 0x707f
+#define MATCH_BLT 0x4063
+#define MASK_BLT 0x707f
+#define MATCH_BGE 0x5063
+#define MASK_BGE 0x707f
+#define MATCH_BLTU 0x6063
+#define MASK_BLTU 0x707f
+#define MATCH_BGEU 0x7063
+#define MASK_BGEU 0x707f
+#define MATCH_JALR 0x67
+#define MASK_JALR 0x707f
+#define MATCH_JAL 0x6f
+#define MASK_JAL 0x7f
+#define MATCH_LUI 0x37
+#define MASK_LUI 0x7f
+#define MATCH_AUIPC 0x17
+#define MASK_AUIPC 0x7f
+#define MATCH_ADDI 0x13
+#define MASK_ADDI 0x707f
+#define MATCH_SLLI 0x1013
+#define MASK_SLLI 0xfc00707f
+#define MATCH_SLTI 0x2013
+#define MASK_SLTI 0x707f
+#define MATCH_SLTIU 0x3013
+#define MASK_SLTIU 0x707f
+#define MATCH_XORI 0x4013
+#define MASK_XORI 0x707f
+#define MATCH_SRLI 0x5013
+#define MASK_SRLI 0xfc00707f
+#define MATCH_SRAI 0x40005013
+#define MASK_SRAI 0xfc00707f
+#define MATCH_ORI 0x6013
+#define MASK_ORI 0x707f
+#define MATCH_ANDI 0x7013
+#define MASK_ANDI 0x707f
+#define MATCH_ADD 0x33
+#define MASK_ADD 0xfe00707f
+#define MATCH_SUB 0x40000033
+#define MASK_SUB 0xfe00707f
+#define MATCH_SLL 0x1033
+#define MASK_SLL 0xfe00707f
+#define MATCH_SLT 0x2033
+#define MASK_SLT 0xfe00707f
+#define MATCH_SLTU 0x3033
+#define MASK_SLTU 0xfe00707f
+#define MATCH_XOR 0x4033
+#define MASK_XOR 0xfe00707f
+#define MATCH_SRL 0x5033
+#define MASK_SRL 0xfe00707f
+#define MATCH_SRA 0x40005033
+#define MASK_SRA 0xfe00707f
+#define MATCH_OR 0x6033
+#define MASK_OR 0xfe00707f
+#define MATCH_AND 0x7033
+#define MASK_AND 0xfe00707f
+#define MATCH_ADDIW 0x1b
+#define MASK_ADDIW 0x707f
+#define MATCH_SLLIW 0x101b
+#define MASK_SLLIW 0xfe00707f
+#define MATCH_SRLIW 0x501b
+#define MASK_SRLIW 0xfe00707f
+#define MATCH_SRAIW 0x4000501b
+#define MASK_SRAIW 0xfe00707f
+#define MATCH_ADDW 0x3b
+#define MASK_ADDW 0xfe00707f
+#define MATCH_SUBW 0x4000003b
+#define MASK_SUBW 0xfe00707f
+#define MATCH_SLLW 0x103b
+#define MASK_SLLW 0xfe00707f
+#define MATCH_SRLW 0x503b
+#define MASK_SRLW 0xfe00707f
+#define MATCH_SRAW 0x4000503b
+#define MASK_SRAW 0xfe00707f
+#define MATCH_LB 0x3
+#define MASK_LB 0x707f
+#define MATCH_LH 0x1003
+#define MASK_LH 0x707f
+#define MATCH_LW 0x2003
+#define MASK_LW 0x707f
+#define MATCH_LD 0x3003
+#define MASK_LD 0x707f
+#define MATCH_LBU 0x4003
+#define MASK_LBU 0x707f
+#define MATCH_LHU 0x5003
+#define MASK_LHU 0x707f
+#define MATCH_LWU 0x6003
+#define MASK_LWU 0x707f
+#define MATCH_SB 0x23
+#define MASK_SB 0x707f
+#define MATCH_SH 0x1023
+#define MASK_SH 0x707f
+#define MATCH_SW 0x2023
+#define MASK_SW 0x707f
+#define MATCH_SD 0x3023
+#define MASK_SD 0x707f
+#define MATCH_FENCE 0xf
+#define MASK_FENCE 0x707f
+#define MATCH_FENCE_I 0x100f
+#define MASK_FENCE_I 0x707f
+#define MATCH_MUL 0x2000033
+#define MASK_MUL 0xfe00707f
+#define MATCH_MULH 0x2001033
+#define MASK_MULH 0xfe00707f
+#define MATCH_MULHSU 0x2002033
+#define MASK_MULHSU 0xfe00707f
+#define MATCH_MULHU 0x2003033
+#define MASK_MULHU 0xfe00707f
+#define MATCH_DIV 0x2004033
+#define MASK_DIV 0xfe00707f
+#define MATCH_DIVU 0x2005033
+#define MASK_DIVU 0xfe00707f
+#define MATCH_REM 0x2006033
+#define MASK_REM 0xfe00707f
+#define MATCH_REMU 0x2007033
+#define MASK_REMU 0xfe00707f
+#define MATCH_MULW 0x200003b
+#define MASK_MULW 0xfe00707f
+#define MATCH_DIVW 0x200403b
+#define MASK_DIVW 0xfe00707f
+#define MATCH_DIVUW 0x200503b
+#define MASK_DIVUW 0xfe00707f
+#define MATCH_REMW 0x200603b
+#define MASK_REMW 0xfe00707f
+#define MATCH_REMUW 0x200703b
+#define MASK_REMUW 0xfe00707f
+#define MATCH_AMOADD_W 0x202f
+#define MASK_AMOADD_W 0xf800707f
+#define MATCH_AMOXOR_W 0x2000202f
+#define MASK_AMOXOR_W 0xf800707f
+#define MATCH_AMOOR_W 0x4000202f
+#define MASK_AMOOR_W 0xf800707f
+#define MATCH_AMOAND_W 0x6000202f
+#define MASK_AMOAND_W 0xf800707f
+#define MATCH_AMOMIN_W 0x8000202f
+#define MASK_AMOMIN_W 0xf800707f
+#define MATCH_AMOMAX_W 0xa000202f
+#define MASK_AMOMAX_W 0xf800707f
+#define MATCH_AMOMINU_W 0xc000202f
+#define MASK_AMOMINU_W 0xf800707f
+#define MATCH_AMOMAXU_W 0xe000202f
+#define MASK_AMOMAXU_W 0xf800707f
+#define MATCH_AMOSWAP_W 0x800202f
+#define MASK_AMOSWAP_W 0xf800707f
+#define MATCH_LR_W 0x1000202f
+#define MASK_LR_W 0xf9f0707f
+#define MATCH_SC_W 0x1800202f
+#define MASK_SC_W 0xf800707f
+#define MATCH_AMOADD_D 0x302f
+#define MASK_AMOADD_D 0xf800707f
+#define MATCH_AMOXOR_D 0x2000302f
+#define MASK_AMOXOR_D 0xf800707f
+#define MATCH_AMOOR_D 0x4000302f
+#define MASK_AMOOR_D 0xf800707f
+#define MATCH_AMOAND_D 0x6000302f
+#define MASK_AMOAND_D 0xf800707f
+#define MATCH_AMOMIN_D 0x8000302f
+#define MASK_AMOMIN_D 0xf800707f
+#define MATCH_AMOMAX_D 0xa000302f
+#define MASK_AMOMAX_D 0xf800707f
+#define MATCH_AMOMINU_D 0xc000302f
+#define MASK_AMOMINU_D 0xf800707f
+#define MATCH_AMOMAXU_D 0xe000302f
+#define MASK_AMOMAXU_D 0xf800707f
+#define MATCH_AMOSWAP_D 0x800302f
+#define MASK_AMOSWAP_D 0xf800707f
+#define MATCH_LR_D 0x1000302f
+#define MASK_LR_D 0xf9f0707f
+#define MATCH_SC_D 0x1800302f
+#define MASK_SC_D 0xf800707f
+#define MATCH_ECALL 0x73
+#define MASK_ECALL 0xffffffff
+#define MATCH_EBREAK 0x100073
+#define MASK_EBREAK 0xffffffff
+#define MATCH_URET 0x200073
+#define MASK_URET 0xffffffff
+#define MATCH_SRET 0x10200073
+#define MASK_SRET 0xffffffff
+#define MATCH_MRET 0x30200073
+#define MASK_MRET 0xffffffff
+#define MATCH_DRET 0x7b200073
+#define MASK_DRET 0xffffffff
+#define MATCH_SFENCE_VMA 0x12000073
+#define MASK_SFENCE_VMA 0xfe007fff
+#define MATCH_WFI 0x10500073
+#define MASK_WFI 0xffffffff
+#define MATCH_CSRRW 0x1073
+#define MASK_CSRRW 0x707f
+#define MATCH_CSRRS 0x2073
+#define MASK_CSRRS 0x707f
+#define MATCH_CSRRC 0x3073
+#define MASK_CSRRC 0x707f
+#define MATCH_CSRRWI 0x5073
+#define MASK_CSRRWI 0x707f
+#define MATCH_CSRRSI 0x6073
+#define MASK_CSRRSI 0x707f
+#define MATCH_CSRRCI 0x7073
+#define MASK_CSRRCI 0x707f
+#define MATCH_FADD_S 0x53
+#define MASK_FADD_S 0xfe00007f
+#define MATCH_FSUB_S 0x8000053
+#define MASK_FSUB_S 0xfe00007f
+#define MATCH_FMUL_S 0x10000053
+#define MASK_FMUL_S 0xfe00007f
+#define MATCH_FDIV_S 0x18000053
+#define MASK_FDIV_S 0xfe00007f
+#define MATCH_FSGNJ_S 0x20000053
+#define MASK_FSGNJ_S 0xfe00707f
+#define MATCH_FSGNJN_S 0x20001053
+#define MASK_FSGNJN_S 0xfe00707f
+#define MATCH_FSGNJX_S 0x20002053
+#define MASK_FSGNJX_S 0xfe00707f
+#define MATCH_FMIN_S 0x28000053
+#define MASK_FMIN_S 0xfe00707f
+#define MATCH_FMAX_S 0x28001053
+#define MASK_FMAX_S 0xfe00707f
+#define MATCH_FSQRT_S 0x58000053
+#define MASK_FSQRT_S 0xfff0007f
+#define MATCH_FADD_D 0x2000053
+#define MASK_FADD_D 0xfe00007f
+#define MATCH_FSUB_D 0xa000053
+#define MASK_FSUB_D 0xfe00007f
+#define MATCH_FMUL_D 0x12000053
+#define MASK_FMUL_D 0xfe00007f
+#define MATCH_FDIV_D 0x1a000053
+#define MASK_FDIV_D 0xfe00007f
+#define MATCH_FSGNJ_D 0x22000053
+#define MASK_FSGNJ_D 0xfe00707f
+#define MATCH_FSGNJN_D 0x22001053
+#define MASK_FSGNJN_D 0xfe00707f
+#define MATCH_FSGNJX_D 0x22002053
+#define MASK_FSGNJX_D 0xfe00707f
+#define MATCH_FMIN_D 0x2a000053
+#define MASK_FMIN_D 0xfe00707f
+#define MATCH_FMAX_D 0x2a001053
+#define MASK_FMAX_D 0xfe00707f
+#define MATCH_FCVT_S_D 0x40100053
+#define MASK_FCVT_S_D 0xfff0007f
+#define MATCH_FCVT_D_S 0x42000053
+#define MASK_FCVT_D_S 0xfff0007f
+#define MATCH_FSQRT_D 0x5a000053
+#define MASK_FSQRT_D 0xfff0007f
+#define MATCH_FADD_Q 0x6000053
+#define MASK_FADD_Q 0xfe00007f
+#define MATCH_FSUB_Q 0xe000053
+#define MASK_FSUB_Q 0xfe00007f
+#define MATCH_FMUL_Q 0x16000053
+#define MASK_FMUL_Q 0xfe00007f
+#define MATCH_FDIV_Q 0x1e000053
+#define MASK_FDIV_Q 0xfe00007f
+#define MATCH_FSGNJ_Q 0x26000053
+#define MASK_FSGNJ_Q 0xfe00707f
+#define MATCH_FSGNJN_Q 0x26001053
+#define MASK_FSGNJN_Q 0xfe00707f
+#define MATCH_FSGNJX_Q 0x26002053
+#define MASK_FSGNJX_Q 0xfe00707f
+#define MATCH_FMIN_Q 0x2e000053
+#define MASK_FMIN_Q 0xfe00707f
+#define MATCH_FMAX_Q 0x2e001053
+#define MASK_FMAX_Q 0xfe00707f
+#define MATCH_FCVT_S_Q 0x40300053
+#define MASK_FCVT_S_Q 0xfff0007f
+#define MATCH_FCVT_Q_S 0x46000053
+#define MASK_FCVT_Q_S 0xfff0007f
+#define MATCH_FCVT_D_Q 0x42300053
+#define MASK_FCVT_D_Q 0xfff0007f
+#define MATCH_FCVT_Q_D 0x46100053
+#define MASK_FCVT_Q_D 0xfff0007f
+#define MATCH_FSQRT_Q 0x5e000053
+#define MASK_FSQRT_Q 0xfff0007f
+#define MATCH_FLE_S 0xa0000053
+#define MASK_FLE_S 0xfe00707f
+#define MATCH_FLT_S 0xa0001053
+#define MASK_FLT_S 0xfe00707f
+#define MATCH_FEQ_S 0xa0002053
+#define MASK_FEQ_S 0xfe00707f
+#define MATCH_FLE_D 0xa2000053
+#define MASK_FLE_D 0xfe00707f
+#define MATCH_FLT_D 0xa2001053
+#define MASK_FLT_D 0xfe00707f
+#define MATCH_FEQ_D 0xa2002053
+#define MASK_FEQ_D 0xfe00707f
+#define MATCH_FLE_Q 0xa6000053
+#define MASK_FLE_Q 0xfe00707f
+#define MATCH_FLT_Q 0xa6001053
+#define MASK_FLT_Q 0xfe00707f
+#define MATCH_FEQ_Q 0xa6002053
+#define MASK_FEQ_Q 0xfe00707f
+#define MATCH_FCVT_W_S 0xc0000053
+#define MASK_FCVT_W_S 0xfff0007f
+#define MATCH_FCVT_WU_S 0xc0100053
+#define MASK_FCVT_WU_S 0xfff0007f
+#define MATCH_FCVT_L_S 0xc0200053
+#define MASK_FCVT_L_S 0xfff0007f
+#define MATCH_FCVT_LU_S 0xc0300053
+#define MASK_FCVT_LU_S 0xfff0007f
+#define MATCH_FMV_X_W 0xe0000053
+#define MASK_FMV_X_W 0xfff0707f
+#define MATCH_FCLASS_S 0xe0001053
+#define MASK_FCLASS_S 0xfff0707f
+#define MATCH_FCVT_W_D 0xc2000053
+#define MASK_FCVT_W_D 0xfff0007f
+#define MATCH_FCVT_WU_D 0xc2100053
+#define MASK_FCVT_WU_D 0xfff0007f
+#define MATCH_FCVT_L_D 0xc2200053
+#define MASK_FCVT_L_D 0xfff0007f
+#define MATCH_FCVT_LU_D 0xc2300053
+#define MASK_FCVT_LU_D 0xfff0007f
+#define MATCH_FMV_X_D 0xe2000053
+#define MASK_FMV_X_D 0xfff0707f
+#define MATCH_FCLASS_D 0xe2001053
+#define MASK_FCLASS_D 0xfff0707f
+#define MATCH_FCVT_W_Q 0xc6000053
+#define MASK_FCVT_W_Q 0xfff0007f
+#define MATCH_FCVT_WU_Q 0xc6100053
+#define MASK_FCVT_WU_Q 0xfff0007f
+#define MATCH_FCVT_L_Q 0xc6200053
+#define MASK_FCVT_L_Q 0xfff0007f
+#define MATCH_FCVT_LU_Q 0xc6300053
+#define MASK_FCVT_LU_Q 0xfff0007f
+#define MATCH_FMV_X_Q 0xe6000053
+#define MASK_FMV_X_Q 0xfff0707f
+#define MATCH_FCLASS_Q 0xe6001053
+#define MASK_FCLASS_Q 0xfff0707f
+#define MATCH_FCVT_S_W 0xd0000053
+#define MASK_FCVT_S_W 0xfff0007f
+#define MATCH_FCVT_S_WU 0xd0100053
+#define MASK_FCVT_S_WU 0xfff0007f
+#define MATCH_FCVT_S_L 0xd0200053
+#define MASK_FCVT_S_L 0xfff0007f
+#define MATCH_FCVT_S_LU 0xd0300053
+#define MASK_FCVT_S_LU 0xfff0007f
+#define MATCH_FMV_W_X 0xf0000053
+#define MASK_FMV_W_X 0xfff0707f
+#define MATCH_FCVT_D_W 0xd2000053
+#define MASK_FCVT_D_W 0xfff0007f
+#define MATCH_FCVT_D_WU 0xd2100053
+#define MASK_FCVT_D_WU 0xfff0007f
+#define MATCH_FCVT_D_L 0xd2200053
+#define MASK_FCVT_D_L 0xfff0007f
+#define MATCH_FCVT_D_LU 0xd2300053
+#define MASK_FCVT_D_LU 0xfff0007f
+#define MATCH_FMV_D_X 0xf2000053
+#define MASK_FMV_D_X 0xfff0707f
+#define MATCH_FCVT_Q_W 0xd6000053
+#define MASK_FCVT_Q_W 0xfff0007f
+#define MATCH_FCVT_Q_WU 0xd6100053
+#define MASK_FCVT_Q_WU 0xfff0007f
+#define MATCH_FCVT_Q_L 0xd6200053
+#define MASK_FCVT_Q_L 0xfff0007f
+#define MATCH_FCVT_Q_LU 0xd6300053
+#define MASK_FCVT_Q_LU 0xfff0007f
+#define MATCH_FMV_Q_X 0xf6000053
+#define MASK_FMV_Q_X 0xfff0707f
+#define MATCH_FLW 0x2007
+#define MASK_FLW 0x707f
+#define MATCH_FLD 0x3007
+#define MASK_FLD 0x707f
+#define MATCH_FLQ 0x4007
+#define MASK_FLQ 0x707f
+#define MATCH_FSW 0x2027
+#define MASK_FSW 0x707f
+#define MATCH_FSD 0x3027
+#define MASK_FSD 0x707f
+#define MATCH_FSQ 0x4027
+#define MASK_FSQ 0x707f
+#define MATCH_FMADD_S 0x43
+#define MASK_FMADD_S 0x600007f
+#define MATCH_FMSUB_S 0x47
+#define MASK_FMSUB_S 0x600007f
+#define MATCH_FNMSUB_S 0x4b
+#define MASK_FNMSUB_S 0x600007f
+#define MATCH_FNMADD_S 0x4f
+#define MASK_FNMADD_S 0x600007f
+#define MATCH_FMADD_D 0x2000043
+#define MASK_FMADD_D 0x600007f
+#define MATCH_FMSUB_D 0x2000047
+#define MASK_FMSUB_D 0x600007f
+#define MATCH_FNMSUB_D 0x200004b
+#define MASK_FNMSUB_D 0x600007f
+#define MATCH_FNMADD_D 0x200004f
+#define MASK_FNMADD_D 0x600007f
+#define MATCH_FMADD_Q 0x6000043
+#define MASK_FMADD_Q 0x600007f
+#define MATCH_FMSUB_Q 0x6000047
+#define MASK_FMSUB_Q 0x600007f
+#define MATCH_FNMSUB_Q 0x600004b
+#define MASK_FNMSUB_Q 0x600007f
+#define MATCH_FNMADD_Q 0x600004f
+#define MASK_FNMADD_Q 0x600007f
+#define MATCH_C_NOP 0x1
+#define MASK_C_NOP 0xffff
+#define MATCH_C_ADDI16SP 0x6101
+#define MASK_C_ADDI16SP 0xef83
+#define MATCH_C_JR 0x8002
+#define MASK_C_JR 0xf07f
+#define MATCH_C_JALR 0x9002
+#define MASK_C_JALR 0xf07f
+#define MATCH_C_EBREAK 0x9002
+#define MASK_C_EBREAK 0xffff
+#define MATCH_C_LD 0x6000
+#define MASK_C_LD 0xe003
+#define MATCH_C_SD 0xe000
+#define MASK_C_SD 0xe003
+#define MATCH_C_ADDIW 0x2001
+#define MASK_C_ADDIW 0xe003
+#define MATCH_C_LDSP 0x6002
+#define MASK_C_LDSP 0xe003
+#define MATCH_C_SDSP 0xe002
+#define MASK_C_SDSP 0xe003
+#define MATCH_C_ADDI4SPN 0x0
+#define MASK_C_ADDI4SPN 0xe003
+#define MATCH_C_FLD 0x2000
+#define MASK_C_FLD 0xe003
+#define MATCH_C_LW 0x4000
+#define MASK_C_LW 0xe003
+#define MATCH_C_FLW 0x6000
+#define MASK_C_FLW 0xe003
+#define MATCH_C_FSD 0xa000
+#define MASK_C_FSD 0xe003
+#define MATCH_C_SW 0xc000
+#define MASK_C_SW 0xe003
+#define MATCH_C_FSW 0xe000
+#define MASK_C_FSW 0xe003
+#define MATCH_C_ADDI 0x1
+#define MASK_C_ADDI 0xe003
+#define MATCH_C_JAL 0x2001
+#define MASK_C_JAL 0xe003
+#define MATCH_C_LI 0x4001
+#define MASK_C_LI 0xe003
+#define MATCH_C_LUI 0x6001
+#define MASK_C_LUI 0xe003
+#define MATCH_C_SRLI 0x8001
+#define MASK_C_SRLI 0xec03
+#define MATCH_C_SRAI 0x8401
+#define MASK_C_SRAI 0xec03
+#define MATCH_C_ANDI 0x8801
+#define MASK_C_ANDI 0xec03
+#define MATCH_C_SUB 0x8c01
+#define MASK_C_SUB 0xfc63
+#define MATCH_C_XOR 0x8c21
+#define MASK_C_XOR 0xfc63
+#define MATCH_C_OR 0x8c41
+#define MASK_C_OR 0xfc63
+#define MATCH_C_AND 0x8c61
+#define MASK_C_AND 0xfc63
+#define MATCH_C_SUBW 0x9c01
+#define MASK_C_SUBW 0xfc63
+#define MATCH_C_ADDW 0x9c21
+#define MASK_C_ADDW 0xfc63
+#define MATCH_C_J 0xa001
+#define MASK_C_J 0xe003
+#define MATCH_C_BEQZ 0xc001
+#define MASK_C_BEQZ 0xe003
+#define MATCH_C_BNEZ 0xe001
+#define MASK_C_BNEZ 0xe003
+#define MATCH_C_SLLI 0x2
+#define MASK_C_SLLI 0xe003
+#define MATCH_C_FLDSP 0x2002
+#define MASK_C_FLDSP 0xe003
+#define MATCH_C_LWSP 0x4002
+#define MASK_C_LWSP 0xe003
+#define MATCH_C_FLWSP 0x6002
+#define MASK_C_FLWSP 0xe003
+#define MATCH_C_MV 0x8002
+#define MASK_C_MV 0xf003
+#define MATCH_C_ADD 0x9002
+#define MASK_C_ADD 0xf003
+#define MATCH_C_FSDSP 0xa002
+#define MASK_C_FSDSP 0xe003
+#define MATCH_C_SWSP 0xc002
+#define MASK_C_SWSP 0xe003
+#define MATCH_C_FSWSP 0xe002
+#define MASK_C_FSWSP 0xe003
+#define MATCH_CUSTOM0 0xb
+#define MASK_CUSTOM0 0x707f
+#define MATCH_CUSTOM0_RS1 0x200b
+#define MASK_CUSTOM0_RS1 0x707f
+#define MATCH_CUSTOM0_RS1_RS2 0x300b
+#define MASK_CUSTOM0_RS1_RS2 0x707f
+#define MATCH_CUSTOM0_RD 0x400b
+#define MASK_CUSTOM0_RD 0x707f
+#define MATCH_CUSTOM0_RD_RS1 0x600b
+#define MASK_CUSTOM0_RD_RS1 0x707f
+#define MATCH_CUSTOM0_RD_RS1_RS2 0x700b
+#define MASK_CUSTOM0_RD_RS1_RS2 0x707f
+#define MATCH_CUSTOM1 0x2b
+#define MASK_CUSTOM1 0x707f
+#define MATCH_CUSTOM1_RS1 0x202b
+#define MASK_CUSTOM1_RS1 0x707f
+#define MATCH_CUSTOM1_RS1_RS2 0x302b
+#define MASK_CUSTOM1_RS1_RS2 0x707f
+#define MATCH_CUSTOM1_RD 0x402b
+#define MASK_CUSTOM1_RD 0x707f
+#define MATCH_CUSTOM1_RD_RS1 0x602b
+#define MASK_CUSTOM1_RD_RS1 0x707f
+#define MATCH_CUSTOM1_RD_RS1_RS2 0x702b
+#define MASK_CUSTOM1_RD_RS1_RS2 0x707f
+#define MATCH_CUSTOM2 0x5b
+#define MASK_CUSTOM2 0x707f
+#define MATCH_CUSTOM2_RS1 0x205b
+#define MASK_CUSTOM2_RS1 0x707f
+#define MATCH_CUSTOM2_RS1_RS2 0x305b
+#define MASK_CUSTOM2_RS1_RS2 0x707f
+#define MATCH_CUSTOM2_RD 0x405b
+#define MASK_CUSTOM2_RD 0x707f
+#define MATCH_CUSTOM2_RD_RS1 0x605b
+#define MASK_CUSTOM2_RD_RS1 0x707f
+#define MATCH_CUSTOM2_RD_RS1_RS2 0x705b
+#define MASK_CUSTOM2_RD_RS1_RS2 0x707f
+#define MATCH_CUSTOM3 0x7b
+#define MASK_CUSTOM3 0x707f
+#define MATCH_CUSTOM3_RS1 0x207b
+#define MASK_CUSTOM3_RS1 0x707f
+#define MATCH_CUSTOM3_RS1_RS2 0x307b
+#define MASK_CUSTOM3_RS1_RS2 0x707f
+#define MATCH_CUSTOM3_RD 0x407b
+#define MASK_CUSTOM3_RD 0x707f
+#define MATCH_CUSTOM3_RD_RS1 0x607b
+#define MASK_CUSTOM3_RD_RS1 0x707f
+#define MATCH_CUSTOM3_RD_RS1_RS2 0x707b
+#define MASK_CUSTOM3_RD_RS1_RS2 0x707f
+#define CSR_FFLAGS 0x1
+#define CSR_FRM 0x2
+#define CSR_FCSR 0x3
+#define CSR_CYCLE 0xc00
+#define CSR_TIME 0xc01
+#define CSR_INSTRET 0xc02
+#define CSR_HPMCOUNTER3 0xc03
+#define CSR_HPMCOUNTER4 0xc04
+#define CSR_HPMCOUNTER5 0xc05
+#define CSR_HPMCOUNTER6 0xc06
+#define CSR_HPMCOUNTER7 0xc07
+#define CSR_HPMCOUNTER8 0xc08
+#define CSR_HPMCOUNTER9 0xc09
+#define CSR_HPMCOUNTER10 0xc0a
+#define CSR_HPMCOUNTER11 0xc0b
+#define CSR_HPMCOUNTER12 0xc0c
+#define CSR_HPMCOUNTER13 0xc0d
+#define CSR_HPMCOUNTER14 0xc0e
+#define CSR_HPMCOUNTER15 0xc0f
+#define CSR_HPMCOUNTER16 0xc10
+#define CSR_HPMCOUNTER17 0xc11
+#define CSR_HPMCOUNTER18 0xc12
+#define CSR_HPMCOUNTER19 0xc13
+#define CSR_HPMCOUNTER20 0xc14
+#define CSR_HPMCOUNTER21 0xc15
+#define CSR_HPMCOUNTER22 0xc16
+#define CSR_HPMCOUNTER23 0xc17
+#define CSR_HPMCOUNTER24 0xc18
+#define CSR_HPMCOUNTER25 0xc19
+#define CSR_HPMCOUNTER26 0xc1a
+#define CSR_HPMCOUNTER27 0xc1b
+#define CSR_HPMCOUNTER28 0xc1c
+#define CSR_HPMCOUNTER29 0xc1d
+#define CSR_HPMCOUNTER30 0xc1e
+#define CSR_HPMCOUNTER31 0xc1f
+#define CSR_SSTATUS 0x100
+#define CSR_SIE 0x104
+#define CSR_STVEC 0x105
+#define CSR_SCOUNTEREN 0x106
+#define CSR_SSCRATCH 0x140
+#define CSR_SEPC 0x141
+#define CSR_SCAUSE 0x142
+#define CSR_SBADADDR 0x143
+#define CSR_SIP 0x144
+#define CSR_SPTBR 0x180
+#define CSR_MSTATUS 0x300
+#define CSR_MISA 0x301
+#define CSR_MEDELEG 0x302
+#define CSR_MIDELEG 0x303
+#define CSR_MIE 0x304
+#define CSR_MTVEC 0x305
+#define CSR_MCOUNTEREN 0x306
+#define CSR_MSCRATCH 0x340
+#define CSR_MEPC 0x341
+#define CSR_MCAUSE 0x342
+#define CSR_MBADADDR 0x343
+#define CSR_MIP 0x344
+#define CSR_PMPCFG0 0x3a0
+#define CSR_PMPCFG1 0x3a1
+#define CSR_PMPCFG2 0x3a2
+#define CSR_PMPCFG3 0x3a3
+#define CSR_PMPADDR0 0x3b0
+#define CSR_PMPADDR1 0x3b1
+#define CSR_PMPADDR2 0x3b2
+#define CSR_PMPADDR3 0x3b3
+#define CSR_PMPADDR4 0x3b4
+#define CSR_PMPADDR5 0x3b5
+#define CSR_PMPADDR6 0x3b6
+#define CSR_PMPADDR7 0x3b7
+#define CSR_PMPADDR8 0x3b8
+#define CSR_PMPADDR9 0x3b9
+#define CSR_PMPADDR10 0x3ba
+#define CSR_PMPADDR11 0x3bb
+#define CSR_PMPADDR12 0x3bc
+#define CSR_PMPADDR13 0x3bd
+#define CSR_PMPADDR14 0x3be
+#define CSR_PMPADDR15 0x3bf
+#define CSR_TSELECT 0x7a0
+#define CSR_TDATA1 0x7a1
+#define CSR_TDATA2 0x7a2
+#define CSR_TDATA3 0x7a3
+#define CSR_DCSR 0x7b0
+#define CSR_DPC 0x7b1
+#define CSR_DSCRATCH 0x7b2
+#define CSR_MCYCLE 0xb00
+#define CSR_MINSTRET 0xb02
+#define CSR_MHPMCOUNTER3 0xb03
+#define CSR_MHPMCOUNTER4 0xb04
+#define CSR_MHPMCOUNTER5 0xb05
+#define CSR_MHPMCOUNTER6 0xb06
+#define CSR_MHPMCOUNTER7 0xb07
+#define CSR_MHPMCOUNTER8 0xb08
+#define CSR_MHPMCOUNTER9 0xb09
+#define CSR_MHPMCOUNTER10 0xb0a
+#define CSR_MHPMCOUNTER11 0xb0b
+#define CSR_MHPMCOUNTER12 0xb0c
+#define CSR_MHPMCOUNTER13 0xb0d
+#define CSR_MHPMCOUNTER14 0xb0e
+#define CSR_MHPMCOUNTER15 0xb0f
+#define CSR_MHPMCOUNTER16 0xb10
+#define CSR_MHPMCOUNTER17 0xb11
+#define CSR_MHPMCOUNTER18 0xb12
+#define CSR_MHPMCOUNTER19 0xb13
+#define CSR_MHPMCOUNTER20 0xb14
+#define CSR_MHPMCOUNTER21 0xb15
+#define CSR_MHPMCOUNTER22 0xb16
+#define CSR_MHPMCOUNTER23 0xb17
+#define CSR_MHPMCOUNTER24 0xb18
+#define CSR_MHPMCOUNTER25 0xb19
+#define CSR_MHPMCOUNTER26 0xb1a
+#define CSR_MHPMCOUNTER27 0xb1b
+#define CSR_MHPMCOUNTER28 0xb1c
+#define CSR_MHPMCOUNTER29 0xb1d
+#define CSR_MHPMCOUNTER30 0xb1e
+#define CSR_MHPMCOUNTER31 0xb1f
+#define CSR_MHPMEVENT3 0x323
+#define CSR_MHPMEVENT4 0x324
+#define CSR_MHPMEVENT5 0x325
+#define CSR_MHPMEVENT6 0x326
+#define CSR_MHPMEVENT7 0x327
+#define CSR_MHPMEVENT8 0x328
+#define CSR_MHPMEVENT9 0x329
+#define CSR_MHPMEVENT10 0x32a
+#define CSR_MHPMEVENT11 0x32b
+#define CSR_MHPMEVENT12 0x32c
+#define CSR_MHPMEVENT13 0x32d
+#define CSR_MHPMEVENT14 0x32e
+#define CSR_MHPMEVENT15 0x32f
+#define CSR_MHPMEVENT16 0x330
+#define CSR_MHPMEVENT17 0x331
+#define CSR_MHPMEVENT18 0x332
+#define CSR_MHPMEVENT19 0x333
+#define CSR_MHPMEVENT20 0x334
+#define CSR_MHPMEVENT21 0x335
+#define CSR_MHPMEVENT22 0x336
+#define CSR_MHPMEVENT23 0x337
+#define CSR_MHPMEVENT24 0x338
+#define CSR_MHPMEVENT25 0x339
+#define CSR_MHPMEVENT26 0x33a
+#define CSR_MHPMEVENT27 0x33b
+#define CSR_MHPMEVENT28 0x33c
+#define CSR_MHPMEVENT29 0x33d
+#define CSR_MHPMEVENT30 0x33e
+#define CSR_MHPMEVENT31 0x33f
+#define CSR_MVENDORID 0xf11
+#define CSR_MARCHID 0xf12
+#define CSR_MIMPID 0xf13
+#define CSR_MHARTID 0xf14
+#define CSR_CYCLEH 0xc80
+#define CSR_TIMEH 0xc81
+#define CSR_INSTRETH 0xc82
+#define CSR_HPMCOUNTER3H 0xc83
+#define CSR_HPMCOUNTER4H 0xc84
+#define CSR_HPMCOUNTER5H 0xc85
+#define CSR_HPMCOUNTER6H 0xc86
+#define CSR_HPMCOUNTER7H 0xc87
+#define CSR_HPMCOUNTER8H 0xc88
+#define CSR_HPMCOUNTER9H 0xc89
+#define CSR_HPMCOUNTER10H 0xc8a
+#define CSR_HPMCOUNTER11H 0xc8b
+#define CSR_HPMCOUNTER12H 0xc8c
+#define CSR_HPMCOUNTER13H 0xc8d
+#define CSR_HPMCOUNTER14H 0xc8e
+#define CSR_HPMCOUNTER15H 0xc8f
+#define CSR_HPMCOUNTER16H 0xc90
+#define CSR_HPMCOUNTER17H 0xc91
+#define CSR_HPMCOUNTER18H 0xc92
+#define CSR_HPMCOUNTER19H 0xc93
+#define CSR_HPMCOUNTER20H 0xc94
+#define CSR_HPMCOUNTER21H 0xc95
+#define CSR_HPMCOUNTER22H 0xc96
+#define CSR_HPMCOUNTER23H 0xc97
+#define CSR_HPMCOUNTER24H 0xc98
+#define CSR_HPMCOUNTER25H 0xc99
+#define CSR_HPMCOUNTER26H 0xc9a
+#define CSR_HPMCOUNTER27H 0xc9b
+#define CSR_HPMCOUNTER28H 0xc9c
+#define CSR_HPMCOUNTER29H 0xc9d
+#define CSR_HPMCOUNTER30H 0xc9e
+#define CSR_HPMCOUNTER31H 0xc9f
+#define CSR_MCYCLEH 0xb80
+#define CSR_MINSTRETH 0xb82
+#define CSR_MHPMCOUNTER3H 0xb83
+#define CSR_MHPMCOUNTER4H 0xb84
+#define CSR_MHPMCOUNTER5H 0xb85
+#define CSR_MHPMCOUNTER6H 0xb86
+#define CSR_MHPMCOUNTER7H 0xb87
+#define CSR_MHPMCOUNTER8H 0xb88
+#define CSR_MHPMCOUNTER9H 0xb89
+#define CSR_MHPMCOUNTER10H 0xb8a
+#define CSR_MHPMCOUNTER11H 0xb8b
+#define CSR_MHPMCOUNTER12H 0xb8c
+#define CSR_MHPMCOUNTER13H 0xb8d
+#define CSR_MHPMCOUNTER14H 0xb8e
+#define CSR_MHPMCOUNTER15H 0xb8f
+#define CSR_MHPMCOUNTER16H 0xb90
+#define CSR_MHPMCOUNTER17H 0xb91
+#define CSR_MHPMCOUNTER18H 0xb92
+#define CSR_MHPMCOUNTER19H 0xb93
+#define CSR_MHPMCOUNTER20H 0xb94
+#define CSR_MHPMCOUNTER21H 0xb95
+#define CSR_MHPMCOUNTER22H 0xb96
+#define CSR_MHPMCOUNTER23H 0xb97
+#define CSR_MHPMCOUNTER24H 0xb98
+#define CSR_MHPMCOUNTER25H 0xb99
+#define CSR_MHPMCOUNTER26H 0xb9a
+#define CSR_MHPMCOUNTER27H 0xb9b
+#define CSR_MHPMCOUNTER28H 0xb9c
+#define CSR_MHPMCOUNTER29H 0xb9d
+#define CSR_MHPMCOUNTER30H 0xb9e
+#define CSR_MHPMCOUNTER31H 0xb9f
+#define CAUSE_MISALIGNED_FETCH 0x0
+#define CAUSE_FETCH_ACCESS 0x1
+#define CAUSE_ILLEGAL_INSTRUCTION 0x2
+#define CAUSE_BREAKPOINT 0x3
+#define CAUSE_MISALIGNED_LOAD 0x4
+#define CAUSE_LOAD_ACCESS 0x5
+#define CAUSE_MISALIGNED_STORE 0x6
+#define CAUSE_STORE_ACCESS 0x7
+#define CAUSE_USER_ECALL 0x8
+#define CAUSE_SUPERVISOR_ECALL 0x9
+#define CAUSE_HYPERVISOR_ECALL 0xa
+#define CAUSE_MACHINE_ECALL 0xb
+#define CAUSE_FETCH_PAGE_FAULT 0xc
+#define CAUSE_LOAD_PAGE_FAULT 0xd
+#define CAUSE_STORE_PAGE_FAULT 0xf
+#endif
+#ifdef DECLARE_INSN
+DECLARE_INSN(beq, MATCH_BEQ, MASK_BEQ)
+DECLARE_INSN(bne, MATCH_BNE, MASK_BNE)
+DECLARE_INSN(blt, MATCH_BLT, MASK_BLT)
+DECLARE_INSN(bge, MATCH_BGE, MASK_BGE)
+DECLARE_INSN(bltu, MATCH_BLTU, MASK_BLTU)
+DECLARE_INSN(bgeu, MATCH_BGEU, MASK_BGEU)
+DECLARE_INSN(jalr, MATCH_JALR, MASK_JALR)
+DECLARE_INSN(jal, MATCH_JAL, MASK_JAL)
+DECLARE_INSN(lui, MATCH_LUI, MASK_LUI)
+DECLARE_INSN(auipc, MATCH_AUIPC, MASK_AUIPC)
+DECLARE_INSN(addi, MATCH_ADDI, MASK_ADDI)
+DECLARE_INSN(slli, MATCH_SLLI, MASK_SLLI)
+DECLARE_INSN(slti, MATCH_SLTI, MASK_SLTI)
+DECLARE_INSN(sltiu, MATCH_SLTIU, MASK_SLTIU)
+DECLARE_INSN(xori, MATCH_XORI, MASK_XORI)
+DECLARE_INSN(srli, MATCH_SRLI, MASK_SRLI)
+DECLARE_INSN(srai, MATCH_SRAI, MASK_SRAI)
+DECLARE_INSN(ori, MATCH_ORI, MASK_ORI)
+DECLARE_INSN(andi, MATCH_ANDI, MASK_ANDI)
+DECLARE_INSN(add, MATCH_ADD, MASK_ADD)
+DECLARE_INSN(sub, MATCH_SUB, MASK_SUB)
+DECLARE_INSN(sll, MATCH_SLL, MASK_SLL)
+DECLARE_INSN(slt, MATCH_SLT, MASK_SLT)
+DECLARE_INSN(sltu, MATCH_SLTU, MASK_SLTU)
+DECLARE_INSN(xor, MATCH_XOR, MASK_XOR)
+DECLARE_INSN(srl, MATCH_SRL, MASK_SRL)
+DECLARE_INSN(sra, MATCH_SRA, MASK_SRA)
+DECLARE_INSN(or, MATCH_OR, MASK_OR)
+DECLARE_INSN(and, MATCH_AND, MASK_AND)
+DECLARE_INSN(addiw, MATCH_ADDIW, MASK_ADDIW)
+DECLARE_INSN(slliw, MATCH_SLLIW, MASK_SLLIW)
+DECLARE_INSN(srliw, MATCH_SRLIW, MASK_SRLIW)
+DECLARE_INSN(sraiw, MATCH_SRAIW, MASK_SRAIW)
+DECLARE_INSN(addw, MATCH_ADDW, MASK_ADDW)
+DECLARE_INSN(subw, MATCH_SUBW, MASK_SUBW)
+DECLARE_INSN(sllw, MATCH_SLLW, MASK_SLLW)
+DECLARE_INSN(srlw, MATCH_SRLW, MASK_SRLW)
+DECLARE_INSN(sraw, MATCH_SRAW, MASK_SRAW)
+DECLARE_INSN(lb, MATCH_LB, MASK_LB)
+DECLARE_INSN(lh, MATCH_LH, MASK_LH)
+DECLARE_INSN(lw, MATCH_LW, MASK_LW)
+DECLARE_INSN(ld, MATCH_LD, MASK_LD)
+DECLARE_INSN(lbu, MATCH_LBU, MASK_LBU)
+DECLARE_INSN(lhu, MATCH_LHU, MASK_LHU)
+DECLARE_INSN(lwu, MATCH_LWU, MASK_LWU)
+DECLARE_INSN(sb, MATCH_SB, MASK_SB)
+DECLARE_INSN(sh, MATCH_SH, MASK_SH)
+DECLARE_INSN(sw, MATCH_SW, MASK_SW)
+DECLARE_INSN(sd, MATCH_SD, MASK_SD)
+DECLARE_INSN(fence, MATCH_FENCE, MASK_FENCE)
+DECLARE_INSN(fence_i, MATCH_FENCE_I, MASK_FENCE_I)
+DECLARE_INSN(mul, MATCH_MUL, MASK_MUL)
+DECLARE_INSN(mulh, MATCH_MULH, MASK_MULH)
+DECLARE_INSN(mulhsu, MATCH_MULHSU, MASK_MULHSU)
+DECLARE_INSN(mulhu, MATCH_MULHU, MASK_MULHU)
+DECLARE_INSN(div, MATCH_DIV, MASK_DIV)
+DECLARE_INSN(divu, MATCH_DIVU, MASK_DIVU)
+DECLARE_INSN(rem, MATCH_REM, MASK_REM)
+DECLARE_INSN(remu, MATCH_REMU, MASK_REMU)
+DECLARE_INSN(mulw, MATCH_MULW, MASK_MULW)
+DECLARE_INSN(divw, MATCH_DIVW, MASK_DIVW)
+DECLARE_INSN(divuw, MATCH_DIVUW, MASK_DIVUW)
+DECLARE_INSN(remw, MATCH_REMW, MASK_REMW)
+DECLARE_INSN(remuw, MATCH_REMUW, MASK_REMUW)
+DECLARE_INSN(amoadd_w, MATCH_AMOADD_W, MASK_AMOADD_W)
+DECLARE_INSN(amoxor_w, MATCH_AMOXOR_W, MASK_AMOXOR_W)
+DECLARE_INSN(amoor_w, MATCH_AMOOR_W, MASK_AMOOR_W)
+DECLARE_INSN(amoand_w, MATCH_AMOAND_W, MASK_AMOAND_W)
+DECLARE_INSN(amomin_w, MATCH_AMOMIN_W, MASK_AMOMIN_W)
+DECLARE_INSN(amomax_w, MATCH_AMOMAX_W, MASK_AMOMAX_W)
+DECLARE_INSN(amominu_w, MATCH_AMOMINU_W, MASK_AMOMINU_W)
+DECLARE_INSN(amomaxu_w, MATCH_AMOMAXU_W, MASK_AMOMAXU_W)
+DECLARE_INSN(amoswap_w, MATCH_AMOSWAP_W, MASK_AMOSWAP_W)
+DECLARE_INSN(lr_w, MATCH_LR_W, MASK_LR_W)
+DECLARE_INSN(sc_w, MATCH_SC_W, MASK_SC_W)
+DECLARE_INSN(amoadd_d, MATCH_AMOADD_D, MASK_AMOADD_D)
+DECLARE_INSN(amoxor_d, MATCH_AMOXOR_D, MASK_AMOXOR_D)
+DECLARE_INSN(amoor_d, MATCH_AMOOR_D, MASK_AMOOR_D)
+DECLARE_INSN(amoand_d, MATCH_AMOAND_D, MASK_AMOAND_D)
+DECLARE_INSN(amomin_d, MATCH_AMOMIN_D, MASK_AMOMIN_D)
+DECLARE_INSN(amomax_d, MATCH_AMOMAX_D, MASK_AMOMAX_D)
+DECLARE_INSN(amominu_d, MATCH_AMOMINU_D, MASK_AMOMINU_D)
+DECLARE_INSN(amomaxu_d, MATCH_AMOMAXU_D, MASK_AMOMAXU_D)
+DECLARE_INSN(amoswap_d, MATCH_AMOSWAP_D, MASK_AMOSWAP_D)
+DECLARE_INSN(lr_d, MATCH_LR_D, MASK_LR_D)
+DECLARE_INSN(sc_d, MATCH_SC_D, MASK_SC_D)
+DECLARE_INSN(ecall, MATCH_ECALL, MASK_ECALL)
+DECLARE_INSN(ebreak, MATCH_EBREAK, MASK_EBREAK)
+DECLARE_INSN(uret, MATCH_URET, MASK_URET)
+DECLARE_INSN(sret, MATCH_SRET, MASK_SRET)
+DECLARE_INSN(mret, MATCH_MRET, MASK_MRET)
+DECLARE_INSN(dret, MATCH_DRET, MASK_DRET)
+DECLARE_INSN(sfence_vma, MATCH_SFENCE_VMA, MASK_SFENCE_VMA)
+DECLARE_INSN(wfi, MATCH_WFI, MASK_WFI)
+DECLARE_INSN(csrrw, MATCH_CSRRW, MASK_CSRRW)
+DECLARE_INSN(csrrs, MATCH_CSRRS, MASK_CSRRS)
+DECLARE_INSN(csrrc, MATCH_CSRRC, MASK_CSRRC)
+DECLARE_INSN(csrrwi, MATCH_CSRRWI, MASK_CSRRWI)
+DECLARE_INSN(csrrsi, MATCH_CSRRSI, MASK_CSRRSI)
+DECLARE_INSN(csrrci, MATCH_CSRRCI, MASK_CSRRCI)
+DECLARE_INSN(fadd_s, MATCH_FADD_S, MASK_FADD_S)
+DECLARE_INSN(fsub_s, MATCH_FSUB_S, MASK_FSUB_S)
+DECLARE_INSN(fmul_s, MATCH_FMUL_S, MASK_FMUL_S)
+DECLARE_INSN(fdiv_s, MATCH_FDIV_S, MASK_FDIV_S)
+DECLARE_INSN(fsgnj_s, MATCH_FSGNJ_S, MASK_FSGNJ_S)
+DECLARE_INSN(fsgnjn_s, MATCH_FSGNJN_S, MASK_FSGNJN_S)
+DECLARE_INSN(fsgnjx_s, MATCH_FSGNJX_S, MASK_FSGNJX_S)
+DECLARE_INSN(fmin_s, MATCH_FMIN_S, MASK_FMIN_S)
+DECLARE_INSN(fmax_s, MATCH_FMAX_S, MASK_FMAX_S)
+DECLARE_INSN(fsqrt_s, MATCH_FSQRT_S, MASK_FSQRT_S)
+DECLARE_INSN(fadd_d, MATCH_FADD_D, MASK_FADD_D)
+DECLARE_INSN(fsub_d, MATCH_FSUB_D, MASK_FSUB_D)
+DECLARE_INSN(fmul_d, MATCH_FMUL_D, MASK_FMUL_D)
+DECLARE_INSN(fdiv_d, MATCH_FDIV_D, MASK_FDIV_D)
+DECLARE_INSN(fsgnj_d, MATCH_FSGNJ_D, MASK_FSGNJ_D)
+DECLARE_INSN(fsgnjn_d, MATCH_FSGNJN_D, MASK_FSGNJN_D)
+DECLARE_INSN(fsgnjx_d, MATCH_FSGNJX_D, MASK_FSGNJX_D)
+DECLARE_INSN(fmin_d, MATCH_FMIN_D, MASK_FMIN_D)
+DECLARE_INSN(fmax_d, MATCH_FMAX_D, MASK_FMAX_D)
+DECLARE_INSN(fcvt_s_d, MATCH_FCVT_S_D, MASK_FCVT_S_D)
+DECLARE_INSN(fcvt_d_s, MATCH_FCVT_D_S, MASK_FCVT_D_S)
+DECLARE_INSN(fsqrt_d, MATCH_FSQRT_D, MASK_FSQRT_D)
+DECLARE_INSN(fadd_q, MATCH_FADD_Q, MASK_FADD_Q)
+DECLARE_INSN(fsub_q, MATCH_FSUB_Q, MASK_FSUB_Q)
+DECLARE_INSN(fmul_q, MATCH_FMUL_Q, MASK_FMUL_Q)
+DECLARE_INSN(fdiv_q, MATCH_FDIV_Q, MASK_FDIV_Q)
+DECLARE_INSN(fsgnj_q, MATCH_FSGNJ_Q, MASK_FSGNJ_Q)
+DECLARE_INSN(fsgnjn_q, MATCH_FSGNJN_Q, MASK_FSGNJN_Q)
+DECLARE_INSN(fsgnjx_q, MATCH_FSGNJX_Q, MASK_FSGNJX_Q)
+DECLARE_INSN(fmin_q, MATCH_FMIN_Q, MASK_FMIN_Q)
+DECLARE_INSN(fmax_q, MATCH_FMAX_Q, MASK_FMAX_Q)
+DECLARE_INSN(fcvt_s_q, MATCH_FCVT_S_Q, MASK_FCVT_S_Q)
+DECLARE_INSN(fcvt_q_s, MATCH_FCVT_Q_S, MASK_FCVT_Q_S)
+DECLARE_INSN(fcvt_d_q, MATCH_FCVT_D_Q, MASK_FCVT_D_Q)
+DECLARE_INSN(fcvt_q_d, MATCH_FCVT_Q_D, MASK_FCVT_Q_D)
+DECLARE_INSN(fsqrt_q, MATCH_FSQRT_Q, MASK_FSQRT_Q)
+DECLARE_INSN(fle_s, MATCH_FLE_S, MASK_FLE_S)
+DECLARE_INSN(flt_s, MATCH_FLT_S, MASK_FLT_S)
+DECLARE_INSN(feq_s, MATCH_FEQ_S, MASK_FEQ_S)
+DECLARE_INSN(fle_d, MATCH_FLE_D, MASK_FLE_D)
+DECLARE_INSN(flt_d, MATCH_FLT_D, MASK_FLT_D)
+DECLARE_INSN(feq_d, MATCH_FEQ_D, MASK_FEQ_D)
+DECLARE_INSN(fle_q, MATCH_FLE_Q, MASK_FLE_Q)
+DECLARE_INSN(flt_q, MATCH_FLT_Q, MASK_FLT_Q)
+DECLARE_INSN(feq_q, MATCH_FEQ_Q, MASK_FEQ_Q)
+DECLARE_INSN(fcvt_w_s, MATCH_FCVT_W_S, MASK_FCVT_W_S)
+DECLARE_INSN(fcvt_wu_s, MATCH_FCVT_WU_S, MASK_FCVT_WU_S)
+DECLARE_INSN(fcvt_l_s, MATCH_FCVT_L_S, MASK_FCVT_L_S)
+DECLARE_INSN(fcvt_lu_s, MATCH_FCVT_LU_S, MASK_FCVT_LU_S)
+DECLARE_INSN(fmv_x_w, MATCH_FMV_X_W, MASK_FMV_X_W)
+DECLARE_INSN(fclass_s, MATCH_FCLASS_S, MASK_FCLASS_S)
+DECLARE_INSN(fcvt_w_d, MATCH_FCVT_W_D, MASK_FCVT_W_D)
+DECLARE_INSN(fcvt_wu_d, MATCH_FCVT_WU_D, MASK_FCVT_WU_D)
+DECLARE_INSN(fcvt_l_d, MATCH_FCVT_L_D, MASK_FCVT_L_D)
+DECLARE_INSN(fcvt_lu_d, MATCH_FCVT_LU_D, MASK_FCVT_LU_D)
+DECLARE_INSN(fmv_x_d, MATCH_FMV_X_D, MASK_FMV_X_D)
+DECLARE_INSN(fclass_d, MATCH_FCLASS_D, MASK_FCLASS_D)
+DECLARE_INSN(fcvt_w_q, MATCH_FCVT_W_Q, MASK_FCVT_W_Q)
+DECLARE_INSN(fcvt_wu_q, MATCH_FCVT_WU_Q, MASK_FCVT_WU_Q)
+DECLARE_INSN(fcvt_l_q, MATCH_FCVT_L_Q, MASK_FCVT_L_Q)
+DECLARE_INSN(fcvt_lu_q, MATCH_FCVT_LU_Q, MASK_FCVT_LU_Q)
+DECLARE_INSN(fmv_x_q, MATCH_FMV_X_Q, MASK_FMV_X_Q)
+DECLARE_INSN(fclass_q, MATCH_FCLASS_Q, MASK_FCLASS_Q)
+DECLARE_INSN(fcvt_s_w, MATCH_FCVT_S_W, MASK_FCVT_S_W)
+DECLARE_INSN(fcvt_s_wu, MATCH_FCVT_S_WU, MASK_FCVT_S_WU)
+DECLARE_INSN(fcvt_s_l, MATCH_FCVT_S_L, MASK_FCVT_S_L)
+DECLARE_INSN(fcvt_s_lu, MATCH_FCVT_S_LU, MASK_FCVT_S_LU)
+DECLARE_INSN(fmv_w_x, MATCH_FMV_W_X, MASK_FMV_W_X)
+DECLARE_INSN(fcvt_d_w, MATCH_FCVT_D_W, MASK_FCVT_D_W)
+DECLARE_INSN(fcvt_d_wu, MATCH_FCVT_D_WU, MASK_FCVT_D_WU)
+DECLARE_INSN(fcvt_d_l, MATCH_FCVT_D_L, MASK_FCVT_D_L)
+DECLARE_INSN(fcvt_d_lu, MATCH_FCVT_D_LU, MASK_FCVT_D_LU)
+DECLARE_INSN(fmv_d_x, MATCH_FMV_D_X, MASK_FMV_D_X)
+DECLARE_INSN(fcvt_q_w, MATCH_FCVT_Q_W, MASK_FCVT_Q_W)
+DECLARE_INSN(fcvt_q_wu, MATCH_FCVT_Q_WU, MASK_FCVT_Q_WU)
+DECLARE_INSN(fcvt_q_l, MATCH_FCVT_Q_L, MASK_FCVT_Q_L)
+DECLARE_INSN(fcvt_q_lu, MATCH_FCVT_Q_LU, MASK_FCVT_Q_LU)
+DECLARE_INSN(fmv_q_x, MATCH_FMV_Q_X, MASK_FMV_Q_X)
+DECLARE_INSN(flw, MATCH_FLW, MASK_FLW)
+DECLARE_INSN(fld, MATCH_FLD, MASK_FLD)
+DECLARE_INSN(flq, MATCH_FLQ, MASK_FLQ)
+DECLARE_INSN(fsw, MATCH_FSW, MASK_FSW)
+DECLARE_INSN(fsd, MATCH_FSD, MASK_FSD)
+DECLARE_INSN(fsq, MATCH_FSQ, MASK_FSQ)
+DECLARE_INSN(fmadd_s, MATCH_FMADD_S, MASK_FMADD_S)
+DECLARE_INSN(fmsub_s, MATCH_FMSUB_S, MASK_FMSUB_S)
+DECLARE_INSN(fnmsub_s, MATCH_FNMSUB_S, MASK_FNMSUB_S)
+DECLARE_INSN(fnmadd_s, MATCH_FNMADD_S, MASK_FNMADD_S)
+DECLARE_INSN(fmadd_d, MATCH_FMADD_D, MASK_FMADD_D)
+DECLARE_INSN(fmsub_d, MATCH_FMSUB_D, MASK_FMSUB_D)
+DECLARE_INSN(fnmsub_d, MATCH_FNMSUB_D, MASK_FNMSUB_D)
+DECLARE_INSN(fnmadd_d, MATCH_FNMADD_D, MASK_FNMADD_D)
+DECLARE_INSN(fmadd_q, MATCH_FMADD_Q, MASK_FMADD_Q)
+DECLARE_INSN(fmsub_q, MATCH_FMSUB_Q, MASK_FMSUB_Q)
+DECLARE_INSN(fnmsub_q, MATCH_FNMSUB_Q, MASK_FNMSUB_Q)
+DECLARE_INSN(fnmadd_q, MATCH_FNMADD_Q, MASK_FNMADD_Q)
+DECLARE_INSN(c_nop, MATCH_C_NOP, MASK_C_NOP)
+DECLARE_INSN(c_addi16sp, MATCH_C_ADDI16SP, MASK_C_ADDI16SP)
+DECLARE_INSN(c_jr, MATCH_C_JR, MASK_C_JR)
+DECLARE_INSN(c_jalr, MATCH_C_JALR, MASK_C_JALR)
+DECLARE_INSN(c_ebreak, MATCH_C_EBREAK, MASK_C_EBREAK)
+DECLARE_INSN(c_ld, MATCH_C_LD, MASK_C_LD)
+DECLARE_INSN(c_sd, MATCH_C_SD, MASK_C_SD)
+DECLARE_INSN(c_addiw, MATCH_C_ADDIW, MASK_C_ADDIW)
+DECLARE_INSN(c_ldsp, MATCH_C_LDSP, MASK_C_LDSP)
+DECLARE_INSN(c_sdsp, MATCH_C_SDSP, MASK_C_SDSP)
+DECLARE_INSN(c_addi4spn, MATCH_C_ADDI4SPN, MASK_C_ADDI4SPN)
+DECLARE_INSN(c_fld, MATCH_C_FLD, MASK_C_FLD)
+DECLARE_INSN(c_lw, MATCH_C_LW, MASK_C_LW)
+DECLARE_INSN(c_flw, MATCH_C_FLW, MASK_C_FLW)
+DECLARE_INSN(c_fsd, MATCH_C_FSD, MASK_C_FSD)
+DECLARE_INSN(c_sw, MATCH_C_SW, MASK_C_SW)
+DECLARE_INSN(c_fsw, MATCH_C_FSW, MASK_C_FSW)
+DECLARE_INSN(c_addi, MATCH_C_ADDI, MASK_C_ADDI)
+DECLARE_INSN(c_jal, MATCH_C_JAL, MASK_C_JAL)
+DECLARE_INSN(c_li, MATCH_C_LI, MASK_C_LI)
+DECLARE_INSN(c_lui, MATCH_C_LUI, MASK_C_LUI)
+DECLARE_INSN(c_srli, MATCH_C_SRLI, MASK_C_SRLI)
+DECLARE_INSN(c_srai, MATCH_C_SRAI, MASK_C_SRAI)
+DECLARE_INSN(c_andi, MATCH_C_ANDI, MASK_C_ANDI)
+DECLARE_INSN(c_sub, MATCH_C_SUB, MASK_C_SUB)
+DECLARE_INSN(c_xor, MATCH_C_XOR, MASK_C_XOR)
+DECLARE_INSN(c_or, MATCH_C_OR, MASK_C_OR)
+DECLARE_INSN(c_and, MATCH_C_AND, MASK_C_AND)
+DECLARE_INSN(c_subw, MATCH_C_SUBW, MASK_C_SUBW)
+DECLARE_INSN(c_addw, MATCH_C_ADDW, MASK_C_ADDW)
+DECLARE_INSN(c_j, MATCH_C_J, MASK_C_J)
+DECLARE_INSN(c_beqz, MATCH_C_BEQZ, MASK_C_BEQZ)
+DECLARE_INSN(c_bnez, MATCH_C_BNEZ, MASK_C_BNEZ)
+DECLARE_INSN(c_slli, MATCH_C_SLLI, MASK_C_SLLI)
+DECLARE_INSN(c_fldsp, MATCH_C_FLDSP, MASK_C_FLDSP)
+DECLARE_INSN(c_lwsp, MATCH_C_LWSP, MASK_C_LWSP)
+DECLARE_INSN(c_flwsp, MATCH_C_FLWSP, MASK_C_FLWSP)
+DECLARE_INSN(c_mv, MATCH_C_MV, MASK_C_MV)
+DECLARE_INSN(c_add, MATCH_C_ADD, MASK_C_ADD)
+DECLARE_INSN(c_fsdsp, MATCH_C_FSDSP, MASK_C_FSDSP)
+DECLARE_INSN(c_swsp, MATCH_C_SWSP, MASK_C_SWSP)
+DECLARE_INSN(c_fswsp, MATCH_C_FSWSP, MASK_C_FSWSP)
+DECLARE_INSN(custom0, MATCH_CUSTOM0, MASK_CUSTOM0)
+DECLARE_INSN(custom0_rs1, MATCH_CUSTOM0_RS1, MASK_CUSTOM0_RS1)
+DECLARE_INSN(custom0_rs1_rs2, MATCH_CUSTOM0_RS1_RS2, MASK_CUSTOM0_RS1_RS2)
+DECLARE_INSN(custom0_rd, MATCH_CUSTOM0_RD, MASK_CUSTOM0_RD)
+DECLARE_INSN(custom0_rd_rs1, MATCH_CUSTOM0_RD_RS1, MASK_CUSTOM0_RD_RS1)
+DECLARE_INSN(custom0_rd_rs1_rs2, MATCH_CUSTOM0_RD_RS1_RS2, MASK_CUSTOM0_RD_RS1_RS2)
+DECLARE_INSN(custom1, MATCH_CUSTOM1, MASK_CUSTOM1)
+DECLARE_INSN(custom1_rs1, MATCH_CUSTOM1_RS1, MASK_CUSTOM1_RS1)
+DECLARE_INSN(custom1_rs1_rs2, MATCH_CUSTOM1_RS1_RS2, MASK_CUSTOM1_RS1_RS2)
+DECLARE_INSN(custom1_rd, MATCH_CUSTOM1_RD, MASK_CUSTOM1_RD)
+DECLARE_INSN(custom1_rd_rs1, MATCH_CUSTOM1_RD_RS1, MASK_CUSTOM1_RD_RS1)
+DECLARE_INSN(custom1_rd_rs1_rs2, MATCH_CUSTOM1_RD_RS1_RS2, MASK_CUSTOM1_RD_RS1_RS2)
+DECLARE_INSN(custom2, MATCH_CUSTOM2, MASK_CUSTOM2)
+DECLARE_INSN(custom2_rs1, MATCH_CUSTOM2_RS1, MASK_CUSTOM2_RS1)
+DECLARE_INSN(custom2_rs1_rs2, MATCH_CUSTOM2_RS1_RS2, MASK_CUSTOM2_RS1_RS2)
+DECLARE_INSN(custom2_rd, MATCH_CUSTOM2_RD, MASK_CUSTOM2_RD)
+DECLARE_INSN(custom2_rd_rs1, MATCH_CUSTOM2_RD_RS1, MASK_CUSTOM2_RD_RS1)
+DECLARE_INSN(custom2_rd_rs1_rs2, MATCH_CUSTOM2_RD_RS1_RS2, MASK_CUSTOM2_RD_RS1_RS2)
+DECLARE_INSN(custom3, MATCH_CUSTOM3, MASK_CUSTOM3)
+DECLARE_INSN(custom3_rs1, MATCH_CUSTOM3_RS1, MASK_CUSTOM3_RS1)
+DECLARE_INSN(custom3_rs1_rs2, MATCH_CUSTOM3_RS1_RS2, MASK_CUSTOM3_RS1_RS2)
+DECLARE_INSN(custom3_rd, MATCH_CUSTOM3_RD, MASK_CUSTOM3_RD)
+DECLARE_INSN(custom3_rd_rs1, MATCH_CUSTOM3_RD_RS1, MASK_CUSTOM3_RD_RS1)
+DECLARE_INSN(custom3_rd_rs1_rs2, MATCH_CUSTOM3_RD_RS1_RS2, MASK_CUSTOM3_RD_RS1_RS2)
+#endif
+#ifdef DECLARE_CSR
+DECLARE_CSR(fflags, CSR_FFLAGS)
+DECLARE_CSR(frm, CSR_FRM)
+DECLARE_CSR(fcsr, CSR_FCSR)
+DECLARE_CSR(cycle, CSR_CYCLE)
+DECLARE_CSR(time, CSR_TIME)
+DECLARE_CSR(instret, CSR_INSTRET)
+DECLARE_CSR(hpmcounter3, CSR_HPMCOUNTER3)
+DECLARE_CSR(hpmcounter4, CSR_HPMCOUNTER4)
+DECLARE_CSR(hpmcounter5, CSR_HPMCOUNTER5)
+DECLARE_CSR(hpmcounter6, CSR_HPMCOUNTER6)
+DECLARE_CSR(hpmcounter7, CSR_HPMCOUNTER7)
+DECLARE_CSR(hpmcounter8, CSR_HPMCOUNTER8)
+DECLARE_CSR(hpmcounter9, CSR_HPMCOUNTER9)
+DECLARE_CSR(hpmcounter10, CSR_HPMCOUNTER10)
+DECLARE_CSR(hpmcounter11, CSR_HPMCOUNTER11)
+DECLARE_CSR(hpmcounter12, CSR_HPMCOUNTER12)
+DECLARE_CSR(hpmcounter13, CSR_HPMCOUNTER13)
+DECLARE_CSR(hpmcounter14, CSR_HPMCOUNTER14)
+DECLARE_CSR(hpmcounter15, CSR_HPMCOUNTER15)
+DECLARE_CSR(hpmcounter16, CSR_HPMCOUNTER16)
+DECLARE_CSR(hpmcounter17, CSR_HPMCOUNTER17)
+DECLARE_CSR(hpmcounter18, CSR_HPMCOUNTER18)
+DECLARE_CSR(hpmcounter19, CSR_HPMCOUNTER19)
+DECLARE_CSR(hpmcounter20, CSR_HPMCOUNTER20)
+DECLARE_CSR(hpmcounter21, CSR_HPMCOUNTER21)
+DECLARE_CSR(hpmcounter22, CSR_HPMCOUNTER22)
+DECLARE_CSR(hpmcounter23, CSR_HPMCOUNTER23)
+DECLARE_CSR(hpmcounter24, CSR_HPMCOUNTER24)
+DECLARE_CSR(hpmcounter25, CSR_HPMCOUNTER25)
+DECLARE_CSR(hpmcounter26, CSR_HPMCOUNTER26)
+DECLARE_CSR(hpmcounter27, CSR_HPMCOUNTER27)
+DECLARE_CSR(hpmcounter28, CSR_HPMCOUNTER28)
+DECLARE_CSR(hpmcounter29, CSR_HPMCOUNTER29)
+DECLARE_CSR(hpmcounter30, CSR_HPMCOUNTER30)
+DECLARE_CSR(hpmcounter31, CSR_HPMCOUNTER31)
+DECLARE_CSR(sstatus, CSR_SSTATUS)
+DECLARE_CSR(sie, CSR_SIE)
+DECLARE_CSR(stvec, CSR_STVEC)
+DECLARE_CSR(scounteren, CSR_SCOUNTEREN)
+DECLARE_CSR(sscratch, CSR_SSCRATCH)
+DECLARE_CSR(sepc, CSR_SEPC)
+DECLARE_CSR(scause, CSR_SCAUSE)
+DECLARE_CSR(sbadaddr, CSR_SBADADDR)
+DECLARE_CSR(sip, CSR_SIP)
+DECLARE_CSR(sptbr, CSR_SPTBR)
+DECLARE_CSR(mstatus, CSR_MSTATUS)
+DECLARE_CSR(misa, CSR_MISA)
+DECLARE_CSR(medeleg, CSR_MEDELEG)
+DECLARE_CSR(mideleg, CSR_MIDELEG)
+DECLARE_CSR(mie, CSR_MIE)
+DECLARE_CSR(mtvec, CSR_MTVEC)
+DECLARE_CSR(mcounteren, CSR_MCOUNTEREN)
+DECLARE_CSR(mscratch, CSR_MSCRATCH)
+DECLARE_CSR(mepc, CSR_MEPC)
+DECLARE_CSR(mcause, CSR_MCAUSE)
+DECLARE_CSR(mbadaddr, CSR_MBADADDR)
+DECLARE_CSR(mip, CSR_MIP)
+DECLARE_CSR(pmpcfg0, CSR_PMPCFG0)
+DECLARE_CSR(pmpcfg1, CSR_PMPCFG1)
+DECLARE_CSR(pmpcfg2, CSR_PMPCFG2)
+DECLARE_CSR(pmpcfg3, CSR_PMPCFG3)
+DECLARE_CSR(pmpaddr0, CSR_PMPADDR0)
+DECLARE_CSR(pmpaddr1, CSR_PMPADDR1)
+DECLARE_CSR(pmpaddr2, CSR_PMPADDR2)
+DECLARE_CSR(pmpaddr3, CSR_PMPADDR3)
+DECLARE_CSR(pmpaddr4, CSR_PMPADDR4)
+DECLARE_CSR(pmpaddr5, CSR_PMPADDR5)
+DECLARE_CSR(pmpaddr6, CSR_PMPADDR6)
+DECLARE_CSR(pmpaddr7, CSR_PMPADDR7)
+DECLARE_CSR(pmpaddr8, CSR_PMPADDR8)
+DECLARE_CSR(pmpaddr9, CSR_PMPADDR9)
+DECLARE_CSR(pmpaddr10, CSR_PMPADDR10)
+DECLARE_CSR(pmpaddr11, CSR_PMPADDR11)
+DECLARE_CSR(pmpaddr12, CSR_PMPADDR12)
+DECLARE_CSR(pmpaddr13, CSR_PMPADDR13)
+DECLARE_CSR(pmpaddr14, CSR_PMPADDR14)
+DECLARE_CSR(pmpaddr15, CSR_PMPADDR15)
+DECLARE_CSR(tselect, CSR_TSELECT)
+DECLARE_CSR(tdata1, CSR_TDATA1)
+DECLARE_CSR(tdata2, CSR_TDATA2)
+DECLARE_CSR(tdata3, CSR_TDATA3)
+DECLARE_CSR(dcsr, CSR_DCSR)
+DECLARE_CSR(dpc, CSR_DPC)
+DECLARE_CSR(dscratch, CSR_DSCRATCH)
+DECLARE_CSR(mcycle, CSR_MCYCLE)
+DECLARE_CSR(minstret, CSR_MINSTRET)
+DECLARE_CSR(mhpmcounter3, CSR_MHPMCOUNTER3)
+DECLARE_CSR(mhpmcounter4, CSR_MHPMCOUNTER4)
+DECLARE_CSR(mhpmcounter5, CSR_MHPMCOUNTER5)
+DECLARE_CSR(mhpmcounter6, CSR_MHPMCOUNTER6)
+DECLARE_CSR(mhpmcounter7, CSR_MHPMCOUNTER7)
+DECLARE_CSR(mhpmcounter8, CSR_MHPMCOUNTER8)
+DECLARE_CSR(mhpmcounter9, CSR_MHPMCOUNTER9)
+DECLARE_CSR(mhpmcounter10, CSR_MHPMCOUNTER10)
+DECLARE_CSR(mhpmcounter11, CSR_MHPMCOUNTER11)
+DECLARE_CSR(mhpmcounter12, CSR_MHPMCOUNTER12)
+DECLARE_CSR(mhpmcounter13, CSR_MHPMCOUNTER13)
+DECLARE_CSR(mhpmcounter14, CSR_MHPMCOUNTER14)
+DECLARE_CSR(mhpmcounter15, CSR_MHPMCOUNTER15)
+DECLARE_CSR(mhpmcounter16, CSR_MHPMCOUNTER16)
+DECLARE_CSR(mhpmcounter17, CSR_MHPMCOUNTER17)
+DECLARE_CSR(mhpmcounter18, CSR_MHPMCOUNTER18)
+DECLARE_CSR(mhpmcounter19, CSR_MHPMCOUNTER19)
+DECLARE_CSR(mhpmcounter20, CSR_MHPMCOUNTER20)
+DECLARE_CSR(mhpmcounter21, CSR_MHPMCOUNTER21)
+DECLARE_CSR(mhpmcounter22, CSR_MHPMCOUNTER22)
+DECLARE_CSR(mhpmcounter23, CSR_MHPMCOUNTER23)
+DECLARE_CSR(mhpmcounter24, CSR_MHPMCOUNTER24)
+DECLARE_CSR(mhpmcounter25, CSR_MHPMCOUNTER25)
+DECLARE_CSR(mhpmcounter26, CSR_MHPMCOUNTER26)
+DECLARE_CSR(mhpmcounter27, CSR_MHPMCOUNTER27)
+DECLARE_CSR(mhpmcounter28, CSR_MHPMCOUNTER28)
+DECLARE_CSR(mhpmcounter29, CSR_MHPMCOUNTER29)
+DECLARE_CSR(mhpmcounter30, CSR_MHPMCOUNTER30)
+DECLARE_CSR(mhpmcounter31, CSR_MHPMCOUNTER31)
+DECLARE_CSR(mhpmevent3, CSR_MHPMEVENT3)
+DECLARE_CSR(mhpmevent4, CSR_MHPMEVENT4)
+DECLARE_CSR(mhpmevent5, CSR_MHPMEVENT5)
+DECLARE_CSR(mhpmevent6, CSR_MHPMEVENT6)
+DECLARE_CSR(mhpmevent7, CSR_MHPMEVENT7)
+DECLARE_CSR(mhpmevent8, CSR_MHPMEVENT8)
+DECLARE_CSR(mhpmevent9, CSR_MHPMEVENT9)
+DECLARE_CSR(mhpmevent10, CSR_MHPMEVENT10)
+DECLARE_CSR(mhpmevent11, CSR_MHPMEVENT11)
+DECLARE_CSR(mhpmevent12, CSR_MHPMEVENT12)
+DECLARE_CSR(mhpmevent13, CSR_MHPMEVENT13)
+DECLARE_CSR(mhpmevent14, CSR_MHPMEVENT14)
+DECLARE_CSR(mhpmevent15, CSR_MHPMEVENT15)
+DECLARE_CSR(mhpmevent16, CSR_MHPMEVENT16)
+DECLARE_CSR(mhpmevent17, CSR_MHPMEVENT17)
+DECLARE_CSR(mhpmevent18, CSR_MHPMEVENT18)
+DECLARE_CSR(mhpmevent19, CSR_MHPMEVENT19)
+DECLARE_CSR(mhpmevent20, CSR_MHPMEVENT20)
+DECLARE_CSR(mhpmevent21, CSR_MHPMEVENT21)
+DECLARE_CSR(mhpmevent22, CSR_MHPMEVENT22)
+DECLARE_CSR(mhpmevent23, CSR_MHPMEVENT23)
+DECLARE_CSR(mhpmevent24, CSR_MHPMEVENT24)
+DECLARE_CSR(mhpmevent25, CSR_MHPMEVENT25)
+DECLARE_CSR(mhpmevent26, CSR_MHPMEVENT26)
+DECLARE_CSR(mhpmevent27, CSR_MHPMEVENT27)
+DECLARE_CSR(mhpmevent28, CSR_MHPMEVENT28)
+DECLARE_CSR(mhpmevent29, CSR_MHPMEVENT29)
+DECLARE_CSR(mhpmevent30, CSR_MHPMEVENT30)
+DECLARE_CSR(mhpmevent31, CSR_MHPMEVENT31)
+DECLARE_CSR(mvendorid, CSR_MVENDORID)
+DECLARE_CSR(marchid, CSR_MARCHID)
+DECLARE_CSR(mimpid, CSR_MIMPID)
+DECLARE_CSR(mhartid, CSR_MHARTID)
+DECLARE_CSR(cycleh, CSR_CYCLEH)
+DECLARE_CSR(timeh, CSR_TIMEH)
+DECLARE_CSR(instreth, CSR_INSTRETH)
+DECLARE_CSR(hpmcounter3h, CSR_HPMCOUNTER3H)
+DECLARE_CSR(hpmcounter4h, CSR_HPMCOUNTER4H)
+DECLARE_CSR(hpmcounter5h, CSR_HPMCOUNTER5H)
+DECLARE_CSR(hpmcounter6h, CSR_HPMCOUNTER6H)
+DECLARE_CSR(hpmcounter7h, CSR_HPMCOUNTER7H)
+DECLARE_CSR(hpmcounter8h, CSR_HPMCOUNTER8H)
+DECLARE_CSR(hpmcounter9h, CSR_HPMCOUNTER9H)
+DECLARE_CSR(hpmcounter10h, CSR_HPMCOUNTER10H)
+DECLARE_CSR(hpmcounter11h, CSR_HPMCOUNTER11H)
+DECLARE_CSR(hpmcounter12h, CSR_HPMCOUNTER12H)
+DECLARE_CSR(hpmcounter13h, CSR_HPMCOUNTER13H)
+DECLARE_CSR(hpmcounter14h, CSR_HPMCOUNTER14H)
+DECLARE_CSR(hpmcounter15h, CSR_HPMCOUNTER15H)
+DECLARE_CSR(hpmcounter16h, CSR_HPMCOUNTER16H)
+DECLARE_CSR(hpmcounter17h, CSR_HPMCOUNTER17H)
+DECLARE_CSR(hpmcounter18h, CSR_HPMCOUNTER18H)
+DECLARE_CSR(hpmcounter19h, CSR_HPMCOUNTER19H)
+DECLARE_CSR(hpmcounter20h, CSR_HPMCOUNTER20H)
+DECLARE_CSR(hpmcounter21h, CSR_HPMCOUNTER21H)
+DECLARE_CSR(hpmcounter22h, CSR_HPMCOUNTER22H)
+DECLARE_CSR(hpmcounter23h, CSR_HPMCOUNTER23H)
+DECLARE_CSR(hpmcounter24h, CSR_HPMCOUNTER24H)
+DECLARE_CSR(hpmcounter25h, CSR_HPMCOUNTER25H)
+DECLARE_CSR(hpmcounter26h, CSR_HPMCOUNTER26H)
+DECLARE_CSR(hpmcounter27h, CSR_HPMCOUNTER27H)
+DECLARE_CSR(hpmcounter28h, CSR_HPMCOUNTER28H)
+DECLARE_CSR(hpmcounter29h, CSR_HPMCOUNTER29H)
+DECLARE_CSR(hpmcounter30h, CSR_HPMCOUNTER30H)
+DECLARE_CSR(hpmcounter31h, CSR_HPMCOUNTER31H)
+DECLARE_CSR(mcycleh, CSR_MCYCLEH)
+DECLARE_CSR(minstreth, CSR_MINSTRETH)
+DECLARE_CSR(mhpmcounter3h, CSR_MHPMCOUNTER3H)
+DECLARE_CSR(mhpmcounter4h, CSR_MHPMCOUNTER4H)
+DECLARE_CSR(mhpmcounter5h, CSR_MHPMCOUNTER5H)
+DECLARE_CSR(mhpmcounter6h, CSR_MHPMCOUNTER6H)
+DECLARE_CSR(mhpmcounter7h, CSR_MHPMCOUNTER7H)
+DECLARE_CSR(mhpmcounter8h, CSR_MHPMCOUNTER8H)
+DECLARE_CSR(mhpmcounter9h, CSR_MHPMCOUNTER9H)
+DECLARE_CSR(mhpmcounter10h, CSR_MHPMCOUNTER10H)
+DECLARE_CSR(mhpmcounter11h, CSR_MHPMCOUNTER11H)
+DECLARE_CSR(mhpmcounter12h, CSR_MHPMCOUNTER12H)
+DECLARE_CSR(mhpmcounter13h, CSR_MHPMCOUNTER13H)
+DECLARE_CSR(mhpmcounter14h, CSR_MHPMCOUNTER14H)
+DECLARE_CSR(mhpmcounter15h, CSR_MHPMCOUNTER15H)
+DECLARE_CSR(mhpmcounter16h, CSR_MHPMCOUNTER16H)
+DECLARE_CSR(mhpmcounter17h, CSR_MHPMCOUNTER17H)
+DECLARE_CSR(mhpmcounter18h, CSR_MHPMCOUNTER18H)
+DECLARE_CSR(mhpmcounter19h, CSR_MHPMCOUNTER19H)
+DECLARE_CSR(mhpmcounter20h, CSR_MHPMCOUNTER20H)
+DECLARE_CSR(mhpmcounter21h, CSR_MHPMCOUNTER21H)
+DECLARE_CSR(mhpmcounter22h, CSR_MHPMCOUNTER22H)
+DECLARE_CSR(mhpmcounter23h, CSR_MHPMCOUNTER23H)
+DECLARE_CSR(mhpmcounter24h, CSR_MHPMCOUNTER24H)
+DECLARE_CSR(mhpmcounter25h, CSR_MHPMCOUNTER25H)
+DECLARE_CSR(mhpmcounter26h, CSR_MHPMCOUNTER26H)
+DECLARE_CSR(mhpmcounter27h, CSR_MHPMCOUNTER27H)
+DECLARE_CSR(mhpmcounter28h, CSR_MHPMCOUNTER28H)
+DECLARE_CSR(mhpmcounter29h, CSR_MHPMCOUNTER29H)
+DECLARE_CSR(mhpmcounter30h, CSR_MHPMCOUNTER30H)
+DECLARE_CSR(mhpmcounter31h, CSR_MHPMCOUNTER31H)
+#endif
+#ifdef DECLARE_CAUSE
+DECLARE_CAUSE("misaligned fetch", CAUSE_MISALIGNED_FETCH)
+DECLARE_CAUSE("fetch access", CAUSE_FETCH_ACCESS)
+DECLARE_CAUSE("illegal instruction", CAUSE_ILLEGAL_INSTRUCTION)
+DECLARE_CAUSE("breakpoint", CAUSE_BREAKPOINT)
+DECLARE_CAUSE("misaligned load", CAUSE_MISALIGNED_LOAD)
+DECLARE_CAUSE("load access", CAUSE_LOAD_ACCESS)
+DECLARE_CAUSE("misaligned store", CAUSE_MISALIGNED_STORE)
+DECLARE_CAUSE("store access", CAUSE_STORE_ACCESS)
+DECLARE_CAUSE("user_ecall", CAUSE_USER_ECALL)
+DECLARE_CAUSE("supervisor_ecall", CAUSE_SUPERVISOR_ECALL)
+DECLARE_CAUSE("hypervisor_ecall", CAUSE_HYPERVISOR_ECALL)
+DECLARE_CAUSE("machine_ecall", CAUSE_MACHINE_ECALL)
+DECLARE_CAUSE("fetch page fault", CAUSE_FETCH_PAGE_FAULT)
+DECLARE_CAUSE("load page fault", CAUSE_LOAD_PAGE_FAULT)
+DECLARE_CAUSE("store page fault", CAUSE_STORE_PAGE_FAULT)
+#endif
+
+#include "scr1_specific.h"
Index: yifive/trunk/caravel_yifive/verilog/rtl/syntacore/scr1/sim/tests/common/riscv_macros.h
===================================================================
--- yifive/trunk/caravel_yifive/verilog/rtl/syntacore/scr1/sim/tests/common/riscv_macros.h (nonexistent)
+++ yifive/trunk/caravel_yifive/verilog/rtl/syntacore/scr1/sim/tests/common/riscv_macros.h (revision 22)
@@ -0,0 +1,819 @@
+// See LICENSE for license details.
+
+#ifndef __RISCV_MACROS_H
+#define __RISCV_MACROS_H
+
+#include "riscv_csr_encoding.h"
+#include "sc_test.h"
+
+//-----------------------------------------------------------------------
+// Begin Macro
+//-----------------------------------------------------------------------
+
+#define RVTEST_RV64U \
+ .macro init; \
+ .endm
+
+#define RVTEST_RV64UF \
+ .macro init; \
+ RVTEST_FP_ENABLE; \
+ .endm
+
+#define RVTEST_RV32U \
+ .macro init; \
+ .endm
+
+#define RVTEST_RV32UF \
+ .macro init; \
+ RVTEST_FP_ENABLE; \
+ .endm
+
+#define RVTEST_RV64M \
+ .macro init; \
+ RVTEST_ENABLE_MACHINE; \
+ .endm
+
+#define RVTEST_RV64S \
+ .macro init; \
+ RVTEST_ENABLE_SUPERVISOR; \
+ .endm
+
+#define RVTEST_RV32M \
+ .macro init; \
+ RVTEST_ENABLE_MACHINE; \
+ .endm
+
+#define RVTEST_RV32S \
+ .macro init; \
+ RVTEST_ENABLE_SUPERVISOR; \
+ .endm
+
+#if __riscv_xlen == 64
+# define CHECK_XLEN li a0, 1; slli a0, a0, 31; bgez a0, 1f; RVTEST_PASS; 1:
+#else
+# define CHECK_XLEN li a0, 1; slli a0, a0, 31; bltz a0, 1f; RVTEST_PASS; 1:
+#endif
+
+#define INIT_PMP \
+ la t0, 1f; \
+ csrw mtvec, t0; \
+ li t0, -1; /* Set up a PMP to permit all accesses */ \
+ csrw pmpaddr0, t0; \
+ li t0, PMP_NAPOT | PMP_R | PMP_W | PMP_X; \
+ csrw pmpcfg0, t0; \
+ .balign 4; \
+1:
+
+#define INIT_SPTBR \
+ la t0, 1f; \
+ csrw mtvec, t0; \
+ csrwi sptbr, 0; \
+ .balign 4; \
+1:
+
+#define DELEGATE_NO_TRAPS
+
+#define RVTEST_ENABLE_SUPERVISOR \
+ li a0, MSTATUS_MPP & (MSTATUS_MPP >> 1); \
+ csrs mstatus, a0; \
+ li a0, SIP_SSIP | SIP_STIP; \
+ csrs mideleg, a0; \
+
+#define RVTEST_ENABLE_MACHINE \
+ li a0, MSTATUS_MPP; \
+ csrs mstatus, a0; \
+
+#define RVTEST_FP_ENABLE \
+ li a0, MSTATUS_FS & (MSTATUS_FS >> 1); \
+ csrs mstatus, a0; \
+ csrwi fcsr, 0
+
+#define RISCV_MULTICORE_DISABLE \
+ csrr a0, mhartid; \
+ 1: bnez a0, 1b
+
+#define EXTRA_TVEC_USER
+#define EXTRA_TVEC_SUPERVISOR
+#define EXTRA_TVEC_HYPERVISOR
+#define EXTRA_TVEC_MACHINE
+#define EXTRA_INIT
+#define EXTRA_INIT_TIMER
+
+#define INTERRUPT_HANDLER j other_exception /* No interrupts should occur */
+
+#define RVTEST_CODE_BEGIN \
+ .section .text.init; \
+ .org 0xC0, 0x00; \
+ .balign 64; \
+ .weak stvec_handler; \
+ .weak mtvec_handler; \
+trap_vector: \
+ /* test whether the test came from pass/fail */ \
+ csrr a4, mcause; \
+ li a5, CAUSE_USER_ECALL; \
+ beq a4, a5, _report; \
+ li a5, CAUSE_SUPERVISOR_ECALL; \
+ beq a4, a5, _report; \
+ li a5, CAUSE_MACHINE_ECALL; \
+ beq a4, a5, _report; \
+ /* if an mtvec_handler is defined, jump to it */ \
+ la a4, mtvec_handler; \
+ beqz a4, 1f; \
+ jr a4; \
+ /* was it an interrupt or an exception? */ \
+1: csrr a4, mcause; \
+ bgez a4, handle_exception; \
+ INTERRUPT_HANDLER; \
+handle_exception: \
+ /* we don't know how to handle whatever the exception was */ \
+other_exception: \
+ /* some unhandlable exception occurred */ \
+ li a0, 0x1; \
+_report: \
+ j sc_exit; \
+ .balign 64; \
+ .globl _start; \
+_start: \
+ RISCV_MULTICORE_DISABLE; \
+ /*INIT_SPTBR;*/ \
+ /*INIT_PMP;*/ \
+ DELEGATE_NO_TRAPS; \
+ li TESTNUM, 0; \
+ la t0, trap_vector; \
+ csrw mtvec, t0; \
+ CHECK_XLEN; \
+ /* if an stvec_handler is defined, delegate exceptions to it */ \
+ la t0, stvec_handler; \
+ beqz t0, 1f; \
+ csrw stvec, t0; \
+ li t0, (1 << CAUSE_LOAD_PAGE_FAULT) | \
+ (1 << CAUSE_STORE_PAGE_FAULT) | \
+ (1 << CAUSE_FETCH_PAGE_FAULT) | \
+ (1 << CAUSE_MISALIGNED_FETCH) | \
+ (1 << CAUSE_USER_ECALL) | \
+ (1 << CAUSE_BREAKPOINT); \
+ csrw medeleg, t0; \
+ csrr t1, medeleg; \
+ bne t0, t1, other_exception; \
+1: csrwi mstatus, 0; \
+ init; \
+ EXTRA_INIT; \
+ EXTRA_INIT_TIMER; \
+ la t0, _run_test; \
+ csrw mepc, t0; \
+ csrr a0, mhartid; \
+ mret; \
+ .section .text; \
+_run_test:
+
+//-----------------------------------------------------------------------
+// End Macro
+//-----------------------------------------------------------------------
+
+#define RVTEST_CODE_END ecall: ecall
+
+//-----------------------------------------------------------------------
+// Pass/Fail Macro
+//-----------------------------------------------------------------------
+
+#define RVTEST_PASS \
+ fence; \
+ mv a1, TESTNUM; \
+ li a0, 0x0; \
+ ecall
+
+#define TESTNUM x28
+#define RVTEST_FAIL \
+ fence; \
+ mv a1, TESTNUM; \
+ li a0, 0x1; \
+ ecall
+
+//-----------------------------------------------------------------------
+// Data Section Macro
+//-----------------------------------------------------------------------
+
+#define EXTRA_DATA
+
+#define RVTEST_DATA_BEGIN \
+ EXTRA_DATA \
+ .pushsection .tohost,"aw",@progbits; \
+ .balign 64; .global tohost; tohost: .dword 0; \
+ .balign 64; .global fromhost; fromhost: .dword 0; \
+ .popsection; \
+ .balign 16; \
+ .global begin_regstate; begin_regstate: .dword 0; .dword 0; .dword 0; \
+ .balign 16; \
+ .global begin_signature; begin_signature:
+
+#define RVTEST_DATA_END .balign 16; .global end_signature; end_signature:
+
+#-----------------------------------------------------------------------
+# Helper macros
+#-----------------------------------------------------------------------
+
+#define MASK_XLEN(x) ((x) & ((1 << (__riscv_xlen - 1) << 1) - 1))
+
+#define TEST_CASE( testnum, testreg, correctval, code... ) \
+test_ ## testnum: \
+ code; \
+ li x29, MASK_XLEN(correctval); \
+ li TESTNUM, testnum; \
+ bne testreg, x29, fail;
+
+# We use a macro hack to simpify code generation for various numbers
+# of bubble cycles.
+
+#define TEST_INSERT_NOPS_0
+#define TEST_INSERT_NOPS_1 nop; TEST_INSERT_NOPS_0
+#define TEST_INSERT_NOPS_2 nop; TEST_INSERT_NOPS_1
+#define TEST_INSERT_NOPS_3 nop; TEST_INSERT_NOPS_2
+#define TEST_INSERT_NOPS_4 nop; TEST_INSERT_NOPS_3
+#define TEST_INSERT_NOPS_5 nop; TEST_INSERT_NOPS_4
+#define TEST_INSERT_NOPS_6 nop; TEST_INSERT_NOPS_5
+#define TEST_INSERT_NOPS_7 nop; TEST_INSERT_NOPS_6
+#define TEST_INSERT_NOPS_8 nop; TEST_INSERT_NOPS_7
+#define TEST_INSERT_NOPS_9 nop; TEST_INSERT_NOPS_8
+#define TEST_INSERT_NOPS_10 nop; TEST_INSERT_NOPS_9
+
+
+#-----------------------------------------------------------------------
+# RV64UI MACROS
+#-----------------------------------------------------------------------
+
+#-----------------------------------------------------------------------
+# Tests for instructions with immediate operand
+#-----------------------------------------------------------------------
+
+#define SEXT_IMM(x) ((x) | (-(((x) >> 11) & 1) << 11))
+
+#define TEST_IMM_OP( testnum, inst, result, val1, imm ) \
+ TEST_CASE( testnum, x3, result, \
+ li x1, MASK_XLEN(val1); \
+ inst x3, x1, SEXT_IMM(imm); \
+ )
+
+#define TEST_IMM_OP_RVC( testnum, inst, result, val1, imm ) \
+ TEST_CASE( testnum, x1, result, \
+ li x1, val1; \
+ inst x1, imm; \
+ )
+
+#define TEST_IMM_SRC1_EQ_DEST( testnum, inst, result, val1, imm ) \
+ TEST_CASE( testnum, x1, result, \
+ li x1, MASK_XLEN(val1); \
+ inst x1, x1, SEXT_IMM(imm); \
+ )
+
+#define TEST_IMM_DEST_BYPASS( testnum, nop_cycles, inst, result, val1, imm ) \
+ TEST_CASE( testnum, x6, result, \
+ li x4, 0; \
+1: li x1, MASK_XLEN(val1); \
+ inst x3, x1, SEXT_IMM(imm); \
+ TEST_INSERT_NOPS_ ## nop_cycles \
+ addi x6, x3, 0; \
+ addi x4, x4, 1; \
+ li x5, 2; \
+ bne x4, x5, 1b \
+ )
+
+#define TEST_IMM_SRC1_BYPASS( testnum, nop_cycles, inst, result, val1, imm ) \
+ TEST_CASE( testnum, x3, result, \
+ li x4, 0; \
+1: li x1, MASK_XLEN(val1); \
+ TEST_INSERT_NOPS_ ## nop_cycles \
+ inst x3, x1, SEXT_IMM(imm); \
+ addi x4, x4, 1; \
+ li x5, 2; \
+ bne x4, x5, 1b \
+ )
+
+#define TEST_IMM_ZEROSRC1( testnum, inst, result, imm ) \
+ TEST_CASE( testnum, x1, result, \
+ inst x1, x0, SEXT_IMM(imm); \
+ )
+
+#define TEST_IMM_ZERODEST( testnum, inst, val1, imm ) \
+ TEST_CASE( testnum, x0, 0, \
+ li x1, MASK_XLEN(val1); \
+ inst x0, x1, SEXT_IMM(imm); \
+ )
+
+#-----------------------------------------------------------------------
+# Tests for vector config instructions
+#-----------------------------------------------------------------------
+
+#define TEST_VSETCFGIVL( testnum, nxpr, nfpr, bank, vl, result ) \
+ TEST_CASE( testnum, x1, result, \
+ li x1, (bank << 12); \
+ vsetcfg x1,nxpr,nfpr; \
+ li x1, vl; \
+ vsetvl x1,x1; \
+ )
+
+#define TEST_VVCFG( testnum, nxpr, nfpr, bank, vl, result ) \
+ TEST_CASE( testnum, x1, result, \
+ li x1, (bank << 12) | (nfpr << 6) | nxpr; \
+ vsetcfg x1; \
+ li x1, vl; \
+ vsetvl x1,x1; \
+ )
+
+#define TEST_VSETVL( testnum, nxpr, nfpr, bank, vl, result ) \
+ TEST_CASE( testnum, x1, result, \
+ li x1, (bank << 12); \
+ vsetcfg x1,nxpr,nfpr; \
+ li x1, vl; \
+ vsetvl x1, x1; \
+ )
+
+#-----------------------------------------------------------------------
+# Tests for an instruction with register operands
+#-----------------------------------------------------------------------
+
+#define TEST_R_OP( testnum, inst, result, val1 ) \
+ TEST_CASE( testnum, x3, result, \
+ li x1, val1; \
+ inst x3, x1; \
+ )
+
+#define TEST_R_SRC1_EQ_DEST( testnum, inst, result, val1 ) \
+ TEST_CASE( testnum, x1, result, \
+ li x1, val1; \
+ inst x1, x1; \
+ )
+
+#define TEST_R_DEST_BYPASS( testnum, nop_cycles, inst, result, val1 ) \
+ TEST_CASE( testnum, x6, result, \
+ li x4, 0; \
+1: li x1, val1; \
+ inst x3, x1; \
+ TEST_INSERT_NOPS_ ## nop_cycles \
+ addi x6, x3, 0; \
+ addi x4, x4, 1; \
+ li x5, 2; \
+ bne x4, x5, 1b \
+ )
+
+#-----------------------------------------------------------------------
+# Tests for an instruction with register-register operands
+#-----------------------------------------------------------------------
+
+#define TEST_RR_OP( testnum, inst, result, val1, val2 ) \
+ TEST_CASE( testnum, x3, result, \
+ li x1, MASK_XLEN(val1); \
+ li x2, MASK_XLEN(val2); \
+ inst x3, x1, x2; \
+ )
+
+#define TEST_RR_SRC1_EQ_DEST( testnum, inst, result, val1, val2 ) \
+ TEST_CASE( testnum, x1, result, \
+ li x1, MASK_XLEN(val1); \
+ li x2, MASK_XLEN(val2); \
+ inst x1, x1, x2; \
+ )
+
+#define TEST_RR_SRC2_EQ_DEST( testnum, inst, result, val1, val2 ) \
+ TEST_CASE( testnum, x2, result, \
+ li x1, MASK_XLEN(val1); \
+ li x2, MASK_XLEN(val2); \
+ inst x2, x1, x2; \
+ )
+
+#define TEST_RR_SRC12_EQ_DEST( testnum, inst, result, val1 ) \
+ TEST_CASE( testnum, x1, result, \
+ li x1, MASK_XLEN(val1); \
+ inst x1, x1, x1; \
+ )
+
+#define TEST_RR_DEST_BYPASS( testnum, nop_cycles, inst, result, val1, val2 ) \
+ TEST_CASE( testnum, x6, result, \
+ li x4, 0; \
+1: li x1, MASK_XLEN(val1); \
+ li x2, MASK_XLEN(val2); \
+ inst x3, x1, x2; \
+ TEST_INSERT_NOPS_ ## nop_cycles \
+ addi x6, x3, 0; \
+ addi x4, x4, 1; \
+ li x5, 2; \
+ bne x4, x5, 1b \
+ )
+
+#define TEST_RR_SRC12_BYPASS( testnum, src1_nops, src2_nops, inst, result, val1, val2 ) \
+ TEST_CASE( testnum, x3, result, \
+ li x4, 0; \
+1: li x1, MASK_XLEN(val1); \
+ TEST_INSERT_NOPS_ ## src1_nops \
+ li x2, MASK_XLEN(val2); \
+ TEST_INSERT_NOPS_ ## src2_nops \
+ inst x3, x1, x2; \
+ addi x4, x4, 1; \
+ li x5, 2; \
+ bne x4, x5, 1b \
+ )
+
+#define TEST_RR_SRC21_BYPASS( testnum, src1_nops, src2_nops, inst, result, val1, val2 ) \
+ TEST_CASE( testnum, x3, result, \
+ li x4, 0; \
+1: li x2, MASK_XLEN(val2); \
+ TEST_INSERT_NOPS_ ## src1_nops \
+ li x1, MASK_XLEN(val1); \
+ TEST_INSERT_NOPS_ ## src2_nops \
+ inst x3, x1, x2; \
+ addi x4, x4, 1; \
+ li x5, 2; \
+ bne x4, x5, 1b \
+ )
+
+#define TEST_RR_ZEROSRC1( testnum, inst, result, val ) \
+ TEST_CASE( testnum, x2, result, \
+ li x1, MASK_XLEN(val); \
+ inst x2, x0, x1; \
+ )
+
+#define TEST_RR_ZEROSRC2( testnum, inst, result, val ) \
+ TEST_CASE( testnum, x2, result, \
+ li x1, MASK_XLEN(val); \
+ inst x2, x1, x0; \
+ )
+
+#define TEST_RR_ZEROSRC12( testnum, inst, result ) \
+ TEST_CASE( testnum, x1, result, \
+ inst x1, x0, x0; \
+ )
+
+#define TEST_RR_ZERODEST( testnum, inst, val1, val2 ) \
+ TEST_CASE( testnum, x0, 0, \
+ li x1, MASK_XLEN(val1); \
+ li x2, MASK_XLEN(val2); \
+ inst x0, x1, x2; \
+ )
+
+#-----------------------------------------------------------------------
+# Test memory instructions
+#-----------------------------------------------------------------------
+
+#define TEST_LD_OP( testnum, inst, result, offset, base ) \
+ TEST_CASE( testnum, x3, result, \
+ la x1, base; \
+ inst x3, offset(x1); \
+ )
+
+#define TEST_ST_OP( testnum, load_inst, store_inst, result, offset, base ) \
+ TEST_CASE( testnum, x3, result, \
+ la x1, base; \
+ li x2, result; \
+ store_inst x2, offset(x1); \
+ load_inst x3, offset(x1); \
+ )
+
+#define TEST_LD_DEST_BYPASS( testnum, nop_cycles, inst, result, offset, base ) \
+test_ ## testnum: \
+ li TESTNUM, testnum; \
+ li x4, 0; \
+1: la x1, base; \
+ inst x3, offset(x1); \
+ TEST_INSERT_NOPS_ ## nop_cycles \
+ addi x6, x3, 0; \
+ li x29, result; \
+ bne x6, x29, fail; \
+ addi x4, x4, 1; \
+ li x5, 2; \
+ bne x4, x5, 1b; \
+
+#define TEST_LD_SRC1_BYPASS( testnum, nop_cycles, inst, result, offset, base ) \
+test_ ## testnum: \
+ li TESTNUM, testnum; \
+ li x4, 0; \
+1: la x1, base; \
+ TEST_INSERT_NOPS_ ## nop_cycles \
+ inst x3, offset(x1); \
+ li x29, result; \
+ bne x3, x29, fail; \
+ addi x4, x4, 1; \
+ li x5, 2; \
+ bne x4, x5, 1b \
+
+#define TEST_ST_SRC12_BYPASS( testnum, src1_nops, src2_nops, load_inst, store_inst, result, offset, base ) \
+test_ ## testnum: \
+ li TESTNUM, testnum; \
+ li x4, 0; \
+1: li x1, result; \
+ TEST_INSERT_NOPS_ ## src1_nops \
+ la x2, base; \
+ TEST_INSERT_NOPS_ ## src2_nops \
+ store_inst x1, offset(x2); \
+ load_inst x3, offset(x2); \
+ li x29, result; \
+ bne x3, x29, fail; \
+ addi x4, x4, 1; \
+ li x5, 2; \
+ bne x4, x5, 1b \
+
+#define TEST_ST_SRC21_BYPASS( testnum, src1_nops, src2_nops, load_inst, store_inst, result, offset, base ) \
+test_ ## testnum: \
+ li TESTNUM, testnum; \
+ li x4, 0; \
+1: la x2, base; \
+ TEST_INSERT_NOPS_ ## src1_nops \
+ li x1, result; \
+ TEST_INSERT_NOPS_ ## src2_nops \
+ store_inst x1, offset(x2); \
+ load_inst x3, offset(x2); \
+ li x29, result; \
+ bne x3, x29, fail; \
+ addi x4, x4, 1; \
+ li x5, 2; \
+ bne x4, x5, 1b \
+
+#-----------------------------------------------------------------------
+# Test branch instructions
+#-----------------------------------------------------------------------
+
+#define TEST_BR1_OP_TAKEN( testnum, inst, val1 ) \
+test_ ## testnum: \
+ li TESTNUM, testnum; \
+ li x1, val1; \
+ inst x1, 2f; \
+ bne x0, TESTNUM, fail; \
+1: bne x0, TESTNUM, 3f; \
+2: inst x1, 1b; \
+ bne x0, TESTNUM, fail; \
+3:
+
+#define TEST_BR1_OP_NOTTAKEN( testnum, inst, val1 ) \
+test_ ## testnum: \
+ li TESTNUM, testnum; \
+ li x1, val1; \
+ inst x1, 1f; \
+ bne x0, TESTNUM, 2f; \
+1: bne x0, TESTNUM, fail; \
+2: inst x1, 1b; \
+3:
+
+#define TEST_BR1_SRC1_BYPASS( testnum, nop_cycles, inst, val1 ) \
+test_ ## testnum: \
+ li TESTNUM, testnum; \
+ li x4, 0; \
+1: li x1, val1; \
+ TEST_INSERT_NOPS_ ## nop_cycles \
+ inst x1, fail; \
+ addi x4, x4, 1; \
+ li x5, 2; \
+ bne x4, x5, 1b \
+
+#define TEST_BR2_OP_TAKEN( testnum, inst, val1, val2 ) \
+test_ ## testnum: \
+ li TESTNUM, testnum; \
+ li x1, val1; \
+ li x2, val2; \
+ inst x1, x2, 2f; \
+ bne x0, TESTNUM, fail; \
+1: bne x0, TESTNUM, 3f; \
+2: inst x1, x2, 1b; \
+ bne x0, TESTNUM, fail; \
+3:
+
+#define TEST_BR2_OP_NOTTAKEN( testnum, inst, val1, val2 ) \
+test_ ## testnum: \
+ li TESTNUM, testnum; \
+ li x1, val1; \
+ li x2, val2; \
+ inst x1, x2, 1f; \
+ bne x0, TESTNUM, 2f; \
+1: bne x0, TESTNUM, fail; \
+2: inst x1, x2, 1b; \
+3:
+
+#define TEST_BR2_SRC12_BYPASS( testnum, src1_nops, src2_nops, inst, val1, val2 ) \
+test_ ## testnum: \
+ li TESTNUM, testnum; \
+ li x4, 0; \
+1: li x1, val1; \
+ TEST_INSERT_NOPS_ ## src1_nops \
+ li x2, val2; \
+ TEST_INSERT_NOPS_ ## src2_nops \
+ inst x1, x2, fail; \
+ addi x4, x4, 1; \
+ li x5, 2; \
+ bne x4, x5, 1b \
+
+#define TEST_BR2_SRC21_BYPASS( testnum, src1_nops, src2_nops, inst, val1, val2 ) \
+test_ ## testnum: \
+ li TESTNUM, testnum; \
+ li x4, 0; \
+1: li x2, val2; \
+ TEST_INSERT_NOPS_ ## src1_nops \
+ li x1, val1; \
+ TEST_INSERT_NOPS_ ## src2_nops \
+ inst x1, x2, fail; \
+ addi x4, x4, 1; \
+ li x5, 2; \
+ bne x4, x5, 1b \
+
+#-----------------------------------------------------------------------
+# Test jump instructions
+#-----------------------------------------------------------------------
+
+#define TEST_JR_SRC1_BYPASS( testnum, nop_cycles, inst ) \
+test_ ## testnum: \
+ li TESTNUM, testnum; \
+ li x4, 0; \
+1: la x6, 2f; \
+ TEST_INSERT_NOPS_ ## nop_cycles \
+ inst x6; \
+ bne x0, TESTNUM, fail; \
+2: addi x4, x4, 1; \
+ li x5, 2; \
+ bne x4, x5, 1b \
+
+#define TEST_JALR_SRC1_BYPASS( testnum, nop_cycles, inst ) \
+test_ ## testnum: \
+ li TESTNUM, testnum; \
+ li x4, 0; \
+1: la x6, 2f; \
+ TEST_INSERT_NOPS_ ## nop_cycles \
+ inst x19, x6, 0; \
+ bne x0, TESTNUM, fail; \
+2: addi x4, x4, 1; \
+ li x5, 2; \
+ bne x4, x5, 1b \
+
+
+#-----------------------------------------------------------------------
+# RV64UF MACROS
+#-----------------------------------------------------------------------
+
+#-----------------------------------------------------------------------
+# Tests floating-point instructions
+#-----------------------------------------------------------------------
+
+#define qNaNf 0f:7fc00000
+#define sNaNf 0f:7f800001
+#define qNaN 0d:7ff8000000000000
+#define sNaN 0d:7ff0000000000001
+
+#define TEST_FP_OP_S_INTERNAL( testnum, flags, result, val1, val2, val3, code... ) \
+test_ ## testnum: \
+ li TESTNUM, testnum; \
+ la a0, test_ ## testnum ## _data ;\
+ flw f0, 0(a0); \
+ flw f1, 4(a0); \
+ flw f2, 8(a0); \
+ lw a3, 12(a0); \
+ code; \
+ fsflags a1, x0; \
+ li a2, flags; \
+ bne a0, a3, fail; \
+ bne a1, a2, fail; \
+ j 2f; \
+ .balign 4; \
+ .data; \
+ test_ ## testnum ## _data: \
+ .float val1; \
+ .float val2; \
+ .float val3; \
+ .result; \
+ .text; \
+2:
+
+#define TEST_FP_OP_D_INTERNAL( testnum, flags, result, val1, val2, val3, code... ) \
+test_ ## testnum: \
+ li TESTNUM, testnum; \
+ la a0, test_ ## testnum ## _data ;\
+ fld f0, 0(a0); \
+ fld f1, 8(a0); \
+ fld f2, 16(a0); \
+ ld a3, 24(a0); \
+ code; \
+ fsflags a1, x0; \
+ li a2, flags; \
+ bne a0, a3, fail; \
+ bne a1, a2, fail; \
+ j 2f; \
+ .data; \
+ .balign 8; \
+ test_ ## testnum ## _data: \
+ .double val1; \
+ .double val2; \
+ .double val3; \
+ .result; \
+ .text; \
+2:
+
+#define TEST_FCVT_S_D( testnum, result, val1 ) \
+ TEST_FP_OP_D_INTERNAL( testnum, 0, double result, val1, 0.0, 0.0, \
+ fcvt.s.d f3, f0; fcvt.d.s f3, f3; fmv.x.d a0, f3)
+
+#define TEST_FCVT_D_S( testnum, result, val1 ) \
+ TEST_FP_OP_S_INTERNAL( testnum, 0, float result, val1, 0.0, 0.0, \
+ fcvt.d.s f3, f0; fcvt.s.d f3, f3; fmv.x.s a0, f3)
+
+#define TEST_FP_OP1_S( testnum, inst, flags, result, val1 ) \
+ TEST_FP_OP_S_INTERNAL( testnum, flags, float result, val1, 0.0, 0.0, \
+ inst f3, f0; fmv.x.s a0, f3)
+
+#define TEST_FP_OP1_D( testnum, inst, flags, result, val1 ) \
+ TEST_FP_OP_D_INTERNAL( testnum, flags, double result, val1, 0.0, 0.0, \
+ inst f3, f0; fmv.x.d a0, f3)
+
+#define TEST_FP_OP1_S_DWORD_RESULT( testnum, inst, flags, result, val1 ) \
+ TEST_FP_OP_S_INTERNAL( testnum, flags, dword result, val1, 0.0, 0.0, \
+ inst f3, f0; fmv.x.s a0, f3)
+
+#define TEST_FP_OP1_D_DWORD_RESULT( testnum, inst, flags, result, val1 ) \
+ TEST_FP_OP_D_INTERNAL( testnum, flags, dword result, val1, 0.0, 0.0, \
+ inst f3, f0; fmv.x.d a0, f3)
+
+#define TEST_FP_OP2_S( testnum, inst, flags, result, val1, val2 ) \
+ TEST_FP_OP_S_INTERNAL( testnum, flags, float result, val1, val2, 0.0, \
+ inst f3, f0, f1; fmv.x.s a0, f3)
+
+#define TEST_FP_OP2_D( testnum, inst, flags, result, val1, val2 ) \
+ TEST_FP_OP_D_INTERNAL( testnum, flags, double result, val1, val2, 0.0, \
+ inst f3, f0, f1; fmv.x.d a0, f3)
+
+#define TEST_FP_OP3_S( testnum, inst, flags, result, val1, val2, val3 ) \
+ TEST_FP_OP_S_INTERNAL( testnum, flags, float result, val1, val2, val3, \
+ inst f3, f0, f1, f2; fmv.x.s a0, f3)
+
+#define TEST_FP_OP3_D( testnum, inst, flags, result, val1, val2, val3 ) \
+ TEST_FP_OP_D_INTERNAL( testnum, flags, double result, val1, val2, val3, \
+ inst f3, f0, f1, f2; fmv.x.d a0, f3)
+
+#define TEST_FP_INT_OP_S( testnum, inst, flags, result, val1, rm ) \
+ TEST_FP_OP_S_INTERNAL( testnum, flags, word result, val1, 0.0, 0.0, \
+ inst a0, f0, rm)
+
+#define TEST_FP_INT_OP_D( testnum, inst, flags, result, val1, rm ) \
+ TEST_FP_OP_D_INTERNAL( testnum, flags, dword result, val1, 0.0, 0.0, \
+ inst a0, f0, rm)
+
+#define TEST_FP_CMP_OP_S( testnum, inst, flags, result, val1, val2 ) \
+ TEST_FP_OP_S_INTERNAL( testnum, flags, word result, val1, val2, 0.0, \
+ inst a0, f0, f1)
+
+#define TEST_FP_CMP_OP_D( testnum, inst, flags, result, val1, val2 ) \
+ TEST_FP_OP_D_INTERNAL( testnum, flags, dword result, val1, val2, 0.0, \
+ inst a0, f0, f1)
+
+#define TEST_FCLASS_S(testnum, correct, input) \
+ TEST_CASE(testnum, a0, correct, li a0, input; fmv.s.x fa0, a0; \
+ fclass.s a0, fa0)
+
+#define TEST_FCLASS_D(testnum, correct, input) \
+ TEST_CASE(testnum, a0, correct, li a0, input; fmv.d.x fa0, a0; \
+ fclass.d a0, fa0)
+
+#define TEST_INT_FP_OP_S( testnum, inst, result, val1 ) \
+test_ ## testnum: \
+ li TESTNUM, testnum; \
+ la a0, test_ ## testnum ## _data ;\
+ lw a3, 0(a0); \
+ li a0, val1; \
+ inst f0, a0; \
+ fsflags x0; \
+ fmv.x.s a0, f0; \
+ bne a0, a3, fail; \
+ j 1f; \
+ .balign 4; \
+ test_ ## testnum ## _data: \
+ .float result; \
+1:
+
+#define TEST_INT_FP_OP_D( testnum, inst, result, val1 ) \
+test_ ## testnum: \
+ li TESTNUM, testnum; \
+ la a0, test_ ## testnum ## _data ;\
+ ld a3, 0(a0); \
+ li a0, val1; \
+ inst f0, a0; \
+ fsflags x0; \
+ fmv.x.d a0, f0; \
+ bne a0, a3, fail; \
+ j 1f; \
+ .balign 8; \
+ test_ ## testnum ## _data: \
+ .double result; \
+1:
+
+#-----------------------------------------------------------------------
+# Pass and fail code (assumes test num is in TESTNUM)
+#-----------------------------------------------------------------------
+
+#define TEST_PASSFAIL \
+ bne x0, TESTNUM, pass; \
+fail: \
+ RVTEST_FAIL; \
+pass: \
+ RVTEST_PASS \
+
+
+#-----------------------------------------------------------------------
+# Test data section
+#-----------------------------------------------------------------------
+
+#define TEST_DATA
+
+#endif
+
Index: yifive/trunk/caravel_yifive/verilog/rtl/syntacore/scr1/sim/tests/common/sc_print.c
===================================================================
--- yifive/trunk/caravel_yifive/verilog/rtl/syntacore/scr1/sim/tests/common/sc_print.c (nonexistent)
+++ yifive/trunk/caravel_yifive/verilog/rtl/syntacore/scr1/sim/tests/common/sc_print.c (revision 22)
@@ -0,0 +1,282 @@
+/// Copyright by Syntacore LLC © 2016, 2017. See LICENSE for details
+/// @file
+///
+
+#include
+#include
+#include "sc_print.h"
+
+#define SC_SIM_OUTPORT (0xf0000000)
+#define CHAR_BIT (8)
+
+static void
+sc_puts(long str, long strlen) {
+ volatile char *out_ptr = (volatile char*)SC_SIM_OUTPORT;
+ const char *in_ptr = (const char*)str;
+ for (long len = strlen; len > 0; --len)
+ *out_ptr = *in_ptr++;
+}
+
+#undef putchar
+int
+putchar(int ch) {
+ static __thread char buf[64] __attribute__((aligned(64)));
+ static __thread int buflen = 0;
+
+ buf[buflen++] = ch;
+
+ if ( ch == '\n' || buflen == sizeof(buf) ) {
+ sc_puts((long)buf, buflen);
+ buflen = 0;
+ }
+
+ return 0;
+}
+
+static void
+printf_putch(int ch, void** data)
+{
+ putchar(ch);
+}
+
+static void
+print(const char *str)
+{
+ sc_puts((long)str, strlen(str));
+}
+
+
+static long long
+getint(va_list *ap, int lflag)
+{
+ if ( lflag >= 2 )
+ return va_arg(*ap, long long);
+ else if ( lflag )
+ return va_arg(*ap, long);
+ else
+ return va_arg(*ap, int);
+}
+
+
+static unsigned long long
+getuint(va_list *ap, int lflag)
+{
+ if ( lflag >= 2 )
+ return va_arg(*ap, unsigned long long);
+ else if ( lflag )
+ return va_arg(*ap, unsigned long);
+ else
+ return va_arg(*ap, unsigned int);
+}
+
+static inline void
+printnum(void(*putch)(int, void**),
+void **putdat,
+unsigned long long num,
+unsigned base,
+int width,
+int padc,
+int hex_A)
+{
+ unsigned digs[sizeof(num) * CHAR_BIT];
+ int pos = 0;
+
+ for ( ;; ) {
+ digs[pos++] = num % base;
+ if ( num < base )
+ break;
+ num /= base;
+ }
+
+ while ( width-- > pos )
+ putch(padc, putdat);
+
+ while ( pos-- > 0 )
+ putch(digs[pos] + (digs[pos] >= 10 ? hex_A - 10 : '0'), putdat);
+}
+
+static void
+vprintfmt(void(*putch)(int, void**), void **putdat, const char *fmt, va_list ap)
+{
+ register const char* p;
+ const char* last_fmt;
+ register int ch;
+ int err;
+ unsigned long long num;
+ int base;
+ int lflag;
+ int width;
+ int precision;
+ int altflag;
+ char padc;
+ int hex_A = 'a';
+ for ( ;; ) {
+ while ( (ch = *(unsigned char *)fmt) != '%' ) {
+ if ( ch == '\0' )
+ return;
+ ++fmt;
+ putch(ch, putdat);
+ }
+ ++fmt;
+
+ // Process a %-escape sequence
+ last_fmt = fmt;
+ padc = ' ';
+ width = -1;
+ precision = -1;
+ lflag = 0;
+ altflag = 0;
+
+reswitch:
+ switch ( ch = *(unsigned char *)fmt++ ) {
+ // flag to pad on the right
+ case '-':
+ padc = '-';
+ goto reswitch;
+
+ // flag to pad with 0's instead of spaces
+ case '0':
+ padc = '0';
+ goto reswitch;
+
+ // width field
+ case '1':
+ case '2':
+ case '3':
+ case '4':
+ case '5':
+ case '6':
+ case '7':
+ case '8':
+ case '9':
+ for ( precision = 0;; ++fmt ) {
+ precision = precision * 10 + ch - '0';
+ ch = *fmt;
+ if ( ch < '0' || ch > '9' )
+ break;
+ }
+ goto process_precision;
+
+ case '*':
+ precision = va_arg(ap, int);
+ goto process_precision;
+
+ case '.':
+ if ( width < 0 )
+ width = 0;
+ goto reswitch;
+
+ case '#':
+ altflag = 1;
+ goto reswitch;
+
+process_precision:
+ if ( width < 0 ) {
+ width = precision;
+ precision = -1;
+ }
+ goto reswitch;
+
+ // long flag (doubled for long long)
+ case 'l':
+ lflag++;
+ goto reswitch;
+
+ // character
+ case 'c':
+ putch(va_arg(ap, int), putdat);
+ break;
+
+ // string
+ case 's':
+ if ( (p = va_arg(ap, char *)) == NULL )
+ p = "(null)";
+ if ( width > 0 && padc != '-' )
+ for ( width -= strnlen(p, precision); width > 0; width-- )
+ putch(padc, putdat);
+ for ( ; (ch = *p) != '\0' && (precision < 0 || --precision >= 0); width-- ) {
+ putch(ch, putdat);
+ p++;
+ }
+ for ( ; width > 0; width-- )
+ putch(' ', putdat);
+ break;
+
+ // (signed) decimal
+ case 'd':
+ num = getint(&ap, lflag);
+ if ( (long long)num < 0 ) {
+ putch('-', putdat);
+ num = -(long long)num;
+ }
+ base = 10;
+ goto signed_number;
+
+ case 'f':
+ {
+ // #ifndef nopfloat
+ // double num = getdouble(&ap, lflag);
+ // printdoubleF(putch, putdat, num, width, precision, padc);
+ // #endif
+ }
+ break;
+
+ // unsigned decimal
+ case 'u':
+ base = 10;
+ goto unsigned_number;
+
+ // (unsigned) octal
+ case 'o':
+ // should do something with padding so it's always 3 octits
+ base = 8;
+ goto unsigned_number;
+
+ // pointer
+ case 'p':
+ // static_assert(sizeof(long) == sizeof(void*));
+ lflag = 1;
+ putch('0', putdat);
+ putch('x', putdat);
+ /* fall through to 'x' */
+
+ // (unsigned) hexadecimal
+ case 'x':
+ hex_A = 'a';
+ base = 16;
+ goto unsigned_number;
+
+ case 'X':
+ hex_A = 'A';
+ base = 16;
+unsigned_number:
+ num = getuint(&ap, lflag);
+signed_number:
+ printnum(putch, putdat, num, base, width, padc, hex_A);
+ break;
+
+ // escaped '%' character
+ case '%':
+ putch(ch, putdat);
+ break;
+
+ // unrecognized escape sequence - just print it literally
+ default:
+ putch('%', putdat);
+ fmt = last_fmt;
+ break;
+ }
+ }
+}
+
+int
+sc_printf(const char* fmt, ...)
+{
+ va_list ap;
+ va_start(ap, fmt);
+
+ vprintfmt(printf_putch, NULL, fmt, ap);
+
+ va_end(ap);
+ return 0; // incorrect return value, but who cares, anyway?
+}
Index: yifive/trunk/caravel_yifive/verilog/rtl/syntacore/scr1/sim/tests/common/sc_print.h
===================================================================
--- yifive/trunk/caravel_yifive/verilog/rtl/syntacore/scr1/sim/tests/common/sc_print.h (nonexistent)
+++ yifive/trunk/caravel_yifive/verilog/rtl/syntacore/scr1/sim/tests/common/sc_print.h (revision 22)
@@ -0,0 +1,10 @@
+/// Copyright by Syntacore LLC © 2016, 2017. See LICENSE for details
+/// @file
+///
+
+#ifndef SC_PRINT_H
+#define SC_PRINT_H
+
+extern int sc_printf(const char* fmt, ...);
+
+#endif // SC_PRINT_H
\ No newline at end of file
Index: yifive/trunk/caravel_yifive/verilog/rtl/syntacore/scr1/sim/tests/common/sc_test.h
===================================================================
--- yifive/trunk/caravel_yifive/verilog/rtl/syntacore/scr1/sim/tests/common/sc_test.h (nonexistent)
+++ yifive/trunk/caravel_yifive/verilog/rtl/syntacore/scr1/sim/tests/common/sc_test.h (revision 22)
@@ -0,0 +1,48 @@
+/// Copyright by Syntacore LLC © 2016, 2017. See LICENSE for details
+/// @file
+///
+
+#ifndef SC_TEST_H
+#define SC_TEST_H
+
+#if defined(__ASSEMBLER__)
+.altmacro
+
+.macro zero_int_reg regn
+mv x\regn, zero
+.endm
+
+.macro zero_int_regs reg_first, reg_last
+.set regn, \reg_first
+.rept \reg_last - \reg_first + 1
+zero_int_reg %(regn)
+.set regn, regn+1
+.endr
+.endm
+
+#define report_results(result) \
+li a0, result; \
+la t0, sc_exit; \
+jr t0;
+
+.pushsection sc_test_section, "ax"
+sc_exit: la t0, SIM_EXIT; jr t0;
+.balign 32
+.popsection
+#define sc_pass report_results(0x0)
+#define sc_fail report_results(0x1)
+
+#else
+
+extern void sc_exit(unsigned result, unsigned res0, unsigned res1, unsigned res2, unsigned res3)
+ __attribute__ ((noinline, noreturn));
+
+static inline void __attribute__ ((noreturn))
+report_results(unsigned result, unsigned res0, unsigned res1, unsigned res2, unsigned res3)
+{
+ sc_exit(result, res0, res1, res2, res3);
+}
+
+#endif
+
+#endif // SC_TEST_H
Index: yifive/trunk/caravel_yifive/verilog/rtl/syntacore/scr1/sim/tests/common/scr1_specific.h
===================================================================
--- yifive/trunk/caravel_yifive/verilog/rtl/syntacore/scr1/sim/tests/common/scr1_specific.h (nonexistent)
+++ yifive/trunk/caravel_yifive/verilog/rtl/syntacore/scr1/sim/tests/common/scr1_specific.h (revision 22)
@@ -0,0 +1,20 @@
+#ifndef __SCR1__SPECIFIC
+#define __SCR1__SPECIFIC
+
+#define mcounten 0x7E0
+
+// Memory-mapped registers
+#define mtime_ctrl 0x00490000
+#define mtime_div 0x00490004
+#define mtime 0x00490008
+#define mtimeh 0x0049000C
+#define mtimecmp 0x00490010
+#define mtimecmph 0x00490014
+
+#define SCR1_MTIME_CTRL_EN 0
+#define SCR1_MTIME_CTRL_CLKSRC 1
+
+#define SCR1_MTIME_CTRL_WR_MASK 0x3
+#define SCR1_MTIME_DIV_WR_MASK 0x3FF
+
+#endif // _SCR1__SPECIFIC