June 2, 2022

FPGA - "bitstream" project

The ultimate goal here is to have some bare metal code of mine load a bitstream into the PL on a Zynq. I plan to use the Ebaz 4205 for this project, primarily because it is sitting on my bench right now ready to go.

Blink from the PL

My project "ebaz_blink_2" has done just this. It takes a PL fabric clock, divides it down, and sends that to an LED. This works entirely independently of the PS.

I fire up Vivado 2019.1, open that project and see if I can reload the bitstream and get the LED blinking again.

I need to connect a USB cable to my pi-pico USB gadget, and start the server running:

[tom@trona daemon]$ xvcd-pico
xvc-pico listening on port 2542
In Vivado, I open "Hardware Manager". I use "Open Target, Open New Target, go through the dance to add and open a new Xilinx Virtual Cable (XVC)

It get all kinds of weird errors, until I realize that I need to have the target board powered on, not just the JTAG interface. I use "Program Device" under "Hardware Manager" on the lower left. Once this finishes, the green LED is blinking at about 2 Hz, the red LED is off.

This validates the bitstream and lets me use it with confidence in the next stages.

A bitstream download tool

Off on a tangent already. A person certainly can use Vivado to download an existing bitstream (at least if it lives inside of a Vivado project). It would be nice to have an independent tool (maybe a command line tool) to simply do that.

There are many mysteries in this business. Something runs on port 3121 and is part of the process. I have also heard of something called "IMPACT", which is some component of the Xilix software. As near as I can tell, IMPACT is part of the older ISE package and has nothing to do with Vivado.

Some searching led me to this project:

I have run into xc3sprog before, but we will leave that be for the present and investigate openFPGAloader. The name at least is promising.

A quick peek using "ps -alx" shows all this running and indicates what is listening on port 3121.

0  1004  756264    2338  20   0 226340  7848 do_wai Ss   pts/3      0:00 bash
0  1004  756316  756264  20   0  11364  2200 wait_w Sl+  pts/3      1:02 xvcd-pico
0  1004  756318    2134  20   0 222644  3428 do_wai S    ?          0:00 /bin/bash /tools/Xilinx/Vivado/2019.1/bin/vivado
0  1004  756334  756318  20   0 222644  3396 do_wai S    ?          0:00 /bin/bash /tools/Xilinx/Vivado/2019.1/bin/loader -exec vivado
0  1004  756395  756334  20   0 7936752 2106160 futex_ Sl ?         2:18 /tools/Xilinx/Vivado/2019.1/bin/unwrapped/lnx64.o/vivado
1  1004  756767    1405  20   0 622596 11748 do_sel Rsl  ?          0:21 /tools/Xilinx/Vivado/2019.1/bin/unwrapped/lnx64.o/hw_server -d -I20 -s TCP:127.0.0.1:3121
0  1004  756938  756395  20   0 222644  3420 do_wai S    ?          0:00 /bin/bash /tools/Xilinx/Vivado/2019.1/bin/xsdb -e set xsdb_idle_timeout 20 ; source /tools/Xilinx/Vivado/2019.1/scripts/xsd
0  1004  756953  756938  20   0 222644  3448 do_wai S    ?          0:00 /bin/bash /tools/Xilinx/Vivado/2019.1/bin/loader -exec rdi_xsdb -e set xsdb_idle_timeout 20 ; source /tools/Xilinx/Vivado/2
0  1004  757014  756953  20   0 963440 95676 futex_ Sl   ?          0:01 /tools/Xilinx/Vivado/2019.1/bin/unwrapped/lnx64.o/rdi_xsdb -e set xsdb_idle_timeout 20 ; source /tools/Xilinx/Vivado/2019.1
4  1004  758063  757989  20   0 225288  1532 -      R+   pts/8      0:00 ps -alx
Indeed, netstat confirms that "hw_server" is what is listening on port 3121, for what it is worth.

openFPGAloader

It says that it supports an "xvc-client" as one of its cable types, so this is promising. The build instructions are a bit peculiar, here is the game:
git clone https://github.com/trabucayre/openFPGALoader.git
cd openFPGAloader
mkdir build
cd build
cmake ..
make -j4
make install
It builds clean, no errors!
It installs into /usr/local/bin, but also puts a bunch of stuff into /usr/local/share (so I had to make that writeable).
Then I try the following:
openFPGALoader -c xvc-client clocks_wrapper.bit

Nothing! No errors, the program does not return. The board shows no activity. Too bad. It will be yet another project to sort this out, but it looks interesting. It is all C++ code, which is certainly better than Tcl or even Python.

I grep for 2542 in the sources and verify that this is the port it is trying to use to talk to XVC. This is good. Then I kill Vivado, unplug and replug the pico, restart xvcd-pico and now I get:

openFPGALoader -v 2 -c xvc-client clocks_wrapper.bit
detected xvcServer version v1.0 packet size 1024
freq 0
0 0 0 0
found 2 devices
index 0:
	idcode   0x4ba00477
	type     ARM cortex A9
	irlength 4
index 1:
	idcode 0x3722093
	manufacturer xilinx
	family zynq
	model  xc7z010
	irlength 6
File type : raw
Open file FAIL
Why do I get a file open error? The ".bit" file is right there and readable. It turns out that there is some bug and it is not detecting or propogating the fact that it is a "bit" file, even though the file has a ".bit" extension. But explicitly giving the file type makes it work:
openFPGALoader -c xvc-client --file-type bit clocks_wrapper.bit
detected xvcServer version v1.0 packet size 1024
freq 0
0 0 0 0
Open file-- DONE
Parse file DONE
load program
Flash SRAM: [==================================================] 100.00%
Done
So now I have a way (and a tool) to download ".bit" files without having to use Vivado. And beyond that, I have source code for the whole path. This does talk to xvcd-pico, but that is actually a good thing (and I have source code for that too if I am curious).
Feedback? Questions? Drop me a line!

Tom's Computer Info / tom@mmto.org