data/full_repos/permissive/427221126/src/booth.v
data/verilator_xmls/55677448-28c5-43d6-bfd3-bf4576d0c6f4.xml
module booth_fsm
# (parameter DATAWIDTH = 8)
(
  input                        clk,
  input                        rstn,
  input                        en,
  input        [DATAWIDTH-1:0] multiplier,                            
  input        [DATAWIDTH-1:0] multiplicand,
  output reg                   done,
  output reg [2*DATAWIDTH-1:0] product
);


parameter   IDLE   = 2'b00,
            ADD    = 2'b01,
            SHIFT  = 2'b11,
            OUTPUT = 2'b10;

reg  [1:0]              current_state, next_state;
reg  [2*DATAWIDTH+1:0]  a_reg,s_reg,p_reg,sum_reg;
reg  [DATAWIDTH-1:0]    iter_cnt;
wire [DATAWIDTH:0]      multiplier_neg;


always @(posedge clk or negedge rstn)
  if (!rstn) current_state = IDLE;
  else current_state <= next_state;


always @(*) begin
  next_state = 2'bx;
  case (current_state)
    IDLE  : if (en) next_state = ADD;
            else    next_state = IDLE;
    ADD   : next_state = SHIFT;
    SHIFT : if (iter_cnt==DATAWIDTH) next_state = OUTPUT;
            else            next_state = ADD;
    OUTPUT: next_state = IDLE;
  endcase
end


assign multiplier_neg = -{multiplier[DATAWIDTH-1],multiplier}; 

always @(posedge clk or negedge rstn) begin
  if (!rstn) begin
    {a_reg,s_reg,p_reg,iter_cnt,done,sum_reg,product} <= 0;
  end else begin
  case (current_state)
    IDLE :  begin
      a_reg    <= {multiplier[DATAWIDTH-1],multiplier,{(DATAWIDTH+1){1'b0}}};
      s_reg    <= {multiplier_neg,{(DATAWIDTH+1){1'b0}}};
      p_reg    <= {{(DATAWIDTH+1){1'b0}},multiplicand,1'b0};
      iter_cnt <= 0;
      done     <= 1'b0;
    end
    ADD  :  begin
      case (p_reg[1:0])
        2'b01       : sum_reg <= p_reg+a_reg;
        2'b10       : sum_reg <= p_reg+s_reg;
        2'b00,2'b11 : sum_reg <= p_reg;
      endcase
      iter_cnt <= iter_cnt + 1;
    end
    SHIFT :  begin
      p_reg <= {sum_reg[2*DATAWIDTH+1],sum_reg[2*DATAWIDTH+1:1]};
    end
    OUTPUT : begin
      product <= p_reg[2*DATAWIDTH:1];
      done <= 1'b1;
    end
  endcase
 end
end


    
endmodule
module booth_fsm
# (parameter DATAWIDTH = 8)
(
  input                        clk,
  input                        rstn,
  input                        en,
  input        [DATAWIDTH-1:0] multiplier,                            
  input        [DATAWIDTH-1:0] multiplicand,
  output reg                   done,
  output reg [2*DATAWIDTH-1:0] product
);



parameter   IDLE   = 2'b00,
            ADD    = 2'b01,
            SHIFT  = 2'b11,
            OUTPUT = 2'b10;

reg  [1:0]              current_state, next_state;
reg  [2*DATAWIDTH+1:0]  a_reg,s_reg,p_reg,sum_reg;
reg  [DATAWIDTH-1:0]    iter_cnt;
wire [DATAWIDTH:0]      multiplier_neg;


always @(posedge clk or negedge rstn)
  if (!rstn) current_state = IDLE;
  else current_state <= next_state;


always @(*) begin
  next_state = 2'bx;
  case (current_state)
    IDLE  : if (en) next_state = ADD;
            else    next_state = IDLE;
    ADD   : next_state = SHIFT;
    SHIFT : if (iter_cnt==DATAWIDTH) next_state = OUTPUT;
            else            next_state = ADD;
    OUTPUT: next_state = IDLE;
  endcase
end


assign multiplier_neg = -{multiplier[DATAWIDTH-1],multiplier}; 

always @(posedge clk or negedge rstn) begin
  if (!rstn) begin
    {a_reg,s_reg,p_reg,iter_cnt,done,sum_reg,product} <= 0;
  end else begin
  case (current_state)
    IDLE :  begin
      a_reg    <= {multiplier[DATAWIDTH-1],multiplier,{(DATAWIDTH+1){1'b0}}};
      s_reg    <= {multiplier_neg,{(DATAWIDTH+1){1'b0}}};
      p_reg    <= {{(DATAWIDTH+1){1'b0}},multiplicand,1'b0};
      iter_cnt <= 0;
      done     <= 1'b0;
    end
    ADD  :  begin
      case (p_reg[1:0])
        2'b01       : sum_reg <= p_reg+a_reg;
        2'b10       : sum_reg <= p_reg+s_reg;
        2'b00,2'b11 : sum_reg <= p_reg;
      endcase
      iter_cnt <= iter_cnt + 1;
    end
    SHIFT :  begin
      p_reg <= {sum_reg[2*DATAWIDTH+1],sum_reg[2*DATAWIDTH+1:1]};
    end
    OUTPUT : begin
      product <= p_reg[2*DATAWIDTH:1];
      done <= 1'b1;
    end
  endcase
 end
end


    
endmodule