Skip to content

Commit

Permalink
Esop can now be built directly from a Lut
Browse files Browse the repository at this point in the history
  • Loading branch information
Coloquinte committed Jan 2, 2024
1 parent 01156d6 commit dd33412
Show file tree
Hide file tree
Showing 3 changed files with 71 additions and 0 deletions.
10 changes: 10 additions & 0 deletions src/sop/cube.rs
Original file line number Diff line number Diff line change
Expand Up @@ -95,6 +95,16 @@ impl Cube {
}
}

/// Build a cube directly from the integer masks
pub fn from_mask(pos: u32, neg: u32) -> Cube {
let c = Cube { pos, neg };
if c.is_zero() {
Cube::zero()
} else {
c
}
}

/// Return the number of literals
pub fn num_lits(&self) -> usize {
if self.is_zero() {
Expand Down
48 changes: 48 additions & 0 deletions src/sop/esop.rs
Original file line number Diff line number Diff line change
Expand Up @@ -183,6 +183,36 @@ impl fmt::Display for Esop {
}
}

impl From<&Lut> for Esop {
/// Obtain the canonical Esop representation, with only positive cubes
fn from(value: &Lut) -> Self {
// Whether the corresponding positive cube is present in the Esop
let mut esop_lut = value.clone();
let mut ret = Esop::zero(value.num_vars());
for i in 0..value.num_bits() {
if !esop_lut.get_bit(i) {
continue;
}
ret.cubes.push(Cube::from_mask(i as u32, 0));
// Update the value for the other cubes once this one is handled
for j in (i + 1)..value.num_bits() {
if !j & i == 0 {
esop_lut.set_value(j, !esop_lut.value(j));
}
}
// TODO: the above could use bitwise operations
// TODO: this is a linear boolean operation that can certainly be optimized further
}
ret
}
}

impl From<Lut> for Esop {
fn from(value: Lut) -> Self {
Esop::from(&value)
}
}

impl From<&Esop> for Lut {
fn from(value: &Esop) -> Self {
let mut ret = Lut::zero(value.num_vars());
Expand Down Expand Up @@ -221,6 +251,24 @@ mod tests {
}
}

#[test]
#[cfg(feature = "rand")]
fn test_random() {
use crate::Lut;

for i in 0..8 {
let l = Lut::zero(i);
assert_eq!(l, Esop::from(&l).into());
let l = Lut::one(i);
assert_eq!(l, Esop::from(&l).into());

for _ in 0..10 {
let l = Lut::random(i);
assert_eq!(l, Esop::from(&l).into());
}
}
}

#[test]
#[cfg(feature = "rand")]
fn test_xor() {
Expand Down
13 changes: 13 additions & 0 deletions src/sop/sop.rs
Original file line number Diff line number Diff line change
Expand Up @@ -325,6 +325,19 @@ mod tests {
}
}

#[test]
#[cfg(feature = "rand")]
fn test_random() {
use crate::Lut;

for i in 0..8 {
for _ in 0..10 {
let l = Lut::random(i);
assert_eq!(l, Sop::from(&l).into());
}
}
}

#[test]
#[cfg(feature = "rand")]
fn test_not() {
Expand Down

0 comments on commit dd33412

Please sign in to comment.