There are no tags for this page.
Dobrica Pavlinušić's random unstructured stuff
ULX3S Lobby

Helpful notes from chat about ULX3S



It should not be that hard. I have i2c in SaxonSoc in other projects such as https://github.com/SpinalHDL/SaxonSoc/blob/dev/hardware/scala/saxon/board/blackice/BlackiceSocArduino.scala#L25

The generated board support packages include a generated dts, but it is not used yet and the simple i2c generator that I wrote does not generate the dts.

There is a problem building SaxonSoc Linux, that some build randomly do not work. It seems to be something to do with SDRAM access.

@Dolu1990 is about to redo the SDRAM access for the Ulx3s, which should make it more reliable and faster, as he plans to support double frequency access.

There is a lot of information on the development of the u-boot version here , which might be useful to you - SpinalHDL/SaxonSoc#7


I2c Linux support will also need a spinal.lib driver here - https://github.com/SpinalHDL/linux/tree/linux-5.0.y/drivers/i2c

The terasic De1Soc version of SaxonSoc Linux has a dts entry for an led for disk access - https://github.com/SpinalHDL/buildroot/blob/saxon/board/spinal/saxon_default/spinal_saxon_default_de1_soc.dts#L194

We really need a better GPIO mapping for the Ulx3s. That might involve including adding a second gpio peripheral to the hardware (gpioB) and doing a better lpf file mapping to pins. It might mean increasing the niumbers of pins that support interrupts. It would be good to include access to the buttons and switches and to make it easy to add Pmods that need interrupt support like the enc28j60 one.


Mario Hoffmann @hoffma_gitlab Aug 05 16:11

Hello, I wanted to have a 90 degree shifted clock. I was trying out the ecp5pll from @emard. I get it running and the clock adjustment seems to work, but somehow it does not get shifted for me. Is this currently not working with yosys and so forth, is there anything I have to take care of, or might it just be a bug on my side? Tried to search this chat a bit and just searched a bit on the internet but the things I found about it were quite old and not necessarily about my problem. Any ideas? I am using the vhdl version btw

emard @emard Aug 05 16:59

There's some order of signals and small delays between them for dynamic shifting to work. https://github.com/emard/ulx3s-misc/blob/master/examples/sdram/memtest_mister/hdl/top/top_memtest.v#L73 here is module to control phase shifts by pressing of BTN for testing of SDRAM with variable phase shift of the clock to chip

Mario Hoffmann @hoffma_gitlab Aug 05 17:01

alright, ill look at that. thanks

Mario Hoffmann @hoffma_gitlab Aug 05 17:53

Oh nice it works. My thinking was just a bit wrong and there was a little bug too. Thanks

emard @emard Aug 05 18:07

ecp5pll has possibility for fine-precision phase adjustment but this simple BTN module doesn't generate proper phaseloadreg signal https://github.com/emard/ulx3s-misc/blob/master/examples/sdram/memtest_mister/hdl/btn_ecp5pll_phase.v#L51



emard @emard Aug 18 09:06

SSD1331 96x64 is full featured OLED beautiful contrast, but currently best buy is ST7789 1.3" 240x240 LCD less contrast but more pix and less $. Do not solder directly the display. Solder female 7-pin header and plug the display. Mechanical stabilization can be 3D printed https://github.com/emard/ulx3s/tree/master/box it will "work" properly only if whole box is printed. There is no problem with heat normally to FPGA but SSD1331 with wrong software commands can become hot to fry fingers and smoke, it happened to me once, colors faded and I just replaced display. Onboard USB-SERIAL can provide 2nd JTAG channel for openocd debugger of RISCV processor it will work but it will be VERY slow (for debug single step ok, but for transferring Mbps no).



emard @emard Aug 18 09:43

Yes for RTC I first saw it "works" but after few reboots I found out that it resets to compile time or something. Core could consult onboard RTC using i2c and then set unix time integer counter which will continue ticking afterwards. For setting RTC we have esp32 and other options. Btw import ntptime; ntptime.settime() will set ESP32 localtime() from a pool of network NTP servers and then esp32 can initialize onboard RTC here I have played with this https://github.com/emard/ulx3s-misc/tree/master/examples/rtc/micropython-mcp7940n/esp32


