diff --git a/src/V3WidthSel.cpp b/src/V3WidthSel.cpp index d9aab723a..5b19b7e9c 100644 --- a/src/V3WidthSel.cpp +++ b/src/V3WidthSel.cpp @@ -279,10 +279,16 @@ private: VNumRange fromRange = fromdata.m_fromRange; if (ddtypep->castUnpackArrayDType()) { // Slice extraction - AstArraySel* newp = new AstArraySel (nodep->fileline(), fromp, lsbp); - newp->start(lsb); - newp->length((msb - lsb) + 1); - nodep->replaceWith(newp); pushDeletep(nodep); nodep=NULL; + if (fromRange.elements() == (msb-lsb+1) + && fromRange.lo() == lsb) { // Extracting whole of original array + nodep->replaceWith(fromp); pushDeletep(nodep); nodep=NULL; + } else { + // TODO when unpacked arrays fully supported probably need new data type here + AstArraySel* newp = new AstArraySel (nodep->fileline(), fromp, lsbp); + newp->start(lsb); + newp->length((msb - lsb) + 1); + nodep->replaceWith(newp); pushDeletep(nodep); nodep=NULL; + } } else if (AstPackArrayDType* adtypep = ddtypep->castPackArrayDType()) { // SELEXTRACT(array, msb, lsb) -> SEL(array, lsb*width-of-subindex, width-of-subindex*(msb-lsb)) @@ -296,7 +302,8 @@ private: new AstConst(nodep->fileline(),AstConst::Unsized32(),(msb-lsb+1)*elwidth)); newp->declRange(fromRange); newp->declElWidth(elwidth); - if (fromRange.elements() == (msb-lsb+1)) { // Extracting whole of original array + if (fromRange.elements() == (msb-lsb+1) // Extracting whole of original array + && fromRange.lo() == lsb) { newp->dtypeFrom(adtypep); } else { // Need a slice data type, which is an array of the extracted type, but with (presumably) different size diff --git a/test_regress/t/t_inst_port_array.pl b/test_regress/t/t_inst_port_array.pl new file mode 100755 index 000000000..f91289753 --- /dev/null +++ b/test_regress/t/t_inst_port_array.pl @@ -0,0 +1,18 @@ +#!/usr/bin/perl +if (!$::Driver) { use FindBin; exec("$FindBin::Bin/bootstrap.pl", @ARGV, $0); die; } +# DESCRIPTION: Verilator: Verilog Test driver/expect definition +# +# Copyright 2003 by Wilson Snyder. This program is free software; you can +# redistribute it and/or modify it under the terms of either the GNU +# Lesser General Public License Version 3 or the Perl Artistic License +# Version 2.0. + +compile ( + ); + +execute ( + check_finished=>1, + ); + +ok(1); +1; diff --git a/test_regress/t/t_inst_port_array.v b/test_regress/t/t_inst_port_array.v new file mode 100644 index 000000000..dd697f074 --- /dev/null +++ b/test_regress/t/t_inst_port_array.v @@ -0,0 +1,48 @@ +// DESCRIPTION: Verilator: Verilog Test module +// +// This file ONLY is placed into the Public Domain, for any use, +// without warranty, 2013 by Alex Solomatnikov. + +module t (/*AUTOARG*/ + // Inputs + clk + ); + input clk; + + logic [6-1:0] foo[4-1:0]; + + //initial $display("%m: %p\n", foo); + //initial $display("%m: %p\n", foo[3:0]); // VCS not supported %p with slice + //logic [6-1:0] foo2[4-1:0][5:6]; + //initial $display("%m: %p\n", foo2[3:0][5:6]); // This is not legal + + dut #(.W(6), + .D(4)) udut(.clk(clk), + .foo(foo[4-1:0])); +endmodule + +module dut + #(parameter W = 1, + parameter D = 1) + (input logic clk, + input logic [W-1:0] foo[D-1:0]); + + genvar i, j; + generate + for (j = 0; j < D; j++) begin + for (i = 0; i < W; i++) begin + suba ua(.clk(clk), .foo(foo[j][i])); + end + end + endgenerate +endmodule + +module suba + (input logic clk, + input logic foo); + + always @(posedge clk) begin + $write("*-* All Finished *-*\n"); + $finish; + end +endmodule diff --git a/test_regress/t/t_mem_slice.v b/test_regress/t/t_mem_slice.v index 5d14f0253..511d3882b 100644 --- a/test_regress/t/t_mem_slice.v +++ b/test_regress/t/t_mem_slice.v @@ -35,7 +35,8 @@ module t (/*AUTOARG*/ assign active_command[8:0] = (use_AnB) ? command_A[8:0] : command_B[8:0]; assign active_command2 = (use_AnB) ? command_A2 : command_B2; - assign active_command3[1:0][2:0][3:0] = (use_AnB) ? command_A3[1:0][2:0][3:0] : command_B3[1:0][2:0][3:0]; + // Illegal to have [1:0][x:y] here - IEEE only allows single dimension slicing + assign active_command3[1:0] = (use_AnB) ? command_A3[1:0] : command_B3[1:0]; // Check we can cope with things other than packed arrays assign active_command4 = (use_A4nB4[0]) ? command_A4 : command_B4; diff --git a/test_regress/t/t_mem_slice_bad.pl b/test_regress/t/t_mem_slice_bad.pl index 6f96db7a0..8fd4613c2 100755 --- a/test_regress/t/t_mem_slice_bad.pl +++ b/test_regress/t/t_mem_slice_bad.pl @@ -15,7 +15,6 @@ compile ( expect=> '%Error: t/t_mem_slice_bad.v:\d+: Slices of arrays in assignments must have the same unpacked dimensions %Error: t/t_mem_slice_bad.v:\d+: Slices of arrays in assignments must have the same unpacked dimensions -%Error: t/t_mem_slice_bad.v:\d+: Slices of arrays in assignments must have the same unpacked dimensions %Error: t/t_mem_slice_bad.v:\d+: Unsupported: Slices in a non-delayed assignment with the same Var on both sides %Error: t/t_mem_slice_bad.v:\d+: Slices of arrays in assignments must have the same unpacked dimensions %Error: t/t_mem_slice_bad.v:\d+: Slices of arrays in assignments must have the same unpacked dimensions