From 2231e3daaf890cbc3025ae7f9722e9c926e56e36 Mon Sep 17 00:00:00 2001 From: M0stafaRady Date: Mon, 30 Sep 2024 16:06:20 +0300 Subject: [PATCH 1/8] revert synchoronizer over miso and fix unit level --- EF_SPI.yaml | 2 +- hdl/rtl/bus_wrappers/EF_SPI_AHBL.pp.v | 26 ++++++++- hdl/rtl/bus_wrappers/EF_SPI_AHBL.v | 24 +++++++- hdl/rtl/bus_wrappers/EF_SPI_APB.pp.v | 56 +++++++------------ hdl/rtl/bus_wrappers/EF_SPI_APB.v | 48 +++++----------- hdl/rtl/bus_wrappers/EF_SPI_WB.pp.v | 31 ++++++++-- hdl/rtl/bus_wrappers/EF_SPI_WB.v | 23 +++++++- ip/.gitignore | 3 + ip/dependencies.json | 7 +++ verify/uvm-python/Makefile | 2 +- .../spi_seq_lib/spi_MOSI_MISO_seq.py | 1 + .../uvm-python/spi_seq_lib/spi_rx_dis_seq.py | 1 + .../spi_seq_lib/spi_send_MISO_seq.py | 1 + .../spi_seq_lib/spi_send_MOSI_seq.py | 1 + 14 files changed, 146 insertions(+), 80 deletions(-) create mode 100644 ip/.gitignore create mode 100644 ip/dependencies.json diff --git a/EF_SPI.yaml b/EF_SPI.yaml index cbb0e56..713e5b1 100644 --- a/EF_SPI.yaml +++ b/EF_SPI.yaml @@ -140,7 +140,7 @@ external_interface: width: 1 direction: input description: SPI Master In Slave Out. - sync: True + sync: False - name: mosi port: mosi width: 1 diff --git a/hdl/rtl/bus_wrappers/EF_SPI_AHBL.pp.v b/hdl/rtl/bus_wrappers/EF_SPI_AHBL.pp.v index d4e9a6b..13cae82 100644 --- a/hdl/rtl/bus_wrappers/EF_SPI_AHBL.pp.v +++ b/hdl/rtl/bus_wrappers/EF_SPI_AHBL.pp.v @@ -104,6 +104,10 @@ module EF_SPI_AHBL #( CDW = 8, FAW = 4 ) ( + + + + input wire HCLK, input wire HRESETn, input wire HWRITE, @@ -138,7 +142,21 @@ module EF_SPI_AHBL #( localparam MIS_REG_OFFSET = 16'hFF04; localparam RIS_REG_OFFSET = 16'hFF08; localparam IC_REG_OFFSET = 16'hFF0C; - wire clk = HCLK; + + reg [0:0] GCLK_REG; + wire clk_g; + wire clk_gated_en = GCLK_REG[0]; + ef_gating_cell clk_gate_cell( + + + + // USE_POWER_PINS + .clk(HCLK), + .clk_en(clk_gated_en), + .clk_o(clk_g) + ); + + wire clk = clk_g; wire rst_n = HRESETn; @@ -251,6 +269,11 @@ module EF_SPI_AHBL #( else TX_FIFO_FLUSH_REG <= 1'h0 & TX_FIFO_FLUSH_REG; + localparam GCLK_REG_OFFSET = 16'hFF10; + always @(posedge HCLK or negedge HRESETn) if(~HRESETn) GCLK_REG <= 0; + else if(ahbl_we & (last_HADDR[16-1:0]==GCLK_REG_OFFSET)) + GCLK_REG <= HWDATA[1-1:0]; + reg [5:0] IM_REG; reg [5:0] IC_REG; reg [5:0] RIS_REG; @@ -347,6 +370,7 @@ module EF_SPI_AHBL #( (last_HADDR[16-1:0] == MIS_REG_OFFSET) ? MIS_REG : (last_HADDR[16-1:0] == RIS_REG_OFFSET) ? RIS_REG : (last_HADDR[16-1:0] == IC_REG_OFFSET) ? IC_REG : + (last_HADDR[16-1:0] == GCLK_REG_OFFSET) ? GCLK_REG : 32'hDEADBEEF; assign HREADYOUT = 1'b1; diff --git a/hdl/rtl/bus_wrappers/EF_SPI_AHBL.v b/hdl/rtl/bus_wrappers/EF_SPI_AHBL.v index 0d05325..bbd0711 100644 --- a/hdl/rtl/bus_wrappers/EF_SPI_AHBL.v +++ b/hdl/rtl/bus_wrappers/EF_SPI_AHBL.v @@ -31,6 +31,10 @@ module EF_SPI_AHBL #( CDW = 8, FAW = 4 ) ( +`ifdef USE_POWER_PINS + inout VPWR, + inout VGND, +`endif `AHBL_SLAVE_PORTS, input wire [1-1:0] miso, output wire [1-1:0] mosi, @@ -54,7 +58,21 @@ module EF_SPI_AHBL #( localparam MIS_REG_OFFSET = `AHBL_AW'hFF04; localparam RIS_REG_OFFSET = `AHBL_AW'hFF08; localparam IC_REG_OFFSET = `AHBL_AW'hFF0C; - wire clk = HCLK; + + reg [0:0] GCLK_REG; + wire clk_g; + wire clk_gated_en = GCLK_REG[0]; + ef_gating_cell clk_gate_cell( + `ifdef USE_POWER_PINS + .vpwr(VPWR), + .vgnd(VGND), + `endif // USE_POWER_PINS + .clk(HCLK), + .clk_en(clk_gated_en), + .clk_o(clk_g) + ); + + wire clk = clk_g; wire rst_n = HRESETn; @@ -133,6 +151,9 @@ module EF_SPI_AHBL #( assign tx_flush = TX_FIFO_FLUSH_REG[0 : 0]; `AHBL_REG_AC(TX_FIFO_FLUSH_REG, 0, 1, 1'h0) + localparam GCLK_REG_OFFSET = `AHBL_AW'hFF10; + `AHBL_REG(GCLK_REG, 0, 1) + reg [5:0] IM_REG; reg [5:0] IC_REG; reg [5:0] RIS_REG; @@ -224,6 +245,7 @@ module EF_SPI_AHBL #( (last_HADDR[`AHBL_AW-1:0] == MIS_REG_OFFSET) ? MIS_REG : (last_HADDR[`AHBL_AW-1:0] == RIS_REG_OFFSET) ? RIS_REG : (last_HADDR[`AHBL_AW-1:0] == IC_REG_OFFSET) ? IC_REG : + (last_HADDR[`AHBL_AW-1:0] == GCLK_REG_OFFSET) ? GCLK_REG : 32'hDEADBEEF; assign HREADYOUT = 1'b1; diff --git a/hdl/rtl/bus_wrappers/EF_SPI_APB.pp.v b/hdl/rtl/bus_wrappers/EF_SPI_APB.pp.v index 1b26145..6e66e07 100644 --- a/hdl/rtl/bus_wrappers/EF_SPI_APB.pp.v +++ b/hdl/rtl/bus_wrappers/EF_SPI_APB.pp.v @@ -102,10 +102,10 @@ module EF_SPI_APB #( CDW = 8, FAW = 4 ) ( -`ifdef USE_POWER_PINS - inout VPWR, - inout VGND, -`endif + + + + input wire PCLK, input wire PRESETn, input wire PWRITE, @@ -140,27 +140,20 @@ module EF_SPI_APB #( localparam RIS_REG_OFFSET = 16'hFF08; localparam IC_REG_OFFSET = 16'hFF0C; - reg [0:0] GCLK_REG; - wire clk_g; - wire clk_gated_en = GCLK_REG[0]; - - `ifdef FPGA - wire clk = PCLK; - `else - (* keep *) sky130_fd_sc_hd__dlclkp_4 clk_gate( - `ifdef USE_POWER_PINS - .VPWR(VPWR), - .VGND(VGND), - .VNB(VGND), - .VPB(VPWR), - `endif - .GCLK(clk_g), - .GATE(clk_gated_en), - .CLK(PCLK) - ); - - wire clk = clk_g; - `endif + reg [0:0] GCLK_REG; + wire clk_g; + wire clk_gated_en = GCLK_REG[0]; + ef_gating_cell clk_gate_cell( + + + + // USE_POWER_PINS + .clk(PCLK), + .clk_en(clk_gated_en), + .clk_o(clk_g) + ); + + wire clk = clk_g; wire rst_n = PRESETn; @@ -310,17 +303,6 @@ module EF_SPI_APB #( assign IRQ = |MIS_REG; - reg [0:0] _miso_reg_[1:0]; - wire _miso_w_ = _miso_reg_[1]; - always@(posedge PCLK or negedge PRESETn) - if(PRESETn == 0) begin - _miso_reg_[0] <= 'b0; - _miso_reg_[1] <= 'b0; - end - else begin - _miso_reg_[0] <= miso; - _miso_reg_[1] <= _miso_reg_[0]; - end EF_SPI #( .CDW(CDW), .FAW(FAW) @@ -349,7 +331,7 @@ module EF_SPI_APB #( .tx_level(tx_level), .ss(ss), .enable(enable), - .miso(_miso_w_), + .miso(miso), .mosi(mosi), .csb(csb), .sclk(sclk) diff --git a/hdl/rtl/bus_wrappers/EF_SPI_APB.v b/hdl/rtl/bus_wrappers/EF_SPI_APB.v index 0d3e274..7ed1195 100644 --- a/hdl/rtl/bus_wrappers/EF_SPI_APB.v +++ b/hdl/rtl/bus_wrappers/EF_SPI_APB.v @@ -59,27 +59,20 @@ module EF_SPI_APB #( localparam RIS_REG_OFFSET = `APB_AW'hFF08; localparam IC_REG_OFFSET = `APB_AW'hFF0C; - reg [0:0] GCLK_REG; - wire clk_g; - wire clk_gated_en = GCLK_REG[0]; - - `ifdef FPGA - wire clk = PCLK; - `else - (* keep *) sky130_fd_sc_hd__dlclkp_4 clk_gate( - `ifdef USE_POWER_PINS - .VPWR(VPWR), - .VGND(VGND), - .VNB(VGND), - .VPB(VPWR), - `endif - .GCLK(clk_g), - .GATE(clk_gated_en), - .CLK(PCLK) - ); - - wire clk = clk_g; - `endif + reg [0:0] GCLK_REG; + wire clk_g; + wire clk_gated_en = GCLK_REG[0]; + ef_gating_cell clk_gate_cell( + `ifdef USE_POWER_PINS + .vpwr(VPWR), + .vgnd(VGND), + `endif // USE_POWER_PINS + .clk(PCLK), + .clk_en(clk_gated_en), + .clk_o(clk_g) + ); + + wire clk = clk_g; wire rst_n = PRESETn; @@ -201,17 +194,6 @@ module EF_SPI_APB #( assign IRQ = |MIS_REG; - reg [0:0] _miso_reg_[1:0]; - wire _miso_w_ = _miso_reg_[1]; - always@(posedge PCLK or negedge PRESETn) - if(PRESETn == 0) begin - _miso_reg_[0] <= 'b0; - _miso_reg_[1] <= 'b0; - end - else begin - _miso_reg_[0] <= miso; - _miso_reg_[1] <= _miso_reg_[0]; - end EF_SPI #( .CDW(CDW), .FAW(FAW) @@ -240,7 +222,7 @@ module EF_SPI_APB #( .tx_level(tx_level), .ss(ss), .enable(enable), - .miso(_miso_w_), + .miso(miso), .mosi(mosi), .csb(csb), .sclk(sclk) diff --git a/hdl/rtl/bus_wrappers/EF_SPI_WB.pp.v b/hdl/rtl/bus_wrappers/EF_SPI_WB.pp.v index 3e16ec2..4bfc6db 100644 --- a/hdl/rtl/bus_wrappers/EF_SPI_WB.pp.v +++ b/hdl/rtl/bus_wrappers/EF_SPI_WB.pp.v @@ -81,6 +81,10 @@ module EF_SPI_WB #( CDW = 8, FAW = 4 ) ( + + + + input wire ext_clk, input wire clk_i, input wire rst_i, @@ -93,10 +97,10 @@ module EF_SPI_WB #( output reg ack_o, input wire we_i, output wire IRQ, - input wire [1-1:0] miso, - output wire [1-1:0] mosi, - output wire [1-1:0] csb, - output wire [1-1:0] sclk + input wire [1-1:0] miso, + output wire [1-1:0] mosi, + output wire [1-1:0] csb, + output wire [1-1:0] sclk ); localparam RXDATA_REG_OFFSET = 16'h0000; @@ -115,7 +119,21 @@ module EF_SPI_WB #( localparam MIS_REG_OFFSET = 16'hFF04; localparam RIS_REG_OFFSET = 16'hFF08; localparam IC_REG_OFFSET = 16'hFF0C; - wire clk = clk_i; + + reg [0:0] GCLK_REG; + wire clk_g; + wire clk_gated_en = GCLK_REG[0]; + ef_gating_cell clk_gate_cell( + + + + // USE_POWER_PINS + .clk(clk_i), + .clk_en(clk_gated_en), + .clk_o(clk_g) + ); + + wire clk = clk_g; wire rst_n = (~rst_i); @@ -197,6 +215,9 @@ module EF_SPI_WB #( assign tx_flush = TX_FIFO_FLUSH_REG[0 : 0]; always @(posedge clk_i or posedge rst_i) if(rst_i) TX_FIFO_FLUSH_REG <= 0; else if(wb_we & (adr_i[16-1:0]==TX_FIFO_FLUSH_REG_OFFSET)) TX_FIFO_FLUSH_REG <= dat_i[1-1:0]; else TX_FIFO_FLUSH_REG <= 1'h0 & TX_FIFO_FLUSH_REG; + localparam GCLK_REG_OFFSET = 16'hFF10; + always @(posedge clk_i or posedge rst_i) if(rst_i) GCLK_REG <= 0; else if(wb_we & (adr_i[16-1:0]==GCLK_REG_OFFSET)) GCLK_REG <= dat_i[1-1:0]; + reg [5:0] IM_REG; reg [5:0] IC_REG; reg [5:0] RIS_REG; diff --git a/hdl/rtl/bus_wrappers/EF_SPI_WB.v b/hdl/rtl/bus_wrappers/EF_SPI_WB.v index 53c36bd..11b4ce1 100644 --- a/hdl/rtl/bus_wrappers/EF_SPI_WB.v +++ b/hdl/rtl/bus_wrappers/EF_SPI_WB.v @@ -31,6 +31,10 @@ module EF_SPI_WB #( CDW = 8, FAW = 4 ) ( +`ifdef USE_POWER_PINS + inout VPWR, + inout VGND, +`endif `WB_SLAVE_PORTS, input wire [1-1:0] miso, output wire [1-1:0] mosi, @@ -54,7 +58,21 @@ module EF_SPI_WB #( localparam MIS_REG_OFFSET = `WB_AW'hFF04; localparam RIS_REG_OFFSET = `WB_AW'hFF08; localparam IC_REG_OFFSET = `WB_AW'hFF0C; - wire clk = clk_i; + + reg [0:0] GCLK_REG; + wire clk_g; + wire clk_gated_en = GCLK_REG[0]; + ef_gating_cell clk_gate_cell( + `ifdef USE_POWER_PINS + .vpwr(VPWR), + .vgnd(VGND), + `endif // USE_POWER_PINS + .clk(clk_i), + .clk_en(clk_gated_en), + .clk_o(clk_g) + ); + + wire clk = clk_g; wire rst_n = (~rst_i); @@ -133,6 +151,9 @@ module EF_SPI_WB #( assign tx_flush = TX_FIFO_FLUSH_REG[0 : 0]; `WB_REG_AC(TX_FIFO_FLUSH_REG, 0, 1, 1'h0) + localparam GCLK_REG_OFFSET = `WB_AW'hFF10; + `WB_REG(GCLK_REG, 0, 1) + reg [5:0] IM_REG; reg [5:0] IC_REG; reg [5:0] RIS_REG; diff --git a/ip/.gitignore b/ip/.gitignore new file mode 100644 index 0000000..83fe78c --- /dev/null +++ b/ip/.gitignore @@ -0,0 +1,3 @@ +* +!dependencies.json +!.gitignore diff --git a/ip/dependencies.json b/ip/dependencies.json new file mode 100644 index 0000000..bc86f84 --- /dev/null +++ b/ip/dependencies.json @@ -0,0 +1,7 @@ +{ + "IP": [ + { + "IP_Utilities": "v1.0.0" + } + ] +} \ No newline at end of file diff --git a/verify/uvm-python/Makefile b/verify/uvm-python/Makefile index a9ad402..7afddfc 100644 --- a/verify/uvm-python/Makefile +++ b/verify/uvm-python/Makefile @@ -4,7 +4,7 @@ MODULE ?= top_module AHB_FILES ?= $(PWD)/../../hdl/rtl/bus_wrappers/EF_SPI_AHBL.pp.v APB_FILES ?= $(PWD)/../../hdl/rtl/bus_wrappers/EF_SPI_APB.pp.v WB_FILES ?=$(PWD)/../../hdl/rtl/bus_wrappers/EF_SPI_WB.pp.v -HDL_FILES ?= $(PWD)/IP_Utilities/rtl/aucohl_lib.v $(PWD)/IP_Utilities/rtl/aucohl_rtl.vh $(PWD)/../../hdl/rtl/spi_master.v $(PWD)/../../hdl/rtl/EF_SPI.v +HDL_FILES ?= $(PWD)/../../ip/IP_Utilities/rtl/aucohl_lib.v $(PWD)/../../ip/IP_Utilities/rtl/aucohl_rtl.vh $(PWD)/../../hdl/rtl/spi_master.v $(PWD)/../../hdl/rtl/EF_SPI.v VERILOG_SOURCES ?= $(PWD)/top.v $(AHB_FILES) $(APB_FILES) $(WB_FILES) $(HDL_FILES) RTL_MACROS += "" diff --git a/verify/uvm-python/spi_seq_lib/spi_MOSI_MISO_seq.py b/verify/uvm-python/spi_seq_lib/spi_MOSI_MISO_seq.py index d51961c..fb36d33 100644 --- a/verify/uvm-python/spi_seq_lib/spi_MOSI_MISO_seq.py +++ b/verify/uvm-python/spi_seq_lib/spi_MOSI_MISO_seq.py @@ -36,6 +36,7 @@ def __init__( async def body(self): await super().body() + await self.send_req(is_write=True, reg="CLKGATE", data_condition=lambda data: data == 1) if not self.disable_control: await self.send_req( is_write=True, reg="CTRL", data_condition=lambda data: data == 0b0 diff --git a/verify/uvm-python/spi_seq_lib/spi_rx_dis_seq.py b/verify/uvm-python/spi_seq_lib/spi_rx_dis_seq.py index f60c4ea..c1d022d 100644 --- a/verify/uvm-python/spi_seq_lib/spi_rx_dis_seq.py +++ b/verify/uvm-python/spi_seq_lib/spi_rx_dis_seq.py @@ -32,6 +32,7 @@ async def body(self): # Add the sequqnce here # you could use method send_req to send a write or read using the register name # example for writing register by value > 5 + await self.send_req(is_write=True, reg="CLKGATE", data_condition=lambda data: data == 1) await self.send_req( is_write=True, reg="CTRL", data_condition=lambda data: data == 0b011 ) diff --git a/verify/uvm-python/spi_seq_lib/spi_send_MISO_seq.py b/verify/uvm-python/spi_seq_lib/spi_send_MISO_seq.py index c3eec89..923c214 100644 --- a/verify/uvm-python/spi_seq_lib/spi_send_MISO_seq.py +++ b/verify/uvm-python/spi_seq_lib/spi_send_MISO_seq.py @@ -30,6 +30,7 @@ async def body(self): # Add the sequqnce here # you could use method send_req to send a write or read using the register name # example for writing register by value > 5 + await self.send_req(is_write=True, reg="CLKGATE", data_condition=lambda data: data == 1) await self.send_req( is_write=True, reg="CTRL", data_condition=lambda data: data == 0b111 ) diff --git a/verify/uvm-python/spi_seq_lib/spi_send_MOSI_seq.py b/verify/uvm-python/spi_seq_lib/spi_send_MOSI_seq.py index fb28dcb..23cd30c 100644 --- a/verify/uvm-python/spi_seq_lib/spi_send_MOSI_seq.py +++ b/verify/uvm-python/spi_seq_lib/spi_send_MOSI_seq.py @@ -30,6 +30,7 @@ async def body(self): # Add the sequqnce here # you could use method send_req to send a write or read using the register name # example for writing register by value > 5 + await self.send_req(is_write=True, reg="CLKGATE", data_condition=lambda data: data == 1) await self.send_req( is_write=True, reg="CTRL", data_condition=lambda data: data == 0b11 ) From ddf7abbc41583b3f8fd3df0834d71f0318be9292 Mon Sep 17 00:00:00 2001 From: M0stafaRady Date: Mon, 30 Sep 2024 16:37:53 +0300 Subject: [PATCH 2/8] remove IP_Utilities from make file --- verify/uvm-python/Makefile | 4 ---- 1 file changed, 4 deletions(-) diff --git a/verify/uvm-python/Makefile b/verify/uvm-python/Makefile index 7afddfc..88d7085 100644 --- a/verify/uvm-python/Makefile +++ b/verify/uvm-python/Makefile @@ -48,10 +48,6 @@ PDK_DIR = $(HOME)/.volare/volare/sky130/versions/bdc9412b3e468c102d01b7cf6337be0 PDK_FILES = $(PDK_DIR)/libs.ref/sky130_fd_sc_hd/verilog/primitives.v $(PDK_DIR)/libs.ref/sky130_fd_sc_hd/verilog/sky130_fd_sc_hd.v # get this from openlane logs in the future POST_SYS_FILES = $(PWD)/top.v $(VIP_FILES) $(PWD)/../../hdl/gl/synthesis/nl/$(DESIGN_NAME).nl.v -clone_ip_util := $(shell if [ ! -d "IP_Utilities" ]; then \ - echo "Cloning the IP_Utilities repository..."; \ - git clone https://github.com/shalan/IP_Utilities.git; \ -fi;) clone_ef_uvm := $(shell if [ ! -d "EF_UVM" ]; then \ echo "Cloning the EF_UVM repository..."; \ From 425c2af16b708c1dcd1b8bbc48372a99dfc6da9e Mon Sep 17 00:00:00 2001 From: M0stafaRady Date: Mon, 30 Sep 2024 17:42:19 +0300 Subject: [PATCH 3/8] remove 2 from configuration values until debugged --- verify/uvm-python/spi_seq_lib/configure_spi_seq.py | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/verify/uvm-python/spi_seq_lib/configure_spi_seq.py b/verify/uvm-python/spi_seq_lib/configure_spi_seq.py index 90e5fe6..c458586 100644 --- a/verify/uvm-python/spi_seq_lib/configure_spi_seq.py +++ b/verify/uvm-python/spi_seq_lib/configure_spi_seq.py @@ -23,7 +23,8 @@ async def body(self): await self.send_req( is_write=True, reg="CFG", - data_condition=lambda data: data in [0b00, 0b01, 0b10, 0b11], + # data_condition=lambda data: data in [0b00, 0b01, 0b10, 0b11], + data_condition=lambda data: data in [0b00, 0b01, 0b11], ) rsp = [] await self.get_response(rsp) # wait until writing is done From 072bac274e9eac6a8f686aa62aee91e248774f4d Mon Sep 17 00:00:00 2001 From: M0stafaRady Date: Mon, 30 Sep 2024 21:39:52 +0300 Subject: [PATCH 4/8] fix testbench and add done, busy to the status register --- EF_SPI.yaml | 20 ++++++++++++++- hdl/rtl/EF_SPI.v | 7 ++---- hdl/rtl/bus_wrappers/EF_SPI_AHBL.pp.v | 8 +++++- hdl/rtl/bus_wrappers/EF_SPI_AHBL.v | 8 +++++- hdl/rtl/bus_wrappers/EF_SPI_APB.pp.v | 8 +++++- hdl/rtl/bus_wrappers/EF_SPI_APB.v | 8 +++++- hdl/rtl/bus_wrappers/EF_SPI_WB.pp.v | 8 +++++- hdl/rtl/bus_wrappers/EF_SPI_WB.v | 8 +++++- .../spi_seq_lib/configure_spi_seq.py | 3 +++ .../spi_seq_lib/spi_MOSI_MISO_seq.py | 1 - verify/uvm-python/spi_seq_lib/spi_base_seq.py | 25 ++++++++++++------- .../uvm-python/spi_seq_lib/spi_rx_dis_seq.py | 1 - .../spi_seq_lib/spi_send_MISO_seq.py | 2 +- .../spi_seq_lib/spi_send_MOSI_seq.py | 1 - 14 files changed, 83 insertions(+), 25 deletions(-) diff --git a/EF_SPI.yaml b/EF_SPI.yaml index 713e5b1..fd0138f 100644 --- a/EF_SPI.yaml +++ b/EF_SPI.yaml @@ -133,6 +133,14 @@ ports: width: 1 direction: input description: enable for spi master pulse generation +- name: done + width: 1 + direction: output + description: spi done flag. +- name: busy + width: 1 + direction: output + description: spi busy flag. external_interface: - name: miso @@ -231,7 +239,7 @@ registers: write_port: clk_divider description: SPI clock Prescaler; should have a value >= 2. SPI Clock Frequency = System Clock / PR. - name: STATUS - size: 6 + size: 8 mode: r fifo: no offset: 20 @@ -269,6 +277,16 @@ registers: bit_width: 1 read_port: rx_level_above description: Receive FIFO level is Above Threshold. + - name : busy + bit_offset: 6 + bit_width: 1 + read_port: busy + description: spi busy flag. + - name : done + bit_offset: 7 + bit_width: 1 + read_port: done + description: spi done flag. flags: diff --git a/hdl/rtl/EF_SPI.v b/hdl/rtl/EF_SPI.v index 418583b..873cf58 100644 --- a/hdl/rtl/EF_SPI.v +++ b/hdl/rtl/EF_SPI.v @@ -49,8 +49,8 @@ module EF_SPI #(parameter output wire tx_level_below, output wire [FAW-1:0] tx_level, - //output busy, - //output done, + output busy, + output done, input wire miso, output wire mosi, @@ -61,9 +61,6 @@ module EF_SPI #(parameter localparam FDW = 8; - wire busy; - wire done; - // TX Side wire tx_wr = wr; wire tx_rd = !tx_empty & !busy; diff --git a/hdl/rtl/bus_wrappers/EF_SPI_AHBL.pp.v b/hdl/rtl/bus_wrappers/EF_SPI_AHBL.pp.v index 13cae82..e964c38 100644 --- a/hdl/rtl/bus_wrappers/EF_SPI_AHBL.pp.v +++ b/hdl/rtl/bus_wrappers/EF_SPI_AHBL.pp.v @@ -200,6 +200,8 @@ module EF_SPI_AHBL #( wire [FAW-1:0] tx_level; wire [1-1:0] ss; wire [1-1:0] enable; + wire [1-1:0] done; + wire [1-1:0] busy; // Register Definitions wire [8-1:0] RXDATA_WIRE; @@ -227,13 +229,15 @@ module EF_SPI_AHBL #( else if(ahbl_we & (last_HADDR[16-1:0]==PR_REG_OFFSET)) PR_REG <= HWDATA[CDW-1:0]; - wire [6-1:0] STATUS_WIRE; + wire [8-1:0] STATUS_WIRE; assign STATUS_WIRE[0 : 0] = tx_empty; assign STATUS_WIRE[1 : 1] = tx_full; assign STATUS_WIRE[2 : 2] = rx_empty; assign STATUS_WIRE[3 : 3] = rx_full; assign STATUS_WIRE[4 : 4] = tx_level_below; assign STATUS_WIRE[5 : 5] = rx_level_above; + assign STATUS_WIRE[6 : 6] = busy; + assign STATUS_WIRE[7 : 7] = done; wire [FAW-1:0] RX_FIFO_LEVEL_WIRE; assign RX_FIFO_LEVEL_WIRE[(FAW - 1) : 0] = rx_level; @@ -347,6 +351,8 @@ module EF_SPI_AHBL #( .tx_level(tx_level), .ss(ss), .enable(enable), + .done(done), + .busy(busy), .miso(miso), .mosi(mosi), .csb(csb), diff --git a/hdl/rtl/bus_wrappers/EF_SPI_AHBL.v b/hdl/rtl/bus_wrappers/EF_SPI_AHBL.v index bbd0711..11824a2 100644 --- a/hdl/rtl/bus_wrappers/EF_SPI_AHBL.v +++ b/hdl/rtl/bus_wrappers/EF_SPI_AHBL.v @@ -100,6 +100,8 @@ module EF_SPI_AHBL #( wire [FAW-1:0] tx_level; wire [1-1:0] ss; wire [1-1:0] enable; + wire [1-1:0] done; + wire [1-1:0] busy; // Register Definitions wire [8-1:0] RXDATA_WIRE; @@ -121,13 +123,15 @@ module EF_SPI_AHBL #( assign clk_divider = PR_REG; `AHBL_REG(PR_REG, 'h2, CDW) - wire [6-1:0] STATUS_WIRE; + wire [8-1:0] STATUS_WIRE; assign STATUS_WIRE[0 : 0] = tx_empty; assign STATUS_WIRE[1 : 1] = tx_full; assign STATUS_WIRE[2 : 2] = rx_empty; assign STATUS_WIRE[3 : 3] = rx_full; assign STATUS_WIRE[4 : 4] = tx_level_below; assign STATUS_WIRE[5 : 5] = rx_level_above; + assign STATUS_WIRE[6 : 6] = busy; + assign STATUS_WIRE[7 : 7] = done; wire [FAW-1:0] RX_FIFO_LEVEL_WIRE; assign RX_FIFO_LEVEL_WIRE[(FAW - 1) : 0] = rx_level; @@ -222,6 +226,8 @@ module EF_SPI_AHBL #( .tx_level(tx_level), .ss(ss), .enable(enable), + .done(done), + .busy(busy), .miso(miso), .mosi(mosi), .csb(csb), diff --git a/hdl/rtl/bus_wrappers/EF_SPI_APB.pp.v b/hdl/rtl/bus_wrappers/EF_SPI_APB.pp.v index 6e66e07..3c929a9 100644 --- a/hdl/rtl/bus_wrappers/EF_SPI_APB.pp.v +++ b/hdl/rtl/bus_wrappers/EF_SPI_APB.pp.v @@ -183,6 +183,8 @@ module EF_SPI_APB #( wire [FAW-1:0] tx_level; wire [1-1:0] ss; wire [1-1:0] enable; + wire [1-1:0] done; + wire [1-1:0] busy; // Register Definitions wire [8-1:0] RXDATA_WIRE; @@ -210,13 +212,15 @@ module EF_SPI_APB #( else if(apb_we & (PADDR[16-1:0]==PR_REG_OFFSET)) PR_REG <= PWDATA[CDW-1:0]; - wire [6-1:0] STATUS_WIRE; + wire [8-1:0] STATUS_WIRE; assign STATUS_WIRE[0 : 0] = tx_empty; assign STATUS_WIRE[1 : 1] = tx_full; assign STATUS_WIRE[2 : 2] = rx_empty; assign STATUS_WIRE[3 : 3] = rx_full; assign STATUS_WIRE[4 : 4] = tx_level_below; assign STATUS_WIRE[5 : 5] = rx_level_above; + assign STATUS_WIRE[6 : 6] = busy; + assign STATUS_WIRE[7 : 7] = done; wire [FAW-1:0] RX_FIFO_LEVEL_WIRE; assign RX_FIFO_LEVEL_WIRE[(FAW - 1) : 0] = rx_level; @@ -331,6 +335,8 @@ module EF_SPI_APB #( .tx_level(tx_level), .ss(ss), .enable(enable), + .done(done), + .busy(busy), .miso(miso), .mosi(mosi), .csb(csb), diff --git a/hdl/rtl/bus_wrappers/EF_SPI_APB.v b/hdl/rtl/bus_wrappers/EF_SPI_APB.v index 7ed1195..54e83c6 100644 --- a/hdl/rtl/bus_wrappers/EF_SPI_APB.v +++ b/hdl/rtl/bus_wrappers/EF_SPI_APB.v @@ -100,6 +100,8 @@ module EF_SPI_APB #( wire [FAW-1:0] tx_level; wire [1-1:0] ss; wire [1-1:0] enable; + wire [1-1:0] done; + wire [1-1:0] busy; // Register Definitions wire [8-1:0] RXDATA_WIRE; @@ -121,13 +123,15 @@ module EF_SPI_APB #( assign clk_divider = PR_REG; `APB_REG(PR_REG, 'h2, CDW) - wire [6-1:0] STATUS_WIRE; + wire [8-1:0] STATUS_WIRE; assign STATUS_WIRE[0 : 0] = tx_empty; assign STATUS_WIRE[1 : 1] = tx_full; assign STATUS_WIRE[2 : 2] = rx_empty; assign STATUS_WIRE[3 : 3] = rx_full; assign STATUS_WIRE[4 : 4] = tx_level_below; assign STATUS_WIRE[5 : 5] = rx_level_above; + assign STATUS_WIRE[6 : 6] = busy; + assign STATUS_WIRE[7 : 7] = done; wire [FAW-1:0] RX_FIFO_LEVEL_WIRE; assign RX_FIFO_LEVEL_WIRE[(FAW - 1) : 0] = rx_level; @@ -222,6 +226,8 @@ module EF_SPI_APB #( .tx_level(tx_level), .ss(ss), .enable(enable), + .done(done), + .busy(busy), .miso(miso), .mosi(mosi), .csb(csb), diff --git a/hdl/rtl/bus_wrappers/EF_SPI_WB.pp.v b/hdl/rtl/bus_wrappers/EF_SPI_WB.pp.v index 4bfc6db..aceda61 100644 --- a/hdl/rtl/bus_wrappers/EF_SPI_WB.pp.v +++ b/hdl/rtl/bus_wrappers/EF_SPI_WB.pp.v @@ -164,6 +164,8 @@ module EF_SPI_WB #( wire [FAW-1:0] tx_level; wire [1-1:0] ss; wire [1-1:0] enable; + wire [1-1:0] done; + wire [1-1:0] busy; // Register Definitions wire [8-1:0] RXDATA_WIRE; @@ -185,13 +187,15 @@ module EF_SPI_WB #( assign clk_divider = PR_REG; always @(posedge clk_i or posedge rst_i) if(rst_i) PR_REG <= 'h2; else if(wb_we & (adr_i[16-1:0]==PR_REG_OFFSET)) PR_REG <= dat_i[CDW-1:0]; - wire [6-1:0] STATUS_WIRE; + wire [8-1:0] STATUS_WIRE; assign STATUS_WIRE[0 : 0] = tx_empty; assign STATUS_WIRE[1 : 1] = tx_full; assign STATUS_WIRE[2 : 2] = rx_empty; assign STATUS_WIRE[3 : 3] = rx_full; assign STATUS_WIRE[4 : 4] = tx_level_below; assign STATUS_WIRE[5 : 5] = rx_level_above; + assign STATUS_WIRE[6 : 6] = busy; + assign STATUS_WIRE[7 : 7] = done; wire [FAW-1:0] RX_FIFO_LEVEL_WIRE; assign RX_FIFO_LEVEL_WIRE[(FAW - 1) : 0] = rx_level; @@ -290,6 +294,8 @@ module EF_SPI_WB #( .tx_level(tx_level), .ss(ss), .enable(enable), + .done(done), + .busy(busy), .miso(miso), .mosi(mosi), .csb(csb), diff --git a/hdl/rtl/bus_wrappers/EF_SPI_WB.v b/hdl/rtl/bus_wrappers/EF_SPI_WB.v index 11b4ce1..966bca6 100644 --- a/hdl/rtl/bus_wrappers/EF_SPI_WB.v +++ b/hdl/rtl/bus_wrappers/EF_SPI_WB.v @@ -100,6 +100,8 @@ module EF_SPI_WB #( wire [FAW-1:0] tx_level; wire [1-1:0] ss; wire [1-1:0] enable; + wire [1-1:0] done; + wire [1-1:0] busy; // Register Definitions wire [8-1:0] RXDATA_WIRE; @@ -121,13 +123,15 @@ module EF_SPI_WB #( assign clk_divider = PR_REG; `WB_REG(PR_REG, 'h2, CDW) - wire [6-1:0] STATUS_WIRE; + wire [8-1:0] STATUS_WIRE; assign STATUS_WIRE[0 : 0] = tx_empty; assign STATUS_WIRE[1 : 1] = tx_full; assign STATUS_WIRE[2 : 2] = rx_empty; assign STATUS_WIRE[3 : 3] = rx_full; assign STATUS_WIRE[4 : 4] = tx_level_below; assign STATUS_WIRE[5 : 5] = rx_level_above; + assign STATUS_WIRE[6 : 6] = busy; + assign STATUS_WIRE[7 : 7] = done; wire [FAW-1:0] RX_FIFO_LEVEL_WIRE; assign RX_FIFO_LEVEL_WIRE[(FAW - 1) : 0] = rx_level; @@ -222,6 +226,8 @@ module EF_SPI_WB #( .tx_level(tx_level), .ss(ss), .enable(enable), + .done(done), + .busy(busy), .miso(miso), .mosi(mosi), .csb(csb), diff --git a/verify/uvm-python/spi_seq_lib/configure_spi_seq.py b/verify/uvm-python/spi_seq_lib/configure_spi_seq.py index c458586..178526e 100644 --- a/verify/uvm-python/spi_seq_lib/configure_spi_seq.py +++ b/verify/uvm-python/spi_seq_lib/configure_spi_seq.py @@ -20,12 +20,15 @@ async def body(self): # Add the sequqnce here # you could use method send_req to send a write or read using the register name # example for writing register by value > 5 + await self.send_req(is_write=True, reg="CLKGATE", data_condition=lambda data: data == 1) await self.send_req( is_write=True, reg="CFG", # data_condition=lambda data: data in [0b00, 0b01, 0b10, 0b11], data_condition=lambda data: data in [0b00, 0b01, 0b11], ) + await self.send_nop() + await self.send_nop() rsp = [] await self.get_response(rsp) # wait until writing is done diff --git a/verify/uvm-python/spi_seq_lib/spi_MOSI_MISO_seq.py b/verify/uvm-python/spi_seq_lib/spi_MOSI_MISO_seq.py index fb36d33..d51961c 100644 --- a/verify/uvm-python/spi_seq_lib/spi_MOSI_MISO_seq.py +++ b/verify/uvm-python/spi_seq_lib/spi_MOSI_MISO_seq.py @@ -36,7 +36,6 @@ def __init__( async def body(self): await super().body() - await self.send_req(is_write=True, reg="CLKGATE", data_condition=lambda data: data == 1) if not self.disable_control: await self.send_req( is_write=True, reg="CTRL", data_condition=lambda data: data == 0b0 diff --git a/verify/uvm-python/spi_seq_lib/spi_base_seq.py b/verify/uvm-python/spi_seq_lib/spi_base_seq.py index 29adc3d..09151c5 100644 --- a/verify/uvm-python/spi_seq_lib/spi_base_seq.py +++ b/verify/uvm-python/spi_seq_lib/spi_base_seq.py @@ -6,6 +6,8 @@ from cocotb.triggers import Timer from uvm.macros.uvm_sequence_defines import uvm_do_with, uvm_do import random +from uvm.macros import uvm_component_utils, uvm_fatal, uvm_info, uvm_error, uvm_warning +from uvm.base.uvm_object_globals import UVM_HIGH, UVM_LOW, UVM_MEDIUM class spi_base_seq(bus_seq_base): @@ -16,7 +18,7 @@ def __init__(self, name="spi_base_seq"): super().__init__(name) async def wait_tx_fifo_empty(self): - # wait until tx is empty + # wait until tx is empty and not busy self.clear_response_queue() while True: rsp = [] @@ -25,10 +27,10 @@ async def wait_tx_fifo_empty(self): rsp = rsp[0] if ( rsp.addr == self.regs.reg_name_to_address["STATUS"] - and rsp.data & 0b1 == 0b1 + and rsp.data & 0b1 == 0b1 and rsp.data & 0b1000000 == 0b0 ): break - + # wait until not busy cycles_additional = 8 * 4 for _ in range(cycles_additional): await self.send_nop() @@ -36,22 +38,27 @@ async def wait_tx_fifo_empty(self): async def wait_rx_fifo_not_empty(self): # wait received fifo not empty self.clear_response_queue() + await self.send_req( + is_write=True, + reg="TXDATA", + data_condition=lambda data: data == 0, + ) while True: rsp = [] self.clear_response_queue() await self.send_req(is_write=False, reg="STATUS") - await self.get_response(rsp) + while self.response_queue.size() != 0: + await self.get_response(rsp) + uvm_info(self.get_full_name(), f"RSP: {rsp}", UVM_HIGH) + if rsp[0].addr == self.regs.reg_name_to_address["STATUS"]: + break rsp = rsp[0] if ( rsp.addr == self.regs.reg_name_to_address["STATUS"] and rsp.data & 0b100 == 0b0 ): break - await self.send_req( - is_write=True, - reg="TXDATA", - data_condition=lambda data: data == 0, - ) + uvm_object_utils(spi_base_seq) diff --git a/verify/uvm-python/spi_seq_lib/spi_rx_dis_seq.py b/verify/uvm-python/spi_seq_lib/spi_rx_dis_seq.py index c1d022d..f60c4ea 100644 --- a/verify/uvm-python/spi_seq_lib/spi_rx_dis_seq.py +++ b/verify/uvm-python/spi_seq_lib/spi_rx_dis_seq.py @@ -32,7 +32,6 @@ async def body(self): # Add the sequqnce here # you could use method send_req to send a write or read using the register name # example for writing register by value > 5 - await self.send_req(is_write=True, reg="CLKGATE", data_condition=lambda data: data == 1) await self.send_req( is_write=True, reg="CTRL", data_condition=lambda data: data == 0b011 ) diff --git a/verify/uvm-python/spi_seq_lib/spi_send_MISO_seq.py b/verify/uvm-python/spi_seq_lib/spi_send_MISO_seq.py index 923c214..9d9d76b 100644 --- a/verify/uvm-python/spi_seq_lib/spi_send_MISO_seq.py +++ b/verify/uvm-python/spi_seq_lib/spi_send_MISO_seq.py @@ -30,7 +30,6 @@ async def body(self): # Add the sequqnce here # you could use method send_req to send a write or read using the register name # example for writing register by value > 5 - await self.send_req(is_write=True, reg="CLKGATE", data_condition=lambda data: data == 1) await self.send_req( is_write=True, reg="CTRL", data_condition=lambda data: data == 0b111 ) @@ -38,6 +37,7 @@ async def body(self): await self.wait_rx_fifo_not_empty() if random.random() < 0.7: # 20% probability of reading await self.send_req(is_write=False, reg="RXDATA") + uvm_info(self.tag, f"interation number {_}", UVM_MEDIUM) await self.send_req( is_write=True, reg="CTRL", data_condition=lambda data: data == 0b0 diff --git a/verify/uvm-python/spi_seq_lib/spi_send_MOSI_seq.py b/verify/uvm-python/spi_seq_lib/spi_send_MOSI_seq.py index 23cd30c..fb28dcb 100644 --- a/verify/uvm-python/spi_seq_lib/spi_send_MOSI_seq.py +++ b/verify/uvm-python/spi_seq_lib/spi_send_MOSI_seq.py @@ -30,7 +30,6 @@ async def body(self): # Add the sequqnce here # you could use method send_req to send a write or read using the register name # example for writing register by value > 5 - await self.send_req(is_write=True, reg="CLKGATE", data_condition=lambda data: data == 1) await self.send_req( is_write=True, reg="CTRL", data_condition=lambda data: data == 0b11 ) From bcd9ea752c86088300801ac0d3b66e02b9143b58 Mon Sep 17 00:00:00 2001 From: M0stafaRady Date: Thu, 10 Oct 2024 14:20:24 +0300 Subject: [PATCH 5/8] update MISO sequence to make sure the fifo is not empty --- verify/uvm-python/spi_ref_model/spi_ref_model.py | 8 ++++++-- verify/uvm-python/spi_seq_lib/spi_send_MISO_seq.py | 1 + 2 files changed, 7 insertions(+), 2 deletions(-) diff --git a/verify/uvm-python/spi_ref_model/spi_ref_model.py b/verify/uvm-python/spi_ref_model/spi_ref_model.py index b7d2827..1208dd8 100644 --- a/verify/uvm-python/spi_ref_model/spi_ref_model.py +++ b/verify/uvm-python/spi_ref_model/spi_ref_model.py @@ -9,7 +9,7 @@ from EF_UVM.ref_model.ref_model import ref_model from EF_UVM.bus_env.bus_item import bus_item from cocotb.triggers import Event -from cocotb.queue import Queue, QueueFull +from cocotb.queue import Queue, QueueFull, QueueEmpty class spi_ref_model(ref_model): @@ -100,7 +100,11 @@ def write_bus(self, tr): # pass value as it is until logic of ris is implemented pass elif td.addr == self.regs.reg_name_to_address["RXDATA"]: - td.data = self.fifo_rx.get_nowait() + try: + td.data = self.fifo_rx.get_nowait() + except QueueEmpty: + uvm_warning(self.tag, f"reading from rx while fifo is empty") + td.data = "xxxxxxxxxxxxxxxxxxxxxxxx00000000" else: td.data = data self.bus_bus_export.write(td) # this is output to the scoreboard diff --git a/verify/uvm-python/spi_seq_lib/spi_send_MISO_seq.py b/verify/uvm-python/spi_seq_lib/spi_send_MISO_seq.py index 9d9d76b..6401f35 100644 --- a/verify/uvm-python/spi_seq_lib/spi_send_MISO_seq.py +++ b/verify/uvm-python/spi_seq_lib/spi_send_MISO_seq.py @@ -35,6 +35,7 @@ async def body(self): ) for _ in range(self.num_data): await self.wait_rx_fifo_not_empty() + await self.wait_rx_fifo_not_empty()# to make sure it's empty if random.random() < 0.7: # 20% probability of reading await self.send_req(is_write=False, reg="RXDATA") uvm_info(self.tag, f"interation number {_}", UVM_MEDIUM) From 1031ccd329d56508969e875baabbb7f50242bbe7 Mon Sep 17 00:00:00 2001 From: M0stafaRady Date: Thu, 10 Oct 2024 17:07:17 +0300 Subject: [PATCH 6/8] Read fifo status 2 times only in AHB mode --- verify/uvm-python/spi_seq_lib/spi_send_MISO_seq.py | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/verify/uvm-python/spi_seq_lib/spi_send_MISO_seq.py b/verify/uvm-python/spi_seq_lib/spi_send_MISO_seq.py index 6401f35..66c9f68 100644 --- a/verify/uvm-python/spi_seq_lib/spi_send_MISO_seq.py +++ b/verify/uvm-python/spi_seq_lib/spi_send_MISO_seq.py @@ -9,7 +9,7 @@ from uvm.macros import uvm_component_utils, uvm_fatal, uvm_info import random from spi_seq_lib.spi_base_seq import spi_base_seq - +import cocotb class spi_send_MISO_seq(spi_base_seq): # use this sequence write or read from register by the bus interface @@ -35,7 +35,8 @@ async def body(self): ) for _ in range(self.num_data): await self.wait_rx_fifo_not_empty() - await self.wait_rx_fifo_not_empty()# to make sure it's empty + if cocotb.plusargs["BUS_TYPE"] == "AHB": # since apb is so fast + await self.wait_rx_fifo_not_empty()# to make sure it's empty if random.random() < 0.7: # 20% probability of reading await self.send_req(is_write=False, reg="RXDATA") uvm_info(self.tag, f"interation number {_}", UVM_MEDIUM) From 9e462052153a206f391478466b37557e15774ced Mon Sep 17 00:00:00 2001 From: Passant Date: Mon, 4 Nov 2024 17:40:38 -0700 Subject: [PATCH 7/8] bump IP version --- EF_SPI.yaml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/EF_SPI.yaml b/EF_SPI.yaml index fd0138f..00062e9 100644 --- a/EF_SPI.yaml +++ b/EF_SPI.yaml @@ -7,7 +7,7 @@ info: license: APACHE 2.0 author: Mohamed Shalan email: mshalan@efabless.com - version: v1.0.10 + version: v1.0.11 date: 17-09-2024 category: digital tags: From e10fbfb521dd2d006369c9fb820a70d071dd372e Mon Sep 17 00:00:00 2001 From: Passant Date: Fri, 8 Nov 2024 18:33:47 -0700 Subject: [PATCH 8/8] ~ fix syntax error and repackage v1.0.11 --- hdl/rtl/EF_SPI.v | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/hdl/rtl/EF_SPI.v b/hdl/rtl/EF_SPI.v index 873cf58..036c0bd 100644 --- a/hdl/rtl/EF_SPI.v +++ b/hdl/rtl/EF_SPI.v @@ -49,8 +49,8 @@ module EF_SPI #(parameter output wire tx_level_below, output wire [FAW-1:0] tx_level, - output busy, - output done, + output wire busy, + output wire done, input wire miso, output wire mosi,