openXC7 / xc7k325t-blinky-nextpnr

BSD 3-Clause "New" or "Revised" License
42 stars 9 forks source link

Not all I/O are reachable from nextpnr in the xc7k325t #8

Open jrrk2 opened 2 years ago

jrrk2 commented 2 years ago

The toolchain fails when I/O sites outside IOB_X0Yxxx are selected. Inside this range the tool runs without error but only a limited number of I/Os are operational in the resulting bitstream. See PR #7

This is a rough description of the behaviour which needs refining.

unbtorsten commented 2 years ago

Could this be related to how prjxray-db is generated? If so, adjustment of symbiflow/prjxray#1794 such as symbiflow/prjxray#1844 may help resolve this.

unbtorsten commented 2 years ago

(transfer comment from PR)

Connectivity of switches on Genesys2, cf. https://digilent.com/reference/_media/reference/programmable-logic/genesys-2/genesys-2_sch.pdf and https://github.com/Digilent/digilent-xdc/blob/master/Genesys-2-Master.xdc sw0: bank 17 sw1: bank 16 sw2: bank 16 sw3: bank 17 sw4: bank 15 sw5: bank 15 sw6: bank 14 -- operational sw7: bank 14 -- operational

Note that all LEDs are connected to bank 14 as well. This supports your hypothesis stated in #7 , @jrrk2

From Xilinx' documentation https://www.xilinx.com/support/documentation/user_guides/ug475_7Series_Pkg_Pinout.pdf image

On the bright side, this would mean that the following I/O is currently available for bitstream configuration on the Genesys2:

jrrk2 commented 2 years ago

I can confirm the reset button can function as a convenient manual clock.

unbtorsten commented 2 years ago

Investigations in #9 support our current assumptions.

jrrk2 commented 2 years ago

The reset pin may be made bidirectional in order to self-oscillate. This happens at about 64MHz. Now the Genesys2 8-bit counter will self-count. see the ring-oscillator branch of the blinky project.

unbtorsten commented 2 years ago

reset pin may be made bidirectional [...]

Sounds great! How reliable and defined is the clock frequency with this approach? Either way, this is a definite leap for publicity and proving the point that an open-source Genesys2 design is possible! :+1:

Can you rebase your branch to the latest revision of makeit.sh, please?

jrrk2 commented 2 years ago

For details of the approach, see the paper that I previously attached:

https://caslab.csl.yale.edu/publications/burgiel2021characterization.pdf

In short, it’s not great, but for pedagogical purposes it can be used to show how not to do it.

Concerning rebasing, I see no changes of mine that need to be kept in makeit.sh

Regards, Jonathan

hansfbaier commented 2 years ago

I am just finished building a database for the 160T based on @unbtorsten's branch and I have the same issue. Instead of ./download-latest-db.sh, I used a checkout of @jrrk2 's database from https://github.com/jrrk2/prjxray-db. I can build a blinky, when the pins are in bank 14, but an assert failure like this otherwise:

[...]
3. Executing JSON backend.

End of script. Logfile hash: 84acb2d8cd, CPU: user 2.36s system 0.02s, MEM: 195.00 MB peak
Yosys 0.13+15 (git sha1 bc027b2ca, gcc 10.3.0-1ubuntu1~20.04 -fPIC -Os)
Time spent: 25% 26x read_verilog (0 sec), 16% 13x design (0 sec), ...
+ nextpnr-xilinx --chipdb /usr/local/share/nextpnr/xilinx-chipdb/xc7k160tffg676-2.bin --xdc blinky-kx2.xdc --json blinky.json --write blinky_routed.json --fasm blinky.fasm --verbose --debug
Info: Packing constants..
Info: Inserting IO buffers..
Info:     IO port 'clk' driven by IBUF '$iopadmap$blinky.clk'
Info:     IO port 'led' driven by OBUF '$iopadmap$blinky.led'
Info:     Constraining 'clk' to site 'IOB_X1Y124'
Info:     Constraining 'led' to site 'IOB_X1Y99'
Info: Generating input buffer for '$iopadmap$blinky.clk'
terminate called after throwing an instance of 'nextpnr_xilinx::assertion_failure'
  what():  Assertion failure: s != -1 (/home/user/HDL/nextpnr-xilinx/xilinx/arch.h:1602)
./makeit.sh: line 29: 409172 Aborted                 (core dumped) nextpnr-xilinx --chipdb ${CHIPDB_DIR}/${PART}.bin --xdc ${PROJECT_NAME}-${BOARD}.xdc --json ${PROJECT_NAME}.json --write ${PROJECT_NAME}_routed.json --fasm ${PROJECT_NAME}.fasm --verbose --debug

@jrrk2 : What did you use as a basis for your database? Was it ./download-latest-db.sh?

