Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- `timescale 1ns/1ps
- module divider
- #(
- parameter DIVIDEND_WIDTH = 16,
- parameter DIVISOR_WIDTH = 8,
- parameter QUOTIENT_WIDTH = 16,
- parameter TWO_STAGE_SUB = 1
- )
- (
- input wire clk,
- input wire start,
- input wire reset,
- input wire [DIVIDEND_WIDTH - 1:0] dividend,
- input wire [DIVISOR_WIDTH - 1:0] divisor,
- output wire [QUOTIENT_WIDTH - 1:0] quotient,
- output wire ready
- );
- localparam STATE_IDLE = 0;
- localparam STATE_SHIFT = 1;
- localparam STATE_SUB = 2;
- reg [7:0] state;
- reg args_comp = 1'b0;
- reg [$clog2(DIVIDEND_WIDTH) - 1:0] cnt = 'b0;
- reg sub_trig = 1'b0;
- reg [DIVIDEND_WIDTH - 1:0] reg_sub = 'b0;
- reg [DIVIDEND_WIDTH - 1:0] dividend_reg = 'b0;
- reg [DIVIDEND_WIDTH - 1:0] divisor_reg = 'b0;
- reg [DIVIDEND_WIDTH - 1:0] quotient_reg = 'b0;
- assign quotient = quotient_reg[QUOTIENT_WIDTH - 1:0];
- assign ready = state == STATE_IDLE;
- always @(posedge clk) begin
- args_comp <= (divisor_reg <= dividend_reg);
- reg_sub <= dividend_reg - divisor_reg;
- end
- always @(posedge clk) begin
- case (state)
- STATE_IDLE: begin
- if (start) begin
- state <= STATE_SHIFT;
- cnt <= 'b1;
- sub_trig <= 1'b0;
- dividend_reg <= dividend;
- quotient_reg <= 'b0;
- divisor_reg <= divisor;
- end
- end
- STATE_SHIFT: begin
- cnt <= cnt + 1'b1;
- divisor_reg <= divisor_reg << 1;
- if ((divisor_reg & (1 << (DIVIDEND_WIDTH - 2))) || (cnt == {$clog2(DIVIDEND_WIDTH){1'b1}})) begin
- state <= STATE_SUB;
- end
- end
- STATE_SUB: begin
- if (TWO_STAGE_SUB) begin
- sub_trig <= !sub_trig;
- if (sub_trig) begin
- if (cnt == 'b1) begin
- state <= STATE_IDLE;
- end
- if (args_comp) begin
- dividend_reg <= reg_sub;
- quotient_reg <= (quotient_reg << 1) | 1'b1;
- end else begin
- quotient_reg <= (quotient_reg << 1);
- end
- divisor_reg <= divisor_reg >> 1;
- cnt <= cnt - 1'b1;
- end
- end else begin
- if (cnt == 'b1) begin
- state <= STATE_IDLE;
- end
- if (divisor_reg <= dividend_reg) begin
- dividend_reg <= dividend_reg - divisor_reg;
- quotient_reg <= (quotient_reg << 1) | 1'b1;
- end else begin
- quotient_reg <= (quotient_reg << 1);
- end
- divisor_reg <= divisor_reg >> 1;
- cnt <= cnt - 1'b1;
- end
- end
- default: begin
- state <= STATE_IDLE;
- end
- endcase
- end
- endmodule
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement