In the previous post, I was able to harden a RISC-V based SoC in Openlane. There were 3 methods to harden the chip according to Efabless documentation and I utilized the first method, which was hardening the macros first, then integrating all the macros in the top module by instantiating them, while there must be no standard logic in the top module.
You can find the details in these links:
Hardening PicoRV32:
https://www.mehmetburakaykenar.com/open-source-ic-design-flow-for-an-open-source-risc-v-core/444/
Hardening the SoC:
Here is the final view of the chip in Openroad GUI:
Ok, now I will try to utilize the third method, where in the top module there will be hardened macros and standard logic cells. I will only import picorv32 IP as hard macro and let Openlane to synthesize other RTL logic in the top module.
Let’s remember chip integration methods from Efabless Caravel User Project, which uses Openlane also:
https://caravel-user-project.readthedocs.io/en/latest/#caravel-integration
Caravel documentation states that there are 3 Chip hardening options. In their reference, user project wrapper is the top module:
1) Hardening the user macro(s) first, then inserting it in the user project wrapper with no standard cells on the top level:
2) Flattening the user macro(s) with the user_project_wrapper:
3) Placing multiple macros in the wrapper along with standard cells on the top level:
Let’s also remember the configuration parameters for method 3 of the integration. Efabless published a webinar record recently (Dec 11 2023) and gave some insights for integration methods. I took these images from this YouTube video:
Method1:
Method3:
Method3: Placing the user macro(s) in the wrapper along with standard cells on the top level
For method 1, we needed to create a new Verilog file and took all the logic assignments in the top module inside this module, named it as mem_decode. Well, this time we do not need to create this file, since we can include logic assignments in the top module in method 3.
First, focus on config.tcl (you can use json format for config file, even newer versions of Openlane use json but tcl seems easier to modify for me). We only have 1 macro, picorv32 and instatiation name is cpu. The config parameters for the macro are:
set ::env(VERILOG_FILES_BLACKBOX) [glob $::env(DESIGN_DIR)/verilog_blackbox/*.v]
set ::env(EXTRA_LEFS) [glob $::env(DESIGN_DIR)/lef/*.lef]
set ::env(EXTRA_LIBS) [glob $::env(DESIGN_DIR)/lib/*.lib]
set ::env(EXTRA_GDS_FILES) [glob $::env(DESIGN_DIR)/gds/*.gds]
set ::env(MACRO_PLACEMENT_CFG) [glob $::env(DESIGN_DIR)/macro.cfg]
set ::env(FP_PDN_MACRO_HOOKS) "cpu vccd1 vssd1 vccd1 vssd1"
For synthesis options, we need to change SYNTH_ELABORATE_ONLY from 1 to 0 in method 3, since this time we need synthesis for the modules that are not hardened.
set ::env(SYNTH_ELABORATE_ONLY) 0
For floorplan options, we need to change these parameters for method 3:
set ::env(RUN_TAP_DECAP_INSERTION) 1
set ::env(FP_PDN_ENABLE_RAILS) 1
For placement options, we need to change these parameters for method 3:
set ::env(PL_RESIZER_BUFFER_INPUT_PORTS) 1
set ::env(PL_RESIZER_DESIGN_OPTIMIZATIONS) 1
set ::env(PL_RESIZER_TIMING_OPTIMIZATIONS) 1
set ::env(GLB_RESIZER_DESIGN_OPTIMIZATIONS) 1
set ::env(GLB_RESIZER_TIMING_OPTIMIZATIONS) 1
set ::env(RUN_CTS) 1
set ::env(RUN_FILL_INSERTION) 1
For routing options, we need to change these parameters for method 3:
set ::env(GRT_REPAIR_ANTENNAS) 1
I will keep the same dimensions for the die with method 1:
set ::env(DIE_AREA) "0 0 2600 1500
For macro placement file, I only need “cpu” locations. I will keep same location for the cpu:
cpu 1400 600 N
In picosoc.v, we only need power net connections for picorv32 cpu macro. For other modules we won’t include these pins.
`ifdef USE_POWER_PINS
.vccd1 (vccd1), // User area 1 1.8V supply
.vssd1 (vssd1), // User area 1 digital ground
`endif
Pin order file will be the same.
I will add all the Verilog files in src directory other than picorv32. Let’s try our first run and try to guess in which step we will get our first error. My assumption is Linter 🙂
Surprise! It is in step 16 global routing resizer and no error. But, it seems it stucked there:
I checked the synthesis report and we have 36053 cells (actually 1 of them is picorv32). I think the die area I defined could be small for this design but I am not sure. I will wait a little bit more and increase the area and rerun (It can be seen strange to write like this but I am writing this text while Openlane is still running!).
I checked resizer_design.log and saw this warning:
[WARNING GRT-0115] Global routing finished with overflow.
Oohh, meanwhile somehow it passed to the global routing resizer timing optimizations step. Ok, I need to go to bed, so I will leave the run and see what happened in the morning!
In the morning I saw error finally:
Himmm, it seems from the error that we had a crash, could be a memory issue. I need to check. First, let’s look at the placement of the cells from results/placement in the OR GUI:
So, actually it seems we can even reduce the die area. There are plenty of empty spaces in the chip. Let’s find out the crash issue. We can check routing congestion in OR GUI:
We can also see in issue_reproducible logs there is a congestion and violations:
I will try to set FP_SIZING as relative and tune FP_CORE_UTIL and PL_TARGET_DENSITY parameters this time. So I got an error in global routing resizer step.
Let’s check OR GUI for placement:
I didn’t expect this 🙂
I will try 2000×2000 area and place cpu macro in the center and rerun. If that does not work, I will consider using memory as a hardened macro since I assume it causes the routing problems.
The flow got stuck at global routing again. I checked routing congestion:
Well, I will add memory as hard macro to solve this problem and rerun. By the way the flow have thrown error in global routing already while looking congestion.
After I used pre-harden macro for memory IP, the flow completes successfully. Here is the OR GUI view:
Here is the GDS view from Klayout:
We see that memory IP was the reason for Openlane crash. After we utilized memory as a pre-hardened macro, the flow completed successfully.
I tried to show each and every error that I encountered during this design flow and you see the time that I consumed and iteration number for getting the successful result. Still, this design needs a lot more improvements, such as area, speed, power optimizations and verification of the design.
You can find all the files used in this tutorial in my github repo:
https://github.com/mbaykenar/openlane-designs
Regards,
Mehmet Burak AYKENAR
You can connect me via LinkedIn: Just sent me an invitation