-
Notifications
You must be signed in to change notification settings - Fork 244
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
OrangeCrab #98
OrangeCrab #98
Conversation
45d48a3
to
203b628
Compare
This PR is now rebased on top of #99. The last three commits in this PR are the changes required for adding any new board or a new example for an already supported board. |
I had a little bit of time to look at this. Most of the orangecrab r0.2 boards in the wild (including mine) use the LFE5U-25F-8MG285C device, so the correct PNRFLAGS would be:
At this point, the PnR fails because all of the dual port RAM blocks are used up in this device:
I tried to find the best place to adjust this size, but my VHDL is very limited (I'm more of a verilog guy). |
I should also add, this is obviously an issue with the inferred RAMs being way too large, the 25F device should have plenty of RAM. See specs here: https://1bitsquared.com/products/orangecrab |
@jeremyherbert, you are correct. The default sizes of dmem and imem (
The 25F has 126KB or BRAM, which is very slightly below the default 128KB in the MinimalBoot template. That is still much more that the 2KB minimum we have run tests with. Hence, I set both to 32KB arbitrarily. |
See https://github.com/stnolting/neorv32/blob/master/rtl/templates/processor/neorv32_ProcessorTop_MinimalBoot.vhd#L42-L91. Those are the generic parameters defined in the template (entity) we are using. When instantiating that template/entity, BoardTop files typically override the clock frequency only (see https://github.com/stnolting/neorv32/blob/master/setups/examples/neorv32_Fomu_BoardTop_MinimalBoot.vhd#L133), but you can override any of those parameters: https://github.com/stnolting/neorv32/pull/98/files#diff-6b40cb886766bdba185127a98b9d943808cbe81c670ff6ff8cbf3423fa40ed0bR80-R84. |
The OrangeCrab has an external DDR with 128 MB. Hence, the mid-term goal should be to append a controller to the external bus of the NEORV32 and have the IMEM and/or DMEM assigned there. Note that we can have mixed-language designs. Therefore, we might use the same strategy as in antonblanchard/microwatt: they use litedram (see enjoy-digital/litedram). |
Awesome work! 👍 @jeremyherbert
As far as I know, sysMEM primitives in the EPC5 are 2Kbytes (+ bits for something like EEC but I think synthesis cannot use these extra bits for something meaningful here) each. According to the report, Jeremy's FPGA provides 56 of these blocks making 56*2=112kB. 🤔
Thanks for clearing this. @jeremyherbert The core's configuration parameters for memory size are: neorv32/rtl/core/neorv32_top.vhd Line 85 in 87ef9ef
and neorv32/rtl/core/neorv32_top.vhd Line 89 in 87ef9ef
|
That would be awesome!
That looks very good! I'm very happy that the memory controller supports Wishbone so there is no need for extra bridging logic. |
I believe that is decided by the synthesis tool. If it sees it fit as a BRAM, it does not try to use the distributed RAM. If it cannot fit into a BRAM, then distributed RAM is used (e.g. reading multiple registers from a bank at the same time).
I took the number from The nextpnr log in the CI run reports |
@stnolting: |
I am not sure here. I think Vivado does it the other way around: if a RAM is larger than a certain threshold it is mapped to BRAM. If a BRAM description does some non-defualt thinks (like entire memory reset) it is mapped to (lots and lots of) distributed RAM.
😄 👍
The default bootloader uses 4kB of memory making a total of 32kB + 32kB + 4kB = 68kB. With 2kB in each sysMEM this should be 34 BRAMs. So yeah, there is something going wrong. I will also have a look at the implementation report. edit |
Note that synthesis and implementation tools do support specifying it explicitly, either as a global option or through attributes in the VHDL sources. However, the specific mechanism depends on the tool. See the Tip in https://ghdl.github.io/ghdl/using/Synthesis.html#synthesis-options (https://github.com/ghdl/ghdl/blob/master/src/ghdldrv/ghdlsynth.adb#L138-L239). |
DMEM and bootloader ROM mappings seem right. But I cannot find any IMEM related mapping results 🤔 |
neorv32_inst: entity work.neorv32_ProcessorTop_MinimalBoot | ||
generic map ( | ||
CLOCK_FREQUENCY => f_clock_c, -- clock frequency of clk_i in Hz | ||
MEM_INT_IMEM_EN => false, |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
False??? Is this a typo?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It is. My bad 😟 . I'll fix that immediately.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Done. Now synthesis results are ok! 34/56. Thanks for finding that stupid mistake...
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
No worries 😄
Looks fine now! 🎉 Seems like the register file is not mapped to BRAM, but is is identified as RAM:
I wonder if it is mapped to distributed RAM (but there is nothing in the report) or if it is implemented using plain logic? 🤔 |
Search
See also:
|
I had some success this morning, I got to the blinking boot LED and also have UART (19200 baud, 8N1) outputting the following:
I am doing this all over JTAG, not via the OrangeCrab USB bootloader and the SPI flash, so I assume that is what the
Note: The constraints file for the OrangeCrab doesn't match the silkscreen for some pins (pin 9 is one of them). The correct constraints are in this pinout picture: https://gregdavill.github.io/OrangeCrab/r0.2/docs/pinout/ I filed a bug for that here: orangecrab-fpga/orangecrab-examples#20 Below is the VHDL I used for the BoardTop. It's a bit hacky as I was just messing around to get stuff to work. I would create a pull request, but I am not too familiar with VHDL formatting guidelines, so I was hoping you could make these changes in your branch in a neat way. I chose 24MHz as the clock arbitrarily; according to the PnR it should run up to ~70MHz.
Here are the GPIO pins in the constraint file that match the silkscreen (note the commented out ones have no marking on the silkscreen)
|
Could I also suggest generating the |
Thanks for clearing the distributed RAM issue! :hear:
I'm happy to hear that! :)
Sounds reasonable. You could also use the PLL's lockes signal to drive the processor's reset and connect the PLL reset to an external button. But this is just an idea and absolutely not critical here.
I am fine with this. This looks like a very nice start setup 👍
According to this https://gitlab.raptorengineering.com/dormito/litex/-/commit/b014c7194be669d8c471c11074e775b0d6e6d471 it should be possible. But I am an absolute beginner when it comes to Trellis 😅 |
4730a2b
to
b109890
Compare
The following tasks are done (some before and other after Jeremy's update):
However, I did not modify the constraints file. The modifications provided by Jeremy are inconsistent, in the sense that some of the bits of |
acd6915
to
3024afe
Compare
Ok, I fetched all of these changes and built it, loaded the newly generated svf and it works great:
Two small issues:
I think that once these two are sorted, this should be good to merge. And one problem for me to work on is that I have not tested anything to do with the flash (in this case, Ideally I would like to keep the USB bootloader, and then store the neorv32 bit file at an offset in the flash past this bootloader, and then store the actual executable at a further offset in the flash (it's a 16MByte flash, so there should be plenty of room for all of this). I assume that the steps to do this are something like the following
Any ideas, suggestions or pointers here would be appreciated. PS: with respect to the constraints file, I would suggest adding a note to the readme or similar about this. The main issue is that, for example, the silkscreen pin numbers do not have a pin 4 anywhere; the only numbered GPIO pins on the silkscreen are 0, 1, 5, 6, 9, 10, 11, 12, 13; the rest have names like |
I see that I should have read the documentation closer around the flash offset: https://stnolting.github.io/neorv32/ug/#_customizing_the_internal_bootloader |
I should have also read the flash datasheet further as well… it seems that SPI commands are always accepted. So I’m thinking that all I need to do to get application loading from flash is to rebuild the bootloader with the correct flash offset, then copy that newly built executable into the vhd file which contains the bootloader, and it should work from there? |
Co-Authored-By: Jeremy Herbert <jeremy.006@gmail.com>
Co-Authored-By: Jeremy Herbert <jeremy.006@gmail.com>
🎉 🎉 🎉
I fixed both of those. The SVF is now 522K, instead of 1.3M. @stnolting, I think this is ready to merge.
My main point is that it does not make much sense to care about fixing it in this repo only. It is particularly confusing to have GPIO as an array of 13 bits, if ~8 of them have other purposes. My proposal is:
In fact, my expectation is to submodule hdl/constraints at some point. That's why I'm picking the constraints files from there, and maintaining the naming scheme. Overall, maintaining constraint files and board metadata should be out of scope of this repository. We do need those resources, but the effort devoted to it in the context of NEORV32 should be minimal. |
Good to hear! 👍 🎉
I think that all SPI flashs always support "normal" (= single-bit) SPI as a fallback.
That's right! But you do not need to copy anything - the makefile will take care of all that. neorv32/sw/bootloader$ make USER_FLAGS+=-DSPI_BOOT_BASE_ADDR=0x12345678 clean_all bootloader This will override the default SPI boot address with ℹ️ All default defines that shall be overriden have to be added to the |
This is work in progress for supporting ECP5 devices, and specifically the OrangeCrab board.
@jeremyherbert, can you please have a look? Currently, the implementation is successful and a bitstream is generated in CI. However, please, do NOT try that bitstream yet. First, we need to ensure that the design is correct for your board:
Jeremy, can you review
neorv32_OrangeCrab_BoardTop_MinimalBoot.vhd
and enhance it so that it makes sense (the UART works)? The command for generating the bitstream ismake -C setups/examples BOARD=OrangeCrab MinimalBoot
.If you instantiate hard IP (such as a PLL), we need to add
setups/osflow/devices/sb_ecp5_components.*
sources. That might need overridingDEVICE_SRC
, when callingsetups/OrangeCrab/Makefile
fromsetups/examples/Makefile
. Please, let me know if you need help with that.