| |
`timescale 1ns/1ns
module square_root
(
input clk,
input rst,
input load,
input [23:0] data_in,
input load_sqrt,
output reg [11:0] data_out
);
reg [25:0] data_in_shift;
wire [13:0] r_sub;
wire [13:0] r_add;
wire [13:0] r_q;
reg [13:0] r;
reg [13:0] q;
always @ (posedge clk or posedge rst)
begin
if (rst == 1'b1)
data_in_shift <= 26'd0;
else if (load == 1'b1)
data_in_shift <= {data_in,2'd0};
else
data_in_shift <= data_in_shift << 2;
end
assign r_sub = {r[11:0],data_in_shift[25:24]} - {q[11:0],2'b01};
assign r_add = {r[11:0],data_in_shift[25:24]} + {1'b0,q[10:0],2'b11};
assign r_q = (r[13] == 1'b1)? r_add: r_sub;
always @ (posedge clk or posedge rst)
begin
if (rst == 1'b1)
r <= 14'd0;
else if (load == 1'b1)
r <= 14'd0;
else
r <= r_q;
end
always @ (posedge clk or posedge rst)
begin
if (rst == 1'b1)
q <= 14'd0;
else if (load == 1'b1)
q <= 14'd0;
else if (r_q[13] == 1'b1)
q <= {q[12:0],1'b0};
else
q <= {q[12:0],1'b1};
end
always @ (posedge clk or posedge rst)
begin
if (rst == 1'b1)
data_out <= 12'd0;
else if (load_sqrt == 1'b1)
data_out <= q[12:0];
else ;
end
endmodule