Tips, Tricks and Observations
Feel free to suggest any common tips/tricks/observations you make whilst working with WebPACK or your FPGA project.
- You can't put more connections in a UCF then you actually reference in your design. This does mean you can't have one global/common UCF file for all your projects unless you comment out the connections that don't apply to a particular design.
- The FPGA on the Spartan 3E board can be configured a number of ways, the precise method being determined by settings of header J30 (ref UG p26). The default / as received method is for the FPGA to be configured from (i.e. programmed by) the 4Mbit Xilinix XCF04S serial Flash PROM in 'Master Serial mode' (all three jumpers for header J30 present). Note that the on-board XC2C64A CPLD *must* have the original program loaded for the FPGA to be configured in Master Serial mode, as the CPLD is used in a 'helper' role to (as the UG states, p125) "...help reduce the number of jumpers on the board and simplifies the interaction of all the possible FPGA configuration memory sources."
A copy of the contents of the CPLD is included here for restoration if necessary - xc2c64a_original.jed
- Programming the Platform PROM (Spartan-3E Start Kit)
See the procedure starting on page 32 of the user guide: ug230.pdf (available from Xilinx).
- Using WebPACK ISE
First, let me say that I have found WebPACK ISE (for Windows) to be extremely useful. When my design is "sane", ISE has created reliable bit files.
That said, when my design is not sane, i.e., while I'm troubleshooting it, ISE may do some impolite things. It can crash, but remain running and the crashed instance can interfere with a new instance. The only way to tell if that is happening is if you use the task manager to see if a process with image name of _pn.exe exists. If there are two of them, you must close the one you just opened and then kill the other one (there isn't a GUI presentation after it crashes). Sometimes, even after correcting bad code, odd things may happen because you may have already set the conditions for odd behavior with previous code compiles. Things happen that don't make sense. I've found that if I'm not at fault (insane code), sometimes Project -> Cleanup Project Files helps. Sometime, however restarting that application and making sure all instances of it are gone before invoking again. Rarely, but still notably, occasionally a PC hardware restart seems to fix it...
I realize how anecdotal that all sounds - because it is. Your milage may vary.
ISE is somewhat surprising (to me) in the way it assigns "error" or "warning" status to possibly problematic code. IMO, some things that are considered warnings ought to be errors. For example, you will receive a warning if a state machine contains states which can never be reached. If you are testing something, I suppose that's OK because your intention may be to not have these states active, but if you're compiling for actual use and not testing, it seems that something like this would get lost in the ocean of "normal" warnings one always gets, especially in a larger design.
ISE has compiled designs I've created that use more resources than are available in the device. I noticed this with a recent project that actually used more block RAMs and multipliers (combined) than the device had, yet there wasn't even a warning. So make sure you know how to count...
- Language Templates
If you are new to Verilog (or VHDL), you will probably not be familiar with the way the synthesis process infers the logic you describe. This can be frustrating because you will often not get error messages nor will the warnings necessarily mean much to you. IMO, It is worthwhile spending time looking at the design templates in WebPACK ISE. They can be accessed with the lightbulb icon in the toolbar or in the edit menu "Language Templates". Inside are found examples of common structures. These are divided into functional categories such as RAM & ROM, flipflops, multiplexors, etc. If you are trying to infer something, but synthesis is "missing" what you want, then a look at the language templates can tell you what is missing or malformed in your code. I use the language templates regularly. All it takes is something that looks rather innocent to prevent synthesis from inferring proper logic. For example, if you are trying to infer a single port block RAM, you can do a read and a write, but in only one state for each of those operations. Looking at the language template for a single port block RAM shows how this is done in a very simple example that describes only the RAM. You can copy and paste this structure as the basis for your RAM need if you like. Trying to read the RAM from 3 different states does not allow the use of a block RAM and ISE will try to use flipflops (LOTS of them) instead. The first time I saw the warning for this, I really didn't know what it was trying to tell me, but I could see that it wasn't doing what I wanted. To make that kind of thing (reading the RAM from 3 different states) work correctly, you need to follow the language template to make sure the RAM is properly inferred and then use other address substitution and storage or cache techniques to get the same result.