Skip to content

Commit

Permalink
Parity (#47)
Browse files Browse the repository at this point in the history
  • Loading branch information
RPG-coder-intc authored Oct 23, 2023
1 parent 6b9313b commit 7478a31
Show file tree
Hide file tree
Showing 4 changed files with 166 additions and 0 deletions.
13 changes: 13 additions & 0 deletions doc/parity.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
# Parity

ROHD HCL implements `Parity` functionality class that other modules can apply error checking. For satisfying the functionality of Parity error checking in `Logic` data, ROHD HCL provides 2 `Module`, namely `ParityTransmitter` and `ParityReceiver`.

## Parity Transmitter

The `ParityTransmitter` is a module that accepts a Logic `bus` for data and makes the data `bus` suitable for transmission with parity. A parity check is handled by appending parity bit to `bus` data.

## Parity Receiver

The `ParityReceiver` is a module that accepts a Logic `bus` for transmitted data with a parity bit appended. The receiver functionality splits the provided `bus` into original `data` and `parityBit`. Also, the process of parity error check is handled within this module at result output `checkError`.

Please visit [API docs](https://intel.github.io/rohd-hcl/rohd_hcl/rohd_hcl-library.html) for more details about parity.
1 change: 1 addition & 0 deletions lib/rohd_hcl.dart
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@ export 'src/memory/memories.dart';
export 'src/models/models.dart';
export 'src/multiplier.dart';
export 'src/one_hot.dart';
export 'src/parity.dart';
export 'src/ripple_carry_adder.dart';
export 'src/rotate.dart';
export 'src/shift_register.dart';
Expand Down
79 changes: 79 additions & 0 deletions lib/src/parity.dart
Original file line number Diff line number Diff line change
@@ -0,0 +1,79 @@
// Copyright (C) 2023 Intel Corporation
// SPDX-License-Identifier: BSD-3-Clause
//
// parity.dart
// Implementation of Parity modules.
//
// 2023 August 20
// Author: Rahul Gautham Putcha <[email protected]>
//

import 'package:rohd/rohd.dart';

/// Encode data to transport with Parity bits
class ParityTransmitter extends Module {
/// [_output] is output of parity
/// (use index for accessing from outside Module)
late Logic _output;

/// [data] is an getter for transmit data having a parity check
Logic get data => _output;

/// [parity] is a getter for parity bit
Logic get parity => output('parity');

/// Construct a [Module] for generating transmit data [data].
/// Combine given [Logic] named [bus] with a parity bit for error check after
/// transmission
ParityTransmitter(Logic bus) {
bus = addInput('bus', bus, width: bus.width);
addOutput('parity');
parity <= bus.xor();
final transmitData = [parity, bus].swizzle();
_output = addOutput('transmitData', width: transmitData.width);
_output <= transmitData;
}
}

/// Check for error & Receive data on transmitted data via parity
class ParityReceiver extends Module {
/// [_checkError] is parity with result `0` for success and `1` for fail
late Logic _checkError;

/// [_parityBit] is parity bit appended to transmitted data for parity
late Logic _parityBit;

/// [_data] is transmitted data (not containing without [_parityBit])
late Logic _data;

/// [checkError] is an getter for parity result with
/// `0` for success and `1` for fail
Logic get checkError => _checkError;

/// [data] is an getter for transmitted/original data (without [parityBit])
Logic get data => _data;

/// [parityBit] is an getter for parity Bit received upon data transmission
Logic get parityBit => _parityBit;

/// Constructs a [Module] which encodes data transmitted via parity.
/// This will split the transmitted data in [bus] into 2 parts: the [data]
/// having the original, and the error bit upon which [checkError] is
/// calculated for parity error checking.
ParityReceiver(Logic bus) {
bus = addInput('bus', bus, width: bus.width);

// Slice from 1 from least significant bit to the end
final transmittedData = bus.slice(-2, 0);
final parityBit = bus[-1];
final parityError = ~transmittedData.xor().eq(parityBit);

_data = addOutput('transmittedData', width: transmittedData.width);
_parityBit = addOutput('parityBit', width: parityBit.width);
_checkError = addOutput('checkError', width: parityError.width);

_data <= transmittedData;
_parityBit <= parityBit;
_checkError <= parityError;
}
}
73 changes: 73 additions & 0 deletions test/parity_test.dart
Original file line number Diff line number Diff line change
@@ -0,0 +1,73 @@
// Copyright (C) 2023 Intel Corporation
// SPDX-License-Identifier: BSD-3-Clause
//
// arbiter_test.dart
// Tests for arbiters
//
// 2023 March 13
// Author: Rahul Gautham Putcha <[email protected]>
//

import 'package:rohd/rohd.dart';
import 'package:rohd_hcl/rohd_hcl.dart';
import 'package:rohd_hcl/src/parity.dart';
import 'package:test/test.dart';

void main() {
test('parity transmitter', () async {
const width = 8;

final vector = Logic(width: width);

final parityTransmitter = ParityTransmitter(vector);

vector.put(bin('00000000'));
expect(parityTransmitter.data.value, LogicValue.ofString('000000000'));

vector.put(bin('00000001'));
expect(parityTransmitter.data.value, LogicValue.ofString('100000001'));

vector.put(bin('10000001'));
expect(parityTransmitter.data.value, LogicValue.ofString('010000001'));

vector.put(bin('10001001'));
expect(parityTransmitter.data.value, LogicValue.ofString('110001001'));

vector.put(bin('11111101'));
expect(parityTransmitter.data.value, LogicValue.ofString('111111101'));

vector.put(bin('11111111'));
expect(parityTransmitter.data.value, LogicValue.ofString('011111111'));
});

test('parity receiver checking', () async {
const width = 9;

final vector = Logic(width: width);

final parityReceiver = ParityReceiver(vector);

vector.put(bin('000000000'));
expect(parityReceiver.data.value, LogicValue.ofString('00000000'));
expect(parityReceiver.parityBit.value, LogicValue.ofString('0'));
expect(parityReceiver.checkError.value, LogicValue.ofString('0'));

vector.put(bin('011111111'));
expect(parityReceiver.data.value, LogicValue.ofString('11111111'));
expect(parityReceiver.parityBit.value, LogicValue.ofString('0'));
expect(parityReceiver.checkError.value, LogicValue.ofString('0'));

vector.put(bin('111111101'));
expect(parityReceiver.data.value, LogicValue.ofString('11111101'));
expect(parityReceiver.parityBit.value, LogicValue.ofString('1'));
expect(parityReceiver.checkError.value, LogicValue.ofString('0'));

vector.put(bin('111110101'));
expect(parityReceiver.data.value, LogicValue.ofString('11110101'));
// This is set to check the incorrect parity bit on purpose
expect(parityReceiver.parityBit.value, LogicValue.ofString('1'));
// checkError equals to `1` means the parity check fail and
// have noted error in the transmitted data
expect(parityReceiver.checkError.value, LogicValue.ofString('1'));
});
}

0 comments on commit 7478a31

Please sign in to comment.