emard @emard Aug 20 01:52

@pnru_gitlab here is 8-bit master interface. I haven't tested it very simple by reading seconds and seems ok https://github.com/emard/ulx3s-misc/blob/master/examples/rtc/i2c_master/proj/hdl/i2c_master_8bit.v


emard @emard Aug 20 09:58

when we are at verilog, I have found on the net several i2c bidirectional bridges. Only one code worked at our board but it works only if compiled by diamond. trellis compiles but doesn't work. Can someone take a look what I have missed: bridge: https://github.com/emard/ulx3s-misc/blob/master/examples/rtc/micropython-mcp7940n/proj/hdl/i2c_bridge.v toplevel usage: https://github.com/emard/ulx3s-misc/blob/master/examples/rtc/micropython-mcp7940n/proj/top/top_i2c_bridge.v

emard @emard Aug 20 22:04

for me it works for any gpdi_scl/sda PULLMODE=UP, DOWN, or NONE so it's not pull setting. I can prepare a bitstream and micropython to ulx3s-bin example that initializes the clock setting time from NTP

emard @emard Aug 20 22:18

https://github.com/emard/ulx3s-bin/tree/master/esp32/micropython/rtc can you try this RTC esp32 example for NTP setting? >>> rtcdemo.mcp.time should advance seconds

emard @emard Aug 21 00:04

RTC traffic also appears at GPDI connector (if there's i2c chip 3.3V->5V adapter soldered on board PCA9306D). Some monitors may hold i2c lines. Also gpdi connector can be used to monitor traffic if e.g. you have hdmi breakout board
If you don't have battery, RTC will keep setting until board is powered off
If you have 2 ULX3S boards and mini-display OLED/LCD, you can connect 2 ULX3S together and on one run scopeio, which will monitor the other i2c traffic
I can prepare scope stuff for such setup because scopeio is vhdl, advanced so much that ghdl won't have chance in near future to compile it

emard @emard Aug 21 00:09

UPS but we have problem there will be 2 RTC chips colliding address :)
about i2c master 8bit. First write highest bytes 3,2,1 (order not important) and last write byte 0, this should initiate i2c transaction. byte 3=0x80 is READ, byte 3=0x00 is write
If you write 0x00 to register 0x00 (seconds) it will stop RTC. To start, it needs 0x80 written to 0x00 (MSB bit must be set) then the RTC should start "ticking"

emard @emard Aug 21 18:14

I fixed i2c_bridge.v to work with both trellis and diamond.

Paul Ruiz @pnru_gitlab Aug 21 23:35

Which way does the battery go? I think with the + side (cap) up and the - side (ribbed) to the PCB?
@emard: thanks for all the links, but your code already appears to work. The long one is interesting, it uses the same two level state machine idea that my non-working i2c controller uses.

emard @emard Aug 21 23:59

