<napaalm>
The yosys synthesis is wrong, because STAR is no longer a register and its value doesn't change on clock positive edges. Can anyone give me some info on why this happens? Thank you!
<ZipCPU>
napaalm: Yes, your last pastebin will work.
<ZipCPU>
The code you wrote initially is only legal in a simulation context. Verilog was initially written as a simulation language, and so it can work in simulations.
<ZipCPU>
However, you can't map it to hardware.
<ZipCPU>
When it comes to mapping a design to hardware, you have to limit yourself to only the constructs that the hardware supports, and assigning the same register in two separate always blocks is ... well, that doesn't describe any hardware.
<ZipCPU>
It only has meaning in a simulation.
kraiskil has joined #yosys
<ZipCPU>
If that's the kind of logic taught you in your school, then either 1) you are taking a class in how to write Verilog simulations (check your syllabus), 2) you missed a key piece of context in the lesson, or 3) you instructor has been delinquent about telling you the difference.
kraiskil has quit [Ping timeout: 245 seconds]
<napaalm>
Thank you ZipCPU, now it all makes sense! During the class we never touch actual hardware, instead we write simulations with iverilog
<ZipCPU>
napaalm: You aren't the first person with this type of question.
<ZipCPU>
Indeed, its a common beginners mistake. I see this sort of thing all the time.
<napaalm>
I can imagine that
<ZipCPU>
It's also why I limited my tutorial to *only* those parts of Verilog that could be synthesized.
<napaalm>
Speaking of code that can't be synthesized, now I am trying to synthesize tri-state logic, but I can't get yosys to convert it to a form that can be synthesized to an fpga. I don't understand the exact purpose of the "tribuf" command, and it doesn't seem to make a difference in my code
<ZipCPU>
Heh. Yeah, that's another one.
<ZipCPU>
The trick is there's only a couple ways to do it, and a lot of ways to mess it up.
<ZipCPU>
Properly, you might write: assign out = (tristate) ? 1'bz : value;
<ZipCPU>
But beware, you can *only* do that to output of the chip at the top level.
<ZipCPU>
The other way to do it is to instantiate the FPGAs tri-state IO buffer.
<ZipCPU>
Which buffer you instantiate, however, depends upon the FPGA you are using.
<napaalm>
Okay, so this applies only to top-level outputs, and what about internal logic?
<ZipCPU>
Internal tristate logic is only supported by some daring synthesis tools.
<napaalm>
My FPGA is a Lattice ECP5
<ZipCPU>
It's not universally supported.
<ZipCPU>
See, the thing is, there's _NO_SUCH_THING_ as internal tristates on an FPGA. The hardware doesn't allow it.
<ZipCPU>
Some synthesis tools will attempt to approximate it via logic, but the hardware for it doesn't exist.
<ZipCPU>
(I don't mean to yell, but if I were an instructor I would've given a proverbial foot stomp at that, and ... I'm not sure how to write that in IRC text ...)
<napaalm>
Okay, I had found online this limitation of FPGAs, so the question is: can yosys do this kind of approximation?
<ZipCPU>
I haven't tried it. I think some of the developers have said it could, but it wouldn't be a widely used or tested feature so ... your mileage might vary.
<ZipCPU>
In my case, I'm always writing to the lowest common denominator, so if there's one synthesizer my customers might use that doesn't support a feature, I'm stuck without it.
<ZipCPU>
Sometimes I think they bought commercial tool XYZ back in the early 2000's, and they couldn't afford to update the licenses ... so, the market I work with leaves me stuck w/o a lot of language features others really like.
<napaalm>
I see, it doesn't seem like an easy field to work in
<ZipCPU>
It's not all that bad. You just have to learn the few constructs that are universally supported.
<lofty>
napaalm: pretty much whenever you use tristate logic then Yosys will issue a warning about limited support for it.
<lofty>
But, really, there's no real need for tristate logic internally?
<ZipCPU>
I agree with lofty. There's no reason to use it internally.
<napaalm>
Yeah, I am trying to synthesize an educational CPU we studied in class, which has an internal bus to connect to memory and IO space
<napaalm>
I would like to avoid manually reimplement that code without tri-state logic, that's all
<lofty>
I assume your mental model was tristate buffers to control read/write to a common set of wires
<ZipCPU>
Technically, ASICs can support internal tristates. That doesn't mean they're good ideas to use. However, there was a past generation that used them more liberally.
<napaalm>
lofty: Yes, it's a common bus for all devices
<lofty>
Even if tristate buffers were supported in internal fabric, they were *very* slow
<ZipCPU>
To use a tristate bus in an FPGA, you have to keep a copy of the bus for each potential source, together with the tristate enable for each source, and then you use a LUT (or two or three) per bit to determine the bus value.
<ZipCPU>
It's often easier for a two-way bus to simply keep track of both directions independently, rather than those plus the logic necessary to merge them.
<lofty>
napaalm: instead what tends to happen is the CPU has separate read/write buses; all devices read from the CPU's write bus, and their write output is multiplexed based on a device's validity signal
<lofty>
ZipCPU: Well, all ASICs use internal tristates due to the nature of a transistor, but that's being pedantic
<napaalm>
Okay, it makes sense. I thought that yosys could autonomously do this kind of transformation
<ZipCPU>
I was trying to describe how you'd build an internal tristate within an FPGA, but ... okay.
<lofty>
That's pretty much for I/O buffer inference
<napaalm>
And what about the option "-logic"?
<ZipCPU>
Not sure. Try it.
<lofty>
"convert tri-state buffers that do not drive output ports to non-tristate logic."
<lofty>
AKA, infer an input buffer rather than a tristate buffer if possible
<napaalm>
I did try (and it's already included in the synth_ecp5 command), but doesn't help in my case: at the end of the synthesis I get many warning about multiply driven ports
<ZipCPU>
Warning, schmorning. If it's not an error, it did something
<ZipCPU>
Unlike software, warnings are quite plentify in hardware design
<ZipCPU>
Few tools will let you synthesize without generating them
<lofty>
Yeah, uh, I would treat a multiple-driver warning seriously, unlike ZipCPU
<napaalm>
Yeah, if I then proceed to place and route I get an actual error
<napaalm>
ERROR: Net 'C.d7_d0[0]' is multiply driven by cell ports C.P.D7_D0_TRELLIS_FF_Q_7.Q and C.SdIO.Switch.RBR_TRELLIS_FF_Q.Q
<lofty>
Because in the best possible case that's unimplementable
<ZipCPU>
lofty: ;) Normally I'd treat it seriously too.
<lofty>
And in the worst case you have a bitstream that will produce magic smoke
<lofty>
This is...less common these days though, because FPGAs don't have tristate buffers in them
<ZipCPU>
Do we need to explain to napaalm how these FPGAs run on smoke?
<ZipCPU>
This stuff needs its smoke to run. If you ever let the smoke out, it stops working.
<napaalm>
Hahahah
<napaalm>
So, it seems I don't have much choice but to implement two separate buses
<lofty>
Correct
<napaalm>
Thank you very much for your help ZipCPU and lofty !
<ZipCPU>
;)
<ZipCPU>
Good luck.
<napaalm>
Thanks
* ZipCPU
goes back to working on his 10Gb Ethernet, trying to configure those GTX transceivers just right ...
<lofty>
napaalm: no worries
* ZipCPU
can't find a valid way to use Xilinx's 66B/64B gearboxes, grumbles and goes on to write his own ...
<whitequark>
ZipCPU: there are some old FPGAs that do have internal tristates
<whitequark>
I'm not sure whether they exposed those, but architecturally some old Xilinx devices did have them
<ZipCPU>
Seriously? Wow. I have just learned something. Do you remember which ones?
<whitequark>
mwk would know for sure, but I think it was... xc2s, maybe?
<whitequark>
I believe internal tristates were used to save die area on interconnect
<whitequark>
and they stopped using those because doing timing driven routing where you have to consider that your capacitance changes depending on the pass transistors you enable isn't tractable