Attention
This documentation is a work in progress. Expect to see errors and unfinished things.
saturateMath Source File
1/////////////////////////////////////////////////////////
2// Useful modules for performing saturating arithmetic //
3/////////////////////////////////////////////////////////
4
5// Expand a net's width
6module expandWidth #(
7 parameter IWIDTH = 8,
8 parameter OWIDTH = 12) (
9 input wire [IWIDTH-1:0] I,
10 output wire [OWIDTH-1:0] O);
11
12wire signBit;
13assign signBit = I[IWIDTH-1];
14assign O = {{OWIDTH-IWIDTH{signBit}}, I};
15endmodule
16
17// Reduce a net's width
18module reduceWidth #(
19 parameter IWIDTH = 12,
20 parameter OWIDTH = 8) (
21 input wire [IWIDTH-1:0] I,
22 output reg [OWIDTH-1:0] O);
23
24wire signBit;
25assign signBit = I[IWIDTH-1];
26wire [IWIDTH-OWIDTH-1:0] checkBits;
27assign checkBits = I[IWIDTH-2-:IWIDTH-OWIDTH];
28
29always @(I, signBit, checkBits) begin
30 if ((signBit == 1'b0) && (|checkBits == 1'b1)) begin
31 O = {1'b0, {OWIDTH-1{1'b1}}};
32 end
33 else if ((signBit == 1'b1) && (&checkBits != 1'b1)) begin
34 O = {1'b1, {OWIDTH-1{1'b0}}};
35 end
36 else begin
37 O = I[OWIDTH-1:0];
38 end
39end
40endmodule
41
42// Saturating addition
43module saturateAdd #(
44 parameter AWIDTH = 8,
45 parameter BWIDTH = 8,
46 parameter SUMWIDTH = 8) (
47 input wire [AWIDTH-1:0] A,
48 input wire [BWIDTH-1:0] B,
49 output wire [SUMWIDTH-1:0] SUM);
50
51localparam FULLWIDTH = (AWIDTH > BWIDTH) ? AWIDTH+1 : BWIDTH+1;
52
53wire [FULLWIDTH-1:-0] fullWidthA, fullWidthB, fullWidthSum;
54assign fullWidthA = {{FULLWIDTH-AWIDTH{A[AWIDTH-1]}}, A};
55assign fullWidthB = {{FULLWIDTH-BWIDTH{B[BWIDTH-1]}}, B};
56assign fullWidthSum = fullWidthA + fullWidthB;
57reduceWidth #(.IWIDTH(FULLWIDTH),.OWIDTH(SUMWIDTH))rw(.I(fullWidthSum),.O(SUM));
58endmodule
59
60// Saturating subtraction
61module saturateSub #(
62 parameter AWIDTH = 8,
63 parameter BWIDTH = 8,
64 parameter DIFFWIDTH = 8) (
65 input wire [AWIDTH-1:0] A,
66 input wire [BWIDTH-1:0] B,
67 output wire [DIFFWIDTH-1:0] DIFF);
68
69localparam FULLWIDTH = (AWIDTH > BWIDTH) ? AWIDTH+1 : BWIDTH+1;
70
71wire [FULLWIDTH-1:-0] fullWidthA, fullWidthB, fullWidthDiff;
72assign fullWidthA = {{FULLWIDTH-AWIDTH{A[AWIDTH-1]}}, A};
73assign fullWidthB = {{FULLWIDTH-BWIDTH{B[BWIDTH-1]}}, B};
74assign fullWidthDiff = fullWidthA - fullWidthB;
75reduceWidth #(.IWIDTH(FULLWIDTH),.OWIDTH(DIFFWIDTH))rw(.I(fullWidthDiff),.O(DIFF));
76endmodule