hbchf 发表于 2010-12-9 20:43:32

大家帮忙看看这段verilog代码,仿真结果怎么会这样呢?

module cd16
(
input start ,
input clk,
input rst,
input dat_i,

output reg e,
output reg rw,
output reg di,
output reg dat

);

parameter DIV_WORK_CLOCK = 6600;//产生10kHz信号控制lcd.e,设置为100kHz时复位不灵敏
parameter DIV_WORK_CLOCK_WIDTH = 16;


//wire p_clk ;
//reg clk_e_counter ;
reg state ;
reg instruction_state ;
reg instruction_next_state ;
reg instruction ;
reg instruction_set ;
reg instruction_length ;
reg instruction_index ;

wire action_struction ;
wire p_clk_e;//10kHz
reg clk_e_counter;


assign action_struction = instruction ;
assign p_clk_e = (clk_e_counter==0)?1'B1:1'B0;

always@(posedge clk,negedge rst,posedge instruction_set)
begin

if(rst == 0)
           begin
                   e<= 0 ;
                   rw <= 0 ;
                   di <= 0 ;
                   //instruction_set <= 0 ;
                   state <= 0 ;
           end
   else if(instruction_set == 1'B1)
       begin
           //instruction_set <= 0 ;
           instruction_index <= instruction_length - 1'B1 ;
           end
   else if(clk == 1'B1)
           begin
             case(state)
             4'd0 :
                 begin
                           e<= 0 ;
                           rw <= 0 ;
                           di <= 0 ;
                           if(instruction_length > 0)
                                   begin
                                   state <= 4'd1 ;
                                   end
                 end
             
                4'd1:
                begin
                di <= action_struction ;
                rw <= action_struction ;
                dat <= action_struction ;
                state <= 4'd2 ;
                end
                
                4'd2:
                begin
                e <= 0 ;
                if(p_clk_e == 1'b1)
                                begin
                                state <= 4'd3 ;
                                end
                end
                   
                4'd3:
                begin
                e <= 1'b1 ;
                if(p_clk_e == 1'b1)
                   begin
                   state <= 4'd4 ;
                   end
                end
                
                4'd4:
                begin
                e <= 0 ;
                if(p_clk_e == 1'b1)
                   begin
                   if(instruction_index == 1'B0)
                      begin
                      state <= 4'd5 ;
                      end
                      else
                      begin
                      instruction_index <= instruction_index - 1'b1 ;
                      state <= 4'd1 ;
                      end   
                   end
                end
                
             4'd5:
             begin
                 if(instruction_length == 0)
                 state <= 4'd0 ;
             end
             
              default: state <= 4'd0 ;
             
          endcase
      
           end
end

always@(posedge clk,negedge rst)
begin
   
   if(rst == 0)
   begin
   instruction_length <= 0 ;
   instruction_set <= 0 ;
   instruction_state <= 4'd1 ;
   end          
   else if(clk == 1'b1)
   begin
       case(instruction_state)
         4'd0:
         begin
         if(start == 1'b1)       instruction_state <= 4'd4;
         end
         
          4'd1:
          begin
          instruction <= 10'b0000110000 ;
          instruction <= 10'b0000001111 ;
          instruction <= 10'b0000000110 ;
          instruction <= 10'b0000000001 ;
          instruction_length <= 4 ;
          instruction_set <= 1'b1 ;
          instruction_next_state <= 4'd0;
          instruction_state <=4'd2 ;         
          end
         
          4'd2:
          begin
          instruction_set <= 1'B0 ;
          instruction_state <=4'd3 ;
          end
         
          4'd3:
          begin
          if(start == 1'b0)
          instruction_state <= instruction_next_state ;
          end
         
          4'd4:
          begin
          instruction <= {2'b10,dat_i} ;
          instruction_length <= 1 ;
          instruction_set <= 1'b1 ;
          instruction_next_state <= 4'd0 ;
          instruction_state <= 4'd2 ;
          end
         
          default:
            instruction_state <= 4'd0 ;
         
      endcase   
   end
   
end

always@(negedge clk, negedge rst)
        begin
              
                if (rst == 1'B0)
                        clk_e_counter <= 0;
                       
      else if(clk == 1'B0)
      begin
                if (clk_e_counter == DIV_WORK_CLOCK-1'B1)
                        clk_e_counter <= 0;
                else
                        clk_e_counter <= clk_e_counter+1'B1;
                end
        end
       
endmodule       
http://cache.amobbs.com/bbs_upload782111/files_35/ourdev_603602SWWZ07.png
(原文件名:shixu2.png)
仿真光标所指处,两个状态机分别执行到了state=4'd2,instruction_state=4'd2。但是奇怪instruction_index怎么会变成0的?

Fourier00 发表于 2010-12-9 23:38:29

看晕我了

seemrain 发表于 2010-12-10 09:01:31

看不晕的都是高人

hbchf 发表于 2010-12-14 22:01:29

原因找到了,上面的状态机写得有点乱!
导致我上回没有想明白的问题是第二个状态机少了个限制条件,从而导致整段代码完全不能按照我的要求来工作。
下面为1602驱动代码:
仿真产生信号ourdev_604689S2J3JX.txt(文件大小:334字节) (原文件名:clock.txt)
分频ourdev_604690JRX4WE.txt(文件大小:544字节) (原文件名:div_sim.txt)
计数模块ourdev_604691YL84QG.txt(文件大小:2K) (原文件名:counter.txt)
译码模块ourdev_604692ZSYNUR.txt(文件大小:1K) (原文件名:bcd_ascii.txt)
1602控制模块ourdev_604693C5WNIE.txt(文件大小:4K) (原文件名:cd16.txt)
http://cache.amobbs.com/bbs_upload782111/files_35/ourdev_604694DB2AYI.jpg
modelsim仿真时序 (原文件名:时序1.jpg)

以上代码下载板子上测试过的
总是看大家的帖子,今天我也贡献下!
页: [1]
查看完整版本: 大家帮忙看看这段verilog代码,仿真结果怎么会这样呢?