Battery goes + up (larger part of battery should be in contact with metallic holder soldered) - down (smaller part of battery in contact to big circular pad on the PCB
Glad to hear good news that my code works - it hasn't been tested on real CPU but I made some BTNs toplevel and a read and write to register 0 worked



emard @emard Aug 18 21:11

@gkankanh MAX11125 is 1Msa/s total so e.g. if you use 4ch then each channel will be 0.25MSa/s per channel. For oscilloscope it, we have ready solution at hdl4fpga/ULX3S/scopeio you will see traces on monitor. For analysis, onboard USB-serial can do 3Mbps so it could be nearly useable. For faster ADC, yes 100 Mbit ethernet ETH8720 from ebay, module for 2.2$ and for example ebay's AN108 AD/DA module 32MSa/s input, 125MSa/s output https://www.ebay.com/itm/ADDA-Module-Data-Signal-Acquisition-High-speed-Directly-pluggable-connector-/253556250998 also scopeio supports it

how to solder headers


emard @emard Aug 19 09:45

To have GP/GN not be swapped from "default" design, Either solder 90° FEMALE headers on top side of board (nice for PMODs directly) or straight 0° MALE pins down on bottom side of board. PMODs can also plug to other end of flat cable and pinout will be identical as if 90° was soldered onboard.



Lawrie Griffiths @lawrie Aug 19 12:15

I am using Ubuntu 20.04, so I need to use pip3 not pip. (You can't get python2 pip on 20.04 easily).
The installation instructions for nmgen-boards says "Todo", so I installed it like the m_labs version said.
I changed the blinky example to use ULX3S_85F_Platform and ran that. It complained that tool {} was missing.
It seemed that it needed OpenFpgaLoader for upload, so I installed that, and then the blinky worked.

from nmigen import *
from nmigen_boards.ulx3s import *

class Blinky(Elaboratable):
    def elaborate(self, platform):
        led   = platform.request("led", 0)
        timer = Signal(26)

        m = Module()
        m.d.sync += timer.eq(timer + 1)
        m.d.comb += led.o.eq(timer[-1])
        return m

if __name__ == "__main__":
    platform = ULX3S_85F_Platform()
    platform.build(Blinky(), do_program=True)



SDRAM memtest


Lawrie Griffiths @lawrie Sep 01 22:04

@pnru_gitlab @Dolu1990 asked these questions about using the SDRAM, which I thought you might know something about from all your recent work on SDRAM drivers:
I'm thinking about the SDRAM
currently, the soc is at 50 mhz, and the sdram run at 100 Mhz using DDR io
but maybe we should quad pump the SDRAM, and doing some bootloader calibration to ajust read delays
i'm just currently not sure what is the critical path of the SDRAM chip themself
in other words "why they are specified to X frequancy and not more"

Dolu1990 @Dolu1990 Sep 01 22:05

Moaaaar powaaaaaaaa

emard @emard Sep 01 22:36

oooh yeea :)) if you want to push SDRAM near the edge and give it some heat, on selected designs it can push 133MHz chips to 180-200 MHz, fmax depends on each board. 12F performs better than 85F. Here's memtest https://github.com/emard/ulx3s-misc/tree/master/examples/sdram/memtest_mister shows results on DVI monitor and with BTNs can adjust phase shift dynamically and watch for errors.

Dolu1990 @Dolu1990 Sep 01 23:01

