Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

42compress #142

Open
wants to merge 18 commits into
base: main
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from 5 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
50 changes: 3 additions & 47 deletions lib/src/arithmetic/addend_compressor.dart
Original file line number Diff line number Diff line change
Expand Up @@ -12,50 +12,6 @@ import 'package:meta/meta.dart';
import 'package:rohd/rohd.dart';
import 'package:rohd_hcl/rohd_hcl.dart';

// /// Base class for bit-level column compressor function
// abstract class BitCompressor extends Module {
// /// Input bits to compress
// @protected
// late final Logic compressBits;

// /// The addition results [sum] including carry bit
// Logic get sum => output('sum');

// /// The carry results [carry].
// Logic get carry => output('carry');

// /// Construct a column compressor
// BitCompressor(Logic compressBits, {super.name = 'bit_compressor'}) {
// this.compressBits = addInput(
// 'compressBits',
// compressBits,
// width: compressBits.width,
// );
// addOutput('sum');
// addOutput('carry');
// }
// }

// /// 2-input column compressor (half-adder)
// class Compressor2 extends BitCompressor {
// /// Construct a 2-input compressor (half-adder)
// Compressor2(super.compressBits, {super.name = 'compressor_2'}) {
// sum <= compressBits.xor();
// carry <= compressBits.and();
// }
// }

// /// 3-input column compressor (full-adder)
// class Compressor3 extends BitCompressor {
// /// Construct a 3-input column compressor (full-adder)
// Compressor3(super.compressBits, {super.name = 'compressor_3'}) {
// sum <= compressBits.xor();
// carry <=
// mux(compressBits[0], compressBits.slice(2, 1).or(),
// compressBits.slice(2, 1).and());
// }
// }

