Eleven years ago, I did Verilog work and had a good time of it. Life happened and I didn't do any FPGA work since then. I have a project in which I'm getting back into FPGAs and have had a few tries getting some code to work. With a few failures, I've determined that warnings are errors with the modern synthesis engines. I have, since, started from scratch with something which should be pretty straight forward (a simple SPI engine). It is 100% state machine.
The precise question for where I stand right now is at the bottom. Here is the process I've been through:
I get 3 identical errors:
1. Bit 7 of register intState_FSM is stuck at zero (this is, of course, after the synthesizer converts my states to a one-hot design, in which the MSB [bit 7] becomes 1 in the last state).
2. Register intState_FSM_i1 is stuck at zero.
3. Register rdy_54 is stuck at zero.
Now, if it reported everything being stuck at zero, that would tell me I screwed up with my reset signalling. But, as you will see below, it's quite literally if(reset) {} else {bulk of code}
If bit 7 is "stuck at zero" that tells me that either something is wiring it to zero (which should generate blocking vs. non-blocking errors) or I never reach there. Problem is, the state before it does 1 thing and goes to the next state.
As for the ready signal always being zero, the only way I can see this happening is if the state machine never reaches the state which sets the ready flag to 1.
I noted that having a "default: ..." catch in the case statement seems to be a possible source of the problem, as it doesn't exist in the one-hot list. I removed it, and then I get down to two errors:
WARNING - d:/projects/spi_eng.v(100): Bit 0 of Register intState is stuck at Zero. VDB-5010
and later
2. WARNING - logical net 'GND_net' has no load.
My text books are pretty much useless for this. If I switch to the Synplify synthesis, I get completely different synthesis errors (default engine I'm using is Lattice Synthesis Engine). Does anyone have any suggestions? Any help is appreciated. Cheers!
module spi_engine(clk, rst, load, rdy, clr, ext_cs, ext_sdo, ext_sdi, ext_clk, inWord, outWord);
input clk, rst, load,clr;
output rdy;
output ext_cs, ext_sdo, ext_clk;
input ext_sdi;
input [23:0] inWord;
output [23:0] outWord;
reg [7:0] intState;
// 0h00 - powerup
// 0h00 - idle, waiting for load to be triggered.
// 0h02 - triggered system.
// 0h03 - setup chip select and the shifter
/// large valued registers
reg [23:0] wordStorage;
reg [23:0] outWord;
reg [7:0] bitCounter;
// Control Signals
reg rdy;
reg ext_sdo, ext_cs, ext_clk;
wire clr; // wire for the clear signal
always @(posedge clk)
if(1==rst)
begin
// do reset stuff here
intState<=8'h00;
rdy<=0; // not yet ready with a new word.
ext_sdo<=0;
ext_cs<=1;
ext_clk<=0;
bitCounter<=0;
end
else
case(intState) // state machine business
8'h00: begin
wordStorage<=0;
intState<=8'h01;
bitCounter<=0;
end
8'h01: // idle state. Wait for the load pin to be asserted.
if(1==load)
begin
// load pin is high, this is the start of a transaction.
wordStorage<=inWord; // copy the word appearing on the input pins.
intState<=8'h02; // next state.
end
// do nothing if we haven't hit the load assertion.
8'h02: // triggered state. Now we begin the whole business.
begin
// start by setting up chip-select.
ext_cs<=0;
bitCounter<=0; // clear the counter
intState<=8'h03; // jump to the next state
end
8'h03: begin // put the MSB onto the bus
ext_sdo<=wordStorage[23]; // make the serial-data-output bit equal to the MSB of the word-storage reg
intState<=8'h04;
end
8'h04: begin
ext_clk<=1;
intState<=8'h05;
outWord[0]<=ext_sdi;
end
8'h05: begin
ext_clk<=0;
wordStorage<=wordStorage<<1; // shift all the bits in wordStorage left 1.
outWord<=outWord<<1; // shift all the bits in OutWord left 1
intState<=8'h06;
end
8'h06: begin // determine how many bits are left to count...
if(23==bitCounter)
// we're good.
intState<=8'h07;
// still shifting.
bitCounter<=bitCounter+1;
intState<=8'h03;
end
8'h07: begin // do some cleanup.
ext_cs<=1; // indicate we're finished to the device.
intState<=8'h08;
end
8'h08: begin
rdy<=1; // indicate we're done with the transaction.
intState<=8'h0F;
end
8'h09: if(1==clr)
begin
rdy<=0;
intState<=8'h01;
end
endcase
endmodule