Continue to Site

Welcome to EDAboard.com

Welcome to our site! EDAboard.com is an international Electronics Discussion Forum focused on EDA software, circuits, schematics, books, theory, papers, asic, pld, 8051, DSP, Network, RF, Analog Design, PCB, Service Manuals... and a whole lot more! To participate you need to register. Registration is free. Click here to register now.

FSM in verilog problem ... any help please

Status
Not open for further replies.

sammm

Newbie level 5
Joined
Jan 8, 2005
Messages
9
Helped
0
Reputation
0
Reaction score
0
Trophy points
1,281
Activity points
94
verilog st0

Hi,

I am new for the area of HDL programing, what I am trying to do is to create a finite state machine that only have three stages :
ST0 : initial state
ST1 : stay in this stage for 32 times
ST3 : finish then return to ST0

I know that its very simple but for some reason, I can't do it right, here is the code that I wrote :

Code:
module fsm (count, clk, reset, ready);

output [4:0] count;
output ready;
input  clk;
input  reset;

reg ready;
reg [4:0] count;

parameter ST0=0, ST1=1, ST2=2;
reg [1:0] CurrentState, NextState;

always @(CurrentState)
begin 
	case(CurrentState)
		ST0: begin
			count= 0;
			ready= 0;
			NextState= ST1;
			end
		ST1: begin
			if(count < 32)
				begin
				count = count + 1;
				NextState = ST1;
				end
		else
				NextState = ST2;
			end	
		ST2: begin
			ready = 1;
			NextState = ST0;
			end	
		default:begin
			ready = 0;
			NextState = ST0;
			end		
	endcase
end

always @(posedge clk or posedge reset)
begin 
	if(reset)
		CurrentState= ST0;
	else
		CurrentState=NextState;
end

endmodule

What I want to do after getting this simple model work is to add some extra code to the state ST1, I don't want to implement a counter, so if there is any other style to do it please advice...

Thank you
 

cpld xtea

Your counter will never = 32 because it only holds 5 bits.

Also, you have feedback (count = count + 1) in an unclocked block.
 

xtea in verilog

Ok ... then I had to do the following:
1- increase the count # of bits
2- move the count = count +1 statement to the clock section

but what is the correct way to do step 2, I tried to just move it to the clocked section, but I am getting alot of errors...

I will appreciate if anybody could guide me on the proper why of doing it, maybe by a document or an example...

Thanks for your help tkbits
 

I may have been overly strict. I don't know Verilog that well.

You may be able to move the count assignment back, as the code block is not sensitive to changes in count. If that works, I stand corrected.
 

Have a look at this.. might help you

Code:
module fsm (count, clk, reset, ready);

output [5:0] count;
output ready;
input  clk;
input  reset;

reg ready;
reg [5:0] count;

parameter ST0=0, ST1=1, ST2=2;
reg [1:0] CurrentState, NextState;

