circt
circt copied to clipboard
[comb] Missing Optimization to Build Reduction Ops
We are missing an optimization to build reduction ops when possible. Consider the following which is doing b[0] | b[1]:
module {
hw.module @Foo(%a: i1, %b: i2) -> (c: i1) {
%0 = comb.extract %b from 1 : (i2) -> i1
%1 = comb.extract %b from 0 : (i2) -> i1
%2 = comb.or %0, %1 {sv.namehint = "_b"} : i1
hw.output %2 : i1
}
}
This produces:
module Foo(
input a,
input [1:0] b,
output c);
assign c = b[1] | b[0];
endmodule
It would be better to produce (comb.icmp ne 0):
assign c = |b;
This optimization should be possible for any of comb.or, comb.and, and comb.xor.
On 13ea7a51d79dd2d3dc26b1f2474978148727956f I get
// Generated by CIRCT unknown git version
module Foo( // comb.mlir:2:3
input a, // comb.mlir:2:21
input [1:0] b, // comb.mlir:2:32
output c // comb.mlir:2:44
);
assign c = |b; // comb.mlir:5:10, :6:5
endmodule
module {
hw.module @Foo(in %a : i1, in %b : i2, out c : i1) {
%c0_i2 = hw.constant 0 : i2
%0 = comb.icmp ne %b, %c0_i2 {sv.namehint = "_b"} : i2
hw.output %0 : i1
}
}
It seems to me that @Schottkyc137 solved this in ecd49163a5f593b46df8e11ce80dd296e1723767 as a part of #3394.