Saturday, 12 April 2014

chapter 12



Computer Arithmetic
and
Verilog HDL Fundamentals

Chapter 12

Floating-Point Addition

Verilog Code Figures


































Page 565, Figure 12.9

//behavioral floating-point addition
module add_flp3 (flp_a, flp_b, sign, exponent, sum);

input [31:0] flp_a, flp_b;
output [22:0] sum;
output sign;
output [7:0] exponent;

//variables used in an always block
//are declared as registers
reg sign_a, sign_b;
reg [7:0] exp_a, exp_b;
reg [7:0] exp_a_bias, exp_b_bias;
reg [22:0] fract_a, fract_b;
reg [7:0] ctr_align;
reg [22:0] sum;
reg sign;
reg [7:0] exponent;
reg cout;

always @ (flp_a or flp_b)
begin
      sign_a = flp_a [31];
      sign_b = flp_b [31];

      fract_a = flp_a [22:0];
      fract_b = flp_b [22:0];

//bias exponents
      exp_a_bias = exp_a + 8'b0111_1111;
      exp_b_bias = exp_b + 8'b0111_1111;

//align fractions
      if (exp_a_bias < exp_b_bias)
         ctr_align = exp_b_bias - exp_a_bias;

         while (ctr_align)
            begin
               fract_a = fract_a >> 1;
               exp_a_bias = exp_a_bias + 1;
               ctr_align = ctr_align - 1;
            end

      if (exp_b_bias < exp_a_bias)
         ctr_align = exp_a_bias - exp_b_bias;

         while (ctr_align)
            begin
               fract_b = fract_b >> 1;
               exp_b_bias = exp_b_bias + 1;
               ctr_align = ctr_align - 1;
            end





//add fractions
      {cout, sum} = fract_a + fract_b;

//normalize result
      if (cout == 1)
         begin
            {cout, sum} = {cout, sum} >> 1;
            exp_b_bias = exp_b_bias + 1;
         end

      sign = sign_a;
      exponent = exp_b_bias;
      exp_unbiased = exp_b_bias - 8'b0111_1111;

end

endmodule


//test bench for floating-point addition
module add_flp3_tb;
reg [31:0] flp_a, flp_b;
wire sign;
wire [7:0] exponent;
wire [22:0] sum;
initial              //display variables
$monitor ("sign=%b, exp_biased=%b, exp_unbiased=%b, sum=%b",
               sign, exponent, exp_unbiased, sum);
initial              //apply input vectors
begin
         //+12 + +35 = +47
         //          s ----e---- --------------f-------------
   #0    flp_a = 32'b0_0000_0100_1100_0000_0000_0000_0000_000;
         flp_b = 32'b0_0000_0110_1000_1100_0000_0000_0000_000;

         //+26 + +20 = +46
         //          s ----e---- --------------f-------------
   #10   flp_a = 32'b0_0000_0101_1101_0000_0000_0000_0000_000;
         flp_b = 32'b0_0000_0101_1010_0000_0000_0000_0000_000;

         //+26.5 + +4.375 = +30.875
         //          s ----e---- --------------f-------------
   #10   flp_a = 32'b0_0000_0101_1101_0100_0000_0000_0000_000;
         flp_b = 32'b0_0000_0011_1000_1100_0000_0000_0000_000;

         //+11 + +34 = +45
         //          s ----e---- --------------f-------------
   #10   flp_a = 32'b0_0000_0100_1011_0000_0000_0000_0000_000;
         flp_b = 32'b0_0000_0110_1000_1000_0000_0000_0000_000;

         //+23.75 + +87.125 = +110.875
         //          s ----e---- --------------f-------------
   #10   flp_a = 32'b0_0000_0101_1011_1110_0000_0000_0000_000;
         flp_b = 32'b0_0000_0111_1010_1110_0100_0000_0000_000;

   #10      $stop;

end


//instantiate the module into the test bench
add_flp3 inst1 (                   
      .flp_a(flp_a),
      .flp_b(flp_b),
      .sign(sign),
      .exponent(exponent),
      .exp_unbiased(exp_unbiased),
      .sum(sum)
      );

endmodule




No comments:

Post a Comment