always @(CurrentState, count)
begin
   case(CurrentState)
      ST0: begin
         ready= 0;
         NextState= ST1;
         end
      ST1: begin
         if(count < 6'd31)
            begin
            NextState = ST1;
            end
         else
            NextState = ST2;
         end
      ST2: begin
         ready = 1;
         NextState = ST0;
         end
      default:begin
         ready = 0;
         NextState = ST0;
         end
   endcase
end

always @(posedge clk or posedge reset)
begin
   if(reset)
      CurrentState <= ST0;
   else
      CurrentState<= NextState;
end

always @(posedge clk)
begin
    if(CurrentState == ST0)
       count <= 0;
    else if(CurrentState == ST1)
       count       <= count + 1'b1;
end

endmodule
 

    sammm

    Points: 2
    Helpful Answer Positive Rating
Thanks .... it worked just fine
I think that I had alot of readings to done on this area ...
Thank you very much

Added after 59 minutes:

Ok... I hope that you can give me a hint on the following also
I modified the design to implemeny xtea encryption algorithm based on 32 rounds,

the xtea code in c is very small
Code:
usigned long DELTA= 0x9E3779B9;
//  plain text is 64 bit, y holds the fisrt 32 bit of it , z holds the second 32 bits 
for ( int i=0; i<32; i++)
   {
	y+= (z<<4 ^ z>>5) + z ^ sum + k[sum&3];
	sum+= DELTA;
	z+= (y<<4 ^ y>>5) + y ^ sum + k[sum>>11 & 3];
   }

Code:
module fsm (plain, key, count, clk, reset, ready, cipher); 

output [63:0] cipher;
output [5:0] count; 
output ready; 
input  clk; 
input  reset; 
input [63:0] plain;
input  [127:0] key;

reg [63:0] cipher;
reg [31:0] y;
reg [31:0] z;
reg [31:0] sum;
reg ready; 
reg [5:0] count; 
reg [31:0] DELTA;
parameter ST0=0, ST1=1, ST2=2; 
reg [1:0] CurrentState, NextState; 

always @(CurrentState, count, plain, y, z, sum, key) 
begin 
   case(CurrentState) 
      ST0: begin 
         ready= 0;
		 y = plain[31:0];
		 z = plain[63:32];	
		 DELTA = 32'h9E3779B9;
		 sum = 0;
         NextState= ST1; 
         end 
      ST1: begin 
         if(count < 6'd31) 
            begin
			y = y + (z<<4 ^ z>>5) + z^sum + key[sum&3];
			sum = sum + DELTA;
			z = z + (y<<4 ^ y>>5) + y^sum + key[sum>>11 & 3]; 
            NextState = ST1; 
            end 
         else 
            NextState = ST2; 
         end 
      ST2: begin 
         ready = 1;
		 cipher[31:0] = y;
		 cipher[63:32]= z; 
         NextState = ST0; 
         end 
      default:begin 
         ready = 0; 
         NextState = ST0; 
         end 
   endcase 
end 

always @(posedge clk or posedge reset) 
begin 
   if(reset) 
      CurrentState <= ST0; 
   else 
      CurrentState<= NextState; 
end 

always @(posedge clk) 
begin 
    if(CurrentState == ST0)
        count <= 0;
    else if(CurrentState == ST1) 
       count       <= count + 1'b1;	
end 
endmodule

I am not expecting you to correct my code, I only want comments so I can learn the correct coding style ... I know that there is something wrong with the event list of the first "always" , but I don't know how to correct it.

Added after 3 hours 41 minutes:

Another thing I want to check with you guys , is it possibel to write this in verilog
Code:
 y = y + (z<<4 ^ z>>5) + z^sum + key[sum&3]; 
 sum = sum + DELTA; 
 z = z + (y<<4 ^ y>>5) + y^sum + key[sum>>11 & 3];

I mean when I compile it, I didn't get any error, but is it logically true ?
 

z<<4 I think it works fine with simulation, but may not be synthesisable.

With the other code, I suggest you to shift all your calculation (x, y, z, etc) to sequential block.
 

Hi sammm,
I think you should understand the basic rule of HDL logic design before coding, otherwise you will waste mcuh time on unsyntheisable code.
Your essential error is not make clear sequential and combinational logic block.
The "always @(CurrentState ... " should be a conbinational block. But your code have following line:
y = y + (z<<4 ^ z>>5) + z^sum + key[sum&3];
sum = sum + DELTA;
z = z + (y<<4 ^ y>>5) + y^sum + key[sum>>11 & 3];

You may want update y, z and sum the this state, but you can't put them here.
the y, z and sum should be registers, which update these value at clock edges. Right code should look like:

always @(CurrentState
begin
...; sum_in = sum + DELTA; ...;
end

always @(posedge clk or posedge reset)
begin
if(reset)
sum= INITIAL_VALUE;
else
sum=sum_in;
end

Another error: signals in always list should be seperated by 'or', not ','. It is a stupid thing of older version verilog. Use 'always @*' if your compiler support it.

Here is a paper on fundamental FSM coding.
 

    sammm

    Points: 2
    Helpful Answer Positive Rating
it_boy said:
z<<4 I think it works fine with simulation, but may not be synthesisable.

It's OK. Just append 4 zeros.
 

Thanks for the document vale.
I understand now that there is alot of errors in my code, I will rewrite it again, thanks for your help, and I am thinking to use continuos assignments for the functions, and to use them with proper fsm design.
 

Status
Not open for further replies.

Part and Inventory Search

Welcome to EDABoard.com

Sponsor

Back
Top