/// Compress terms
enum CompressTermType {
/// A cout (horizontal carry)
Expand Down Expand Up @@ -248,9 +204,9 @@ class Compressor4 extends BitCompressor {
: super(terms) {
// We need to use internal Logic and regenerate Term lists inside
cinL = [
for (final cin in cinL)
CompressTerm(this, cin.type, addInput('cin', cin.logic), cin.inputs,
cin.row, cin.col)
for (final (i, c) in cinL.indexed)
CompressTerm(
this, c.type, addInput('cin_$i', c.logic), c.inputs, c.row, c.col)
];
final internalTerms = [
for (var i = 0; i < compressBits.width; i++)
Expand Down
10 changes: 9 additions & 1 deletion lib/src/arithmetic/multiplier.dart
Original file line number Diff line number Diff line change
Expand Up @@ -357,7 +357,15 @@ class CompressionTreeMultiplier extends Multiplier {
{String name})
seGen = CompactRectSignExtension.new,
bool use42Compressors = false,
super.name = 'compression_tree_multiplier'}) {
super.name = 'compressison_tree_multiplier'})
: super(
definitionName: 'CompressionTreeMultiplier_W${a.width}x'
'${b.width}_'
'${signedMultiplicand ? 'SD_' : ''}'
'${signedMultiplier ? 'SM_' : ''}'
'${selectSignedMultiplicand != null ? 'SSD_' : ''}'
'${selectSignedMultiplier != null ? 'SSM_' : ''}'
'with${adderGen(a, b).definitionName}') {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

this call to adderGen i think will actually construct an adder connected to those ports, which could lead to additional verilog generation (outside of the module, even) and also slow down simulation since it's simulating a whole additional adder. i think i remember seeing this pattern in a few other places as well and didnt think it through.

// Should be done in base TODO(desmonddak):
final product = addOutput('product', width: a.width + b.width);
final pp = PartialProductGenerator(
Expand Down
53 changes: 53 additions & 0 deletions lib/src/arithmetic/values/logicvalue_extension.dart
Original file line number Diff line number Diff line change
@@ -0,0 +1,53 @@
// Copyright (C) 2025 Intel Corporation
// SPDX-License-Identifier: BSD-3-Clause
//
// logicvalue_extension.dart
// Utilities for LogicValue as an extension.
//
// 2025 January 31
// Author: Desmond Kirkpatrick <[email protected]>

import 'package:rohd/rohd.dart';
import 'package:rohd_hcl/rohd_hcl.dart';

/// This extension will eventually move to ROHD once it is proven useful
extension LogicValueMajority on LogicValue {
/// Compute the unary majority on LogicValue
bool majority() {
if (!isValid) {
return false;
}
final zero = LogicValue.filled(width, LogicValue.zero);
var shiftedValue = this;
var result = 0;
while (shiftedValue != zero) {
result += (shiftedValue[0] & LogicValue.one == LogicValue.one) ? 1 : 0;
shiftedValue >>>= 1;
}
return result > (width ~/ 2);
}

/// Compute the first One find operation on LogicValue, returning its position
int? firstOne() {
if (!isValid) {
return null;
}
var shiftedValue = this;
var result = 0;
while (shiftedValue[0] != LogicValue.one) {
result++;
if (result == width) {
return null;
}
shiftedValue >>>= 1;
}
return result;
}

/// Return the populationCount of 1s in a LogicValue
int popCount() {
final r = RegExp('1');
final matches = r.allMatches(bitString);
return matches.length;
}
}
50 changes: 8 additions & 42 deletions test/arithmetic/addend_compressor_test.dart
Original file line number Diff line number Diff line change
Expand Up @@ -14,50 +14,9 @@ import 'package:rohd_hcl/rohd_hcl.dart';
import 'package:rohd_hcl/src/arithmetic/evaluate_compressor.dart';
import 'package:rohd_hcl/src/arithmetic/evaluate_partial_product.dart';
import 'package:rohd_hcl/src/arithmetic/partial_product_sign_extend.dart';
import 'package:rohd_hcl/src/arithmetic/values/logicvalue_extension.dart';
import 'package:test/test.dart';

/// This extension will eventually move to ROHD once it is proven useful
extension LogicValueMajority on LogicValue {
/// Compute the unary majority on LogicValue
bool majority() {
if (!isValid) {
return false;
}
final zero = LogicValue.filled(width, LogicValue.zero);
var shiftedValue = this;
var result = 0;
while (shiftedValue != zero) {
result += (shiftedValue[0] & LogicValue.one == LogicValue.one) ? 1 : 0;
shiftedValue >>>= 1;
}
return result > (width ~/ 2);
}

/// Compute the first One find operation on LogicValue, returning its position
int? firstOne() {
if (!isValid) {
return null;
}
var shiftedValue = this;
var result = 0;
while (shiftedValue[0] != LogicValue.one) {
result++;
if (result == width) {
return null;
}
shiftedValue >>>= 1;
}
return result;
}

/// Return the populationCount of 1s in a LogicValue
int popCount() {
final r = RegExp('1');
final matches = r.allMatches(bitString);
return matches.length;
}
}

/// This [CompressorTestMod] module is used to test instantiation, where we can
/// catch trace errors (IO not added) not found in a simple test instantiation.
class CompressorTestMod extends Module {
Expand Down Expand Up @@ -201,4 +160,11 @@ void main() {
}
}
});
test('majority function', () async {
expect(LogicValue.ofBigInt(BigInt.from(7), 5).majority(), true);
expect(LogicValue.ofBigInt(BigInt.from(7) << 1, 5).majority(), true);
expect(LogicValue.ofBigInt(BigInt.from(11) << 1, 5).majority(), true);
expect(LogicValue.ofBigInt(BigInt.from(9) << 1, 5).majority(), false);
expect(LogicValue.ofBigInt(BigInt.from(7) << 3, 7).majority(), false);
});
}
3 changes: 2 additions & 1 deletion test/arithmetic/multiplier_test.dart
Original file line number Diff line number Diff line change
Expand Up @@ -521,7 +521,7 @@ void main() {
});

test('single multiplier', () async {
const width = 8;
const width = 16;
final a = Logic(name: 'a', width: width);
final b = Logic(name: 'b', width: width);
const av = 12;
Expand All @@ -544,6 +544,7 @@ void main() {
b.put(bB);

final mod = CompressionTreeMultiplier(a, b, 4,
use42Compressors: true,
adderGen: ParallelPrefixAdder.new,
seGen: StopBitsSignExtension.new,
signedMultiplier: !useSignedLogic && signed,
Expand Down