hansfbaier commented 2 years ago

I got blinky/picosoc designs working on banks 12, 13, 14, 15, 16. Not working: Banks 32, 33, 34, 115, 116 Which means, all banks on the left hand side work, the banks on the right hand side don't: image

hansfbaier commented 2 years ago

I suspect this is due to XRAY_IOI3_TILES, they look like this: image

because on the right hand side banks, the IO Tiles are of different type: image

So the left hand tiles have six sites and the right hand tiles have eight sites in them. Needless to say, the IOI3 fuzzers won't work for the right hand site tiles, because they are not IOI3

hansfbaier commented 2 years ago

The Artix7 on the other hand, has RIOI3 tiles on the right hand side: image So I suppose, we probably might have to write a new fuzzer for the RIOI tiles.

jrrk2 commented 2 years ago

This pretty much agrees with my diagnosis that the root cause is no support for the 1.8V I/O in the prjxray Makefile. Even when that is fixed, we still have to understand the behaviour and configuration bits for the 1.8V I/O (and in particular the LVDS crystal 200MHz input that Genesys2 relies on). This is essential to support the DDR memory interface standards also.

hansfbaier commented 2 years ago

@jrrk2 Can you point me to the exact location in the Makefile?

jrrk2 commented 2 years ago

diff --git a/fuzzers/000-init-db/Makefile b/fuzzers/000-init-db/Makefile index 033ed989..f31c290a 100644 --- a/fuzzers/000-init-db/Makefile +++ b/fuzzers/000-init-db/Makefile @@ -49,11 +49,14 @@ DB_SIMPLE=\ segbits_cmt_top_l_lower_b \ segbits_cmt_top_r_lower_b \ segbits_rioi3 \

-DB_SIMPLE += segbits_lioi3 segbits_liob33 +DB_SIMPLE += segbits_lioi3 segbits_liob18 segbits_liob33

BLOCK_RAM_EXTRA_FOR=\ mask_bram \

jrrk2 commented 2 years ago

I came across this module which should provide access to a clock on Genesys2 from a 3.3V I/O bank. It does not claim PMOD compatibility but with only 3 pins hopefully it will fit somehow:

TCXO

hansfbaier commented 2 years ago

@jrrk2 I patched nextpnr to print the BEL it is looking for before the failed assert, and I got: IOB_X1Y124/IOB33/PAD (that was for a 160T part)

hansfbaier commented 2 years ago

@jrrk2 Oh I wasn't aware you already started working on an iob18 branch. I will try to pull those changes into the kintex-chatter fork.

hansfbaier commented 2 years ago

@jrrk2 In your iob18 branch, shouldn't the IOSTANDARDS also include LVCMOS18? image

jrrk2 commented 2 years ago

What I have is just a mess that doesn’t do anything useful. It’s just a playpen to investigate how many different pieces of code need to be changed. Moreover, we need to reintegrate it all back into the existing iob fuzzer.

jrrk2 commented 2 years ago

This is the previous mentioned external oscillator (10MHz) attached to the JB PMOD of the Genesys2. Documentation is a bit scanty but I am confident the signal will appear either on JB1_P or JB3_P which is connected to pin V29 or T25 (conveniently both in Bank 14).

Somebody with better eyesight than me could have soldered it themselves but it only cost £10 including postage from China, see above.

IMG_2664

jrrk2 commented 2 years ago

External temperature compensated crystal oscillator module is working on Genesys2. Branch main has been updated with the changes. Blinking is fairly slow at 5/8 Hz or so. This can be speeded up by the use of a PLL as required (if that works yet). I did not go through the pull request process since I was confident my changes were small, so feel free to blame me if it breaks your board support.

hansfbaier commented 2 years ago

@jrrk2 We have now working preliminary support for the high speed IO banks. See https://twitter.com/1gkojima/status/1506925318875267072 Since the fuzzers support LVDS it now might be possible to get the clock working on the genesys2 board. Using these repos: https://github.com/kazkojima/nextpnr-xilinx And: https://github.com/kintex-chatter/db-workspace-for-kintex7

jrrk2 commented 2 years ago

Excellent progress. I need to refresh my memory a bit, should I be using branch iob18-trial in the kazkojima nextpnr repo ?

hansfbaier commented 2 years ago

@jrrk2 Yes that should be the branch. I am not shure yet, if nextpnr supports the LVDS IO standard. If not, let me know, I will try to add it.

kazkojima commented 2 years ago

I guess that LVDS IOSTANDARD won't work yet for the several missing keys in the segment DBs.