Nice thanks :)
So this test controle the shift of the clock sent to the DRAM ?
(it doesn't use the programable input delay ?)

emard @emard Sep 01 23:08

Yes this has a classic sdram driver that normally needs 90° phase offset to chip hardware, but as fmax is getting higher the actual phase shift which makes it really work moves. PLL is used to provide phase shift. Paul has made a better sdram driver with cool vendor-independent delay solution with a number of NOT gates.Only ns delay per NOT gate remains vendor dependent

Dolu1990 @Dolu1990 Sep 01 23:09

ok :D

Paul Ruiz @pnru_gitlab 00:02

@lawrie @Dolu1990 I am not sure I understand the SDRAM questions. In any case, my latest version is here: https://gitlab.com/pnru/cortex/-/blob/master/sdram.v
In particular note new lines 45-47 - I am not sure why, but this mod generally pushes Fmax up to about 200MHz (it depends a bit on the NextPNR seed).

I am not sure what you mean by "using DDR io" - does the SDRAM chip on the ULX3S support DDR? Maybe you mean by DDR that it runs at twice the speed of the CPU or that it uses burst size 2?

I don't know what the critical path in the SDRAM chip is, but I do have a hypothesis. When working with a CAS delay of 3 clocks, the data really arrives after 2 clocks plus 6-7ns (spending on the speed grade). If you clock a grade 6 chip (PC166) faster, a clock cycle will take less than 6ns and the data will only arrive after the third rising clock edge. My guess is that the 6-7ns is related to the speed of the sense amplifiers or something like that.

resource utilization


Dolu1990 @Dolu1990 Sep 02 14:12

Is somebody aware of a way to get hearchical ressource utilisation report out from yosys/next-pnr for ECP5 ?
Basicaly, trying to nail down the ressource usage

David Shah @daveshah1 Sep 02 14:18

You can get a hierarchical report with Yosys by passing -noflatten to synth_ecp5

ps2 keyboard


Kid CUDA @KidCUDA_gitlab Sep 08 22:12

anyone used a PS2 keyboard with ULX3S?
like a proper PS2 keyboard with the pins adapted to USB?
is a level shifter needed or is the USB port 5V-data-tolerant?
from the schematic it doesn't look 5V tolerant but I'm not sure how else it would work with just a pure PS2 adapter as suggested in the docs

emard @emard Sep 08 22:52

@KidCUDA_gitlab US2 pins are 5V tolerant, limited by R and Zener diodes. Still some PS/2 keyboards don't accept 3.3V levels. Best is to obtain combo PS/2+USB they usually work in both modes for ULX3S
PS/2 is normally used over OTG connector for most of our retro-computing cores, apple1-2, ti99, zx, vic20, QL just to name a few


source: https://gitlab.com/pnru/cortex


Paul Ruiz @pnru_gitlab Sep 02 23:11

    8s is super-comfortable! Btw I wonder how did cortex start, before it ever booted they need some filesystem to hold files. Is cortex filesystem mountable by modern linux? How did they made it in early times?

The Cortex was a traditional home computer with Basic in its day. Running Unix on it was my project some 6-7 years ago. It was a long journey: porting a C compiler and tool chain, building simple kernels with a linked in user program (downloaded to the H/W via something similar to S-records), etc. When the time for disk access came, I used a tool to create & manage disk images.

For the original Unix, the file system was almost the first thing that was built, after the assembler (that is how a.out got its name: assembler output). An empty disk image was written by a custom format program. Files were then loaded from paper tape. Some 1969/1970 Unix code can be found here:
In its first incarnations it was all assembler, but many of the core ideas were already there. Some more background is here:

emard @emard Sep 02 23:14

Ahaaaa so unix was not all the time available on cortex hardware. Still I'd wanted to know how did you initially start with populated filesystem. Normally e.g. if we have linux on riscv, we can mount the same partition on x86 PC, copy files and and it will work on riscv, but how was this done on cortex?

So If I understood, you have a tool that from a directory creates disk image, but there's currently no support to actually mount cortex fs on linux for example. linux has some possibility to write a user-space fs driver like "fuse" but I ghess thats difficult and fragile

Paul Ruiz @pnru_gitlab Sep 02 23:29

You can follow my journey here, in 315 commits:

I use a program ("ufs") which creates a disk image from scratch and then adds files to it. The source code is here:

Even on the mini Cortex hardware, the CF Card uses FAT formatting and has an image file on it. I make sure the image is contiguous and the boot loader lets the Unix disk driver know in which sector the image starts. This way I can simply copy disk images to the CF card without needing to use special tools.

Actually, the card also has disk images for other OS's as well - MDEX and NOS, which are somewhat similar to CP/M and MS-DOS 3 respectively.

emard @emard Sep 02 23:44

There has been a lot of concentrated effort! The idea to use contiguous file in FAT is very good, so the CF itself can be easily written from laptop.

Paul Ruiz @pnru_gitlab Sep 02 23:53

Thank you. The ulx3s Cortex has it even easier: because of the ESP32, now I don't even have to worry about things being contiguous and I can ftp disk images without having to handle the SD card.

emard @emard Sep 03 00:34

yeees it was a piece of luck that for esp32 appeared good micropython support with almost all important things working and that spi-jtag adventure turned out successful. I have ulx3s with SD in a box and once inserted SD I never move out, just ftp files. Things will be even better when WROVER-E prototype starts working, 4MB RAM, 16MB FLASH no more out of memory. Bitstreams could be unzipped on-the-fly, even larger FLASH chips supported with 64K and 256K erase blocks (esp32 must buffer data size of erase block and now we are struggling with 4K buffers)


Upload Files

Click "Browse" to find the file you want to upload. When you click "Upload file" your file will be uploaded and added to the list of attachments for this page.

Maximum file size: 50MB

File Name Author Date Uploaded Size

Save Page As

Enter a meaningful and distinctive title for your page.

Page Title:

Tip: You'll be able to find this page later by using the title you choose.

Page Already Exists

There is already a page named XXX. Would you like to:

Save with a different name:

Save the page with the name "XXX"

Append your text to the bottom of the existing page named: "XXX"

Upload Files

Click "Browse" to find the file you want to upload. When you click "Add file" this file will be added to the list of attachments for this page, and uploaded when you save the page.

Add Tags

Enter a tag and click "Add tag". The tag will be saved when you save the page.