1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141
|
// DESCRIPTION: Verilator: Verilog Test module
//
// This file ONLY is placed under the Creative Commons Public Domain, for
// any use, without warranty, 2014 by Wilson Snyder.
// SPDX-License-Identifier: CC0-1.0
`define checkh(gotv,expv) do if ((gotv) !== (expv)) begin $write("%%Error: %s:%0d: got='h%x exp='h%x\n", `__FILE__,`__LINE__, (gotv), (expv)); fail='1; end while(0)
`define checkf(gotv,expv) do if ((gotv) !== (expv)) begin $write("%%Error: %s:%0d: got=%f exp=%f\n", `__FILE__,`__LINE__, (gotv), (expv)); fail='1; end while(0)
module t (/*AUTOARG*/);
bit fail;
localparam signed [3:0] bug737_p1 = 4'b1000;
wire [3:0] bug737_a = 4'b1010;
reg [5:0] bug737_y;
reg signed [3:0] w4_s;
reg signed [4:0] w5_s;
reg [3:0] w4_u;
reg [4:0] w5_u;
reg signed [8:0] w9_s;
real r;
initial begin
// verilator lint_off WIDTH
bug737_y = bug737_a + (bug737_p1 + 4'sb0);
`checkh(bug737_y, 6'b010010); //bug737
// 6u +[6u] 4s +[6s] 6s
bug737_y = 6'b001010 + (4'sb1000 + 6'sb0);
`checkh(bug737_y, 6'b010010); //bug737, getx 000010
// 6u +[6u] 4s +[6s] 6s
bug737_y = 6'b001010 + (4'b1000 + 6'sb0);
`checkh(bug737_y, 6'b010010); //ok
bug737_y = 6'b001010 + (6'sb111000 + 6'sb0);
`checkh(bug737_y, 6'b000010); //ok
// v--- sign extends to 6-bits
bug737_y = 6'sb001010 + (4'sb1000 + 6'sb0);
`checkh(bug737_y, 6'b000010); //ok
// From t_math_signed_3
w4_s = 4'sb1111 - 1'b1;
`checkh(w4_s,33'he);
w4_s = 4'sb1111 - 5'b00001;
`checkh(w4_s,33'he);
w4_s = 4'sb1111 - 1'sb1;
`checkh(w4_s,4'h0);
w5_s = 4'sb1111 - 1'sb1;
`checkh(w5_s,4'h0);
w4_s = 4'sb1111 - 4'sb1111;
`checkh(w4_s,4'h0);
w5_s = 4'sb1111 - 4'sb1111;
`checkh(w5_s,5'h0);
// The assign LHS being signed or unsigned does not matter per IEEE
// The upper add being signed DOES matter propagating to lower
w4_s = 4'sb1111 - (1'sb1 + 4'b0); //1'sb1 not extended as unsigned add
`checkh(w4_s,4'he);
w4_s = 4'sb1111 - (1'sb1 + 4'sb0); //1'sb1 does sign extend
`checkh(w4_s,4'h0);
w4_s = 4'b1111 - (1'sb1 + 4'sb0); //1'sb1 does *NOT* sign extend
`checkh(w4_s,4'he); // BUG, Verilator says 'h0
w5_u = 4'b1111 + 4'b0001; // Extends to 5 bits due to LHS
`checkh(w5_u, 5'b10000);
w4_u = 4'b1111 + 4'b0001; // Normal case
`checkh(w4_u, 4'b0000);
// Another example of promotion, the add is 4 bits wide
w4_u = 3'b111 + 3'b010;
`checkh(w4_u, 4'b1001);
//
w4_u = 3'sb111 * 3'sb001; // Signed output, LHS does not matter
`checkh(w4_u, 4'sb1111);
w4_s = 3'sb111 * 3'sb001; // Signed output
`checkh(w4_s, 4'sb1111);
w4_s = 3'b111 * 3'sb001; // Unsigned output
`checkh(w4_s, 4'b0111);
// Conditionals get width from parent; are assignment-like
w4_u = 1'b0 ? 4'b0 : (2'b01+2'b11);
`checkh(w4_u, 4'b0100);
w4_u = 1'b0 ? 4'b0 : (6'b001000+6'b001000);
`checkh(w4_u, 4'b0000);
// If RHS is larger, that larger size is used
w4_u = 5'b10000 / 5'b00100;
`checkh(w4_u, 4'b0100);
// bug754
w5_u = 4'sb0010 << -2'sd1; // << 3
`ifdef VCS
`checkh(w5_u, 5'b00000); // VCS E-2014.03 bug
`else
`checkh(w5_u, 5'b10000); // VCS E-2014.03 bug
`endif
w5_u = 4'sb1000 << 0; // Sign extends
`checkh(w5_u, 5'b11000);
// Reals do not propagate to children
r = 1.0 + ( 1 + (1 / 2));
`checkf(r, 2.0);
// Self determined sign extension
r = $itor(3'sb111);
`checkf(r, -1.0);
// If any part of case is real, all is real
case (22)
22.0: ;
22.1: $stop;
default: $stop;
endcase
// bug759
w5_u = { -4'sd7 };
`checkh(w5_u, 5'b01001);
w5_u = {2{ -2'sd1 }};
`checkh(w5_u, 5'b01111);
// Don't break concats....
w5_u = {{0{1'b1}}, -4'sd7 };
`checkh(w5_u, 5'b01001);
w9_s = { -4'sd7, -4'sd7 };
`checkh(w9_s, 9'b010011001);
{w5_u, {w4_u}} = 9'b10101_1100;
`checkh(w5_u, 5'b10101);
`checkh(w4_u, 4'b1100);
{w4_u} = 4'b1011;
`checkh(w4_u, 4'b1011);
if (fail) $stop;
$write("*-* All Finished *-*\n");
$finish;
end
endmodule
|