More importantly, it's very likely that the modified nextpnr can't set the correct bits in the bitstream, even if the missing keys are resolved. When there is an external chip connected to the IOB18 pins, that chip or FPGA could be damaged with the wrong voltage or some collision, in the worst case. I think we should test them with unconnected pins first. Unfortunately, the high-speed IO pins on the QMTECH xc7k325t board are inaccessible except for the pins connected to DDR3 and the two onboard switches. Maybe I should remove those two switches and their pull-up resistors for that purpose.

hansfbaier commented 2 years ago

@kazkojima I think for the clock input it should not be a problem and the danger of damaging something is fairly minimal. Yes but if the bits are wrong, who knows...

JakeMercer commented 2 years ago

Hi, I was trying to get a different xc7k325 board up and running and came across this issue as I have a differential clock is attached at IOB_X1; is there a solution for this issue? If someone could tell me what needs done, I'd be happy to have a go at fixing it.

jrrk2 commented 2 years ago

I think this is the latest progress:

https://github.com/kazkojima/nextpnr-xilinx/tree/iob18-trial

I haven't personally been able to work on it due to hardware unreliability that was only recently fixed.

hansfbaier commented 2 years ago

@JakeMercer I am working continuously on this, and here is my branch: https://github.com/kintex-chatter/nextpnr-xilinx/commits/iob18-trial I just rebased it on latest upstream. You also can get the database from: https://github.com/kintex-chatter/db-workspace-for-kintex7

hansfbaier commented 2 years ago

The IO bank database bits should be in pretty good shape at this point: https://twitter.com/hansfbaier/status/1536176892167892992 I didn't test it more than that above yet. Now it would be worth testing if the differential clock input works.

hansfbaier commented 2 years ago

@jrrk2 @unbtorsten It's been quite a while, but today I got the differential clock input working on my Kintex 325T board: https://twitter.com/hansfbaier/status/1541642932070952961 I pushed the changes to this repo. I also updated the make setup commands to pull in the latest database and nextpnr-xilinx. With the high speed banks I have tested single ended input and output and differential input.

JakeMercer commented 2 years ago

@hansfbaier Great work! I've got your differential blinky example running on my board. Apologies for taking so long to get back to you; I've been flat out with work but found some time to get back to this, this evening. Is there anything I can check with my board that you aren't able to that would help progress things? https://digilent.com/reference/_media/netfpga-1g-cml:netfpga-1g-cml_rm.pdf is the reference manual; I'm aiming to get the Ethernet's up and running but I'm not sure what the state of DDR I/O is at the moment? Also is bidirectional I/O special in any way as far as the IOBs are concerned or does it work the same as single-ended I/O?

hansfbaier commented 2 years ago

@JakeMercer Yes DDR3 is the next frontier. I already can build a DDR3 design but it does not work yet. We will have to test the individual primitives to see where the problems are.

hansfbaier commented 2 years ago

@JakeMercer I haven't tested bidirectional IO yet and it would be great if you could whip up a simple test case for that, including single ended and differential bidirectional IO.

hansfbaier commented 2 years ago

@JakeMercer I just pushed my latest version of the database, to ensure we are testing the same thing.

hansfbaier commented 2 years ago

@JakeMercer I also just pushed all my interim changes to nextpnr-xilinx. Please pull again from the iob18-trial branch.

JakeMercer commented 2 years ago

@hansfbaier I've pulled in your latest changes and rebuilt after a make clobber. I'm using the following to test bidirectional IO with a physical jumper wire between gpio0 and gpio1:

`default_nettype none   //do not allow undeclared wires

module bidir (
    input  wire clk_p,
    input  wire clk_n,
    output wire led,
    inout wire gpio0,
    inout wire gpio1,
    );

    wire clk_ibufg;
    wire clk;
    wire gpio_in;
    wire gpio_out;

    IBUFDS ibuf_inst        (.I(clk_p), .IB(clk_n), .O(clk_ibufg));
    BUFG   bufg_inst        (.I(clk_ibufg), .O(clk));
    IOBUF  iobuf_in_inst    (.I(gpio_in), .O(), .IO(gpio0), .T(1'b1));
    IOBUF  iobuf_out_inst   (.I(), .O(gpio_out), .IO(gpio1), .T(1'b0));

    reg [28:0] r_count = 0;

    always @(posedge(clk)) r_count <= r_count + 1;

    assign gpio_out = r_count[28];
    assign led = gpio_in;

endmodule

Which does not appear to work. I have isolated both the input and output side by reverting each back to input/output instead of inout and tweaking things to not use the IOBUF instantiations and things operate as expected in the fully reverted case but not when either side uses bidirectional IO.

I have had gpio0 as a normal input and the state is reflected in the LED and I have had gpio1 as a normal output and it changes with r_count. Having gpio0 as bidirectional and configured as input the LED stays off regardless of what is connected to the pin. Having gpio1 as bidirectional and configured as an output it remains at a logic 1.

It's entirely possible that I've made a rookie mistake, so apologies if that is the case.

hansfbaier commented 2 years ago

Hi @JakeMercer You swapped I and O in IOBUF image So 'I' of the IOBUF goes to the output, actually.

hansfbaier commented 2 years ago

@JakeMercer I have now the following set up which seams to work (the key changes the IO direction):

module blinky (
    input  wire clk_p,
    input  wire clk_n,
    output wire led,
    inout wire gpio0,
    inout wire gpio1,
    input wire key,
    output wire key_led
    );

    wire clk_ibufg;
    wire clk;
    wire gpio_in1;
    wire gpio_in2;
    wire gpio_out;

    IBUFDS ibuf_inst        (.I(clk_p), .IB(clk_n), .O(clk_ibufg));
    BUFG   bufg_inst        (.I(clk_ibufg), .O(clk));
    IOBUF  iobuf_in_inst    (.I(gpio_out), .O(gpio_in1), .IO(gpio0), .T(key));
    IOBUF  iobuf_out_inst   (.I(~gpio_out), .O(gpio_in2), .IO(gpio1), .T(~key));

    reg [28:0] r_count = 0;

    always @(posedge(clk)) r_count <= r_count + 1;

    assign gpio_out = r_count[25];
    assign led = gpio_in1 | gpio_in2;
    assign key_led = key;

endmodule
JakeMercer commented 2 years ago

Ah, I knew it would end up being something silly. I've tested that on my side now and looks good!

I've tweaked the above to use 2 extra pins and IOBUFDS and I'm now hitting:

ERROR: No Bel named 'IOB_X0Y125/IOB33M/OUTBUF' located for this chip (processing BEL attribute on 'iobuf_out_inst$subcell$OBUFTDS$subcell$P')
0 warnings, 1 error
JakeMercer commented 2 years ago

This is my .xdc file:

set_property LOC AA2 [get_ports clk_n]
set_property IOSTANDARD LVDS [get_ports clk_n]

set_property LOC AA3 [get_ports clk_p]
set_property IOSTANDARD LVDS [get_ports clk_p]

set_property LOC E17 [get_ports led]
set_property IOSTANDARD LVCMOS33 [get_ports led]

set_property LOC AF14 [get_ports key_led]
set_property IOSTANDARD LVCMOS18 [get_ports key_led]

set_property LOC W6 [get_ports key]
set_property IOSTANDARD LVCMOS15 [get_ports key]

set_property LOC D19 [get_ports gpio0]
set_property IOSTANDARD LVCMOS33 [get_ports gpio0]

set_property LOC E23 [get_ports gpio1]
set_property IOSTANDARD LVCMOS33 [get_ports gpio1]

set_property LOC D25 [get_ports gpio2]
set_property IOSTANDARD LVCMOS33 [get_ports gpio2]

set_property LOC F23 [get_ports gpio3]
set_property IOSTANDARD LVCMOS33 [get_ports gpio3]
hansfbaier commented 2 years ago

Ah, I knew it would end up being something silly. I've tested that on my side now and looks good!

I've tweaked the above to use 2 extra pins and IOBUFDS and I'm now hitting:

ERROR: No Bel named 'IOB_X0Y125/IOB33M/OUTBUF' located for this chip (processing BEL attribute on 'iobuf_out_inst$subcell$OBUFTDS$subcell$P')
0 warnings, 1 error

Can you give me the source and .xdc file for that?

JakeMercer commented 2 years ago

Apologies for the delay; the constraints file is as above and this is the Verilog:

module bidir (
    input  wire clk_p,
    input  wire clk_n,
    output wire led,
    inout wire gpio0,
    inout wire gpio1,
    inout wire gpio2,
    inout wire gpio3,
    input wire key,
    output wire key_led
    );

    wire clk_ibufg;
    wire clk;
    wire gpio_in1;
    wire gpio_in2;
    wire gpio_out;

    IBUFDS ibuf_inst        (.I(clk_p), .IB(clk_n), .O(clk_ibufg));
    BUFG   bufg_inst        (.I(clk_ibufg), .O(clk));
    IOBUFDS  iobuf_in_inst    (.I(gpio_out), .O(gpio_in1), .IO(gpio0), .IOB(gpio2), .T(key));
    IOBUFDS  iobuf_out_inst   (.I(~gpio_out), .O(gpio_in2), .IO(gpio1), .IOB(gpio3), .T(~key));

    reg [28:0] r_count = 0;

    always @(posedge(clk)) r_count <= r_count + 1;

    assign gpio_out = r_count[25];
    assign led = gpio_in1 | gpio_in2;
    assign key_led = key